From dec8de7f50df2dbf5f34b4de420ca834d97884b2 Mon Sep 17 00:00:00 2001 From: Robert Bill <147130488+RobSlgm@users.noreply.github.com> Date: Fri, 17 Jul 2026 08:36:45 +0200 Subject: [PATCH 1/3] Update dependencies --- Data/Data.csproj | 28 ++++++++++++++-------------- Data/erm.sql | 4 ++-- Server.Tests/Server.Tests.csproj | 2 +- openapi.json | 2 +- 4 files changed, 18 insertions(+), 18 deletions(-) diff --git a/Data/Data.csproj b/Data/Data.csproj index d3f8889..398b8d3 100644 --- a/Data/Data.csproj +++ b/Data/Data.csproj @@ -9,23 +9,23 @@ e9f8dafb-10db-45a2-b53a-f8cdf43eab5e - - + + runtime; build; native; contentfiles; analyzers; buildtransitive all - - + + - - - - - - - - - - + + + + + + + + + + \ No newline at end of file diff --git a/Data/erm.sql b/Data/erm.sql index 92ac80c..962f379 100644 --- a/Data/erm.sql +++ b/Data/erm.sql @@ -567,7 +567,7 @@ DO $EF$ BEGIN IF NOT EXISTS(SELECT 1 FROM "__EFMigrationsHistory" WHERE "migration_id" = '20250425070016_CreateInitial') THEN INSERT INTO "__EFMigrationsHistory" (migration_id, product_version) - VALUES ('20250425070016_CreateInitial', '10.0.8'); + VALUES ('20250425070016_CreateInitial', '10.0.10'); END IF; END $EF$; COMMIT; @@ -661,7 +661,7 @@ DO $EF$ BEGIN IF NOT EXISTS(SELECT 1 FROM "__EFMigrationsHistory" WHERE "migration_id" = '20260622060127_BlobItem') THEN INSERT INTO "__EFMigrationsHistory" (migration_id, product_version) - VALUES ('20260622060127_BlobItem', '10.0.8'); + VALUES ('20260622060127_BlobItem', '10.0.10'); END IF; END $EF$; COMMIT; diff --git a/Server.Tests/Server.Tests.csproj b/Server.Tests/Server.Tests.csproj index 2391f1f..581137e 100644 --- a/Server.Tests/Server.Tests.csproj +++ b/Server.Tests/Server.Tests.csproj @@ -15,7 +15,7 @@ runtime; build; native; contentfiles; analyzers; buildtransitive all - + runtime; build; native; contentfiles; analyzers; buildtransitive diff --git a/openapi.json b/openapi.json index f5d179a..5cf9a96 100644 --- a/openapi.json +++ b/openapi.json @@ -10,7 +10,7 @@ "name": "MIT", "url": "https://mit-license.org/" }, - "version": "0.0.1" + "version": "0.8.0" }, "paths": { "/api/version": { From cc662263833a20bee641327505d9de69be3e4bb4 Mon Sep 17 00:00:00 2001 From: Robert Bill <147130488+RobSlgm@users.noreply.github.com> Date: Fri, 17 Jul 2026 11:48:33 +0200 Subject: [PATCH 2/3] Add webdav to readme and install instructions --- Doc/INSTALL.md | 33 +++++++++++++++++++++++++++++++++ README.md | 3 ++- 2 files changed, 35 insertions(+), 1 deletion(-) diff --git a/Doc/INSTALL.md b/Doc/INSTALL.md index fd804b8..c4662af 100644 --- a/Doc/INSTALL.md +++ b/Doc/INSTALL.md @@ -1,6 +1,10 @@ # Install Calendare Server - [Infrastructure requirements](#infrastructure-requirements) + - [Database](#database) + - [File storage](#file-storage) + - [S3 Storage Provider](#s3-storage-provider) + - [Local storage](#local-storage) - [DNS](#dns) - [Domain and subdomain](#domain-and-subdomain) - [Base Path Configuration](#base-path-configuration) @@ -18,8 +22,34 @@ The Calendare Server requires specific infrastructure to operate. +## Database + It uses a **PostgreSQL database** for data persistence and relies on an **OIDC provider** for user authentication. These components must be managed independently and are not covered in the following server installation guide. +The database contains user data and administrative data. The only exception relates to the WebDAV feature (file storage). The file contents are stored externally. + +## File storage + +File storage is only needed if the WebDAV feature is enabled (**not** for calendar or contact information). The default installation doesn't enable WebDAV. + +### S3 Storage Provider + +The **preferred** option is to use an external S3 provider (`provider: S3`). A dedicated bucket needs to be configured. + +> [!WARNING] +> The Calendare Server requires a dedicated bucket. It will regulary **delete** all content which is not managed by the server. + +### Local storage + +The local storage (`provider: Filesystem`) requires a base path to the local file system. Using Kubernetes this means that you need to define `PersistentVolumes` and `VolumeMounts`. + +While local storage is supported, it is primarily intended for development and testing. For production deployments, using an **S3-compatible provider** is highly recommended. + +> [!NOTE] +> Furthermore, if you run a multi-instance (highly available) setup, you must ensure your storage backend is distributed (supporting `ReadWriteMany` access). +> +> In contrast, the **S3 provider option** is much easier to configure, scales seamlessly across multiple instances out-of-the-box, and eliminates the need to manage complex storage volumes in your cluster. + ## DNS ### Domain and subdomain @@ -99,6 +129,7 @@ Similarly, ensure that your environment does not filter or block the specific MI #### Request Body Size Limits Ensure that your ingress controller, proxy, or web server is configured to allow larger HTTP request bodies. Providing a universal "one-size-fits-all" limit is difficult, as CalDAV and CardDAV payloads can be quite large. +The server has for CalDAV and CardDAV requests an internal limit of 30'000'000 bytes (~ 28.6 MB). Currently this limit is fixed and not configurable. Individual calendar events with long descriptions or attachments or contact cards containing high-resolution profile photos (vCards) can significantly increase the request size. We recommend starting with a limit of at least 10MB to 20MB and adjusting based on your specific use case. @@ -110,6 +141,8 @@ ingress: nginx.ingress.kubernetes.io/proxy-body-size: "10m" ``` +If you enable WebDAV take care to revisit the body size limit. The server removes for WebDAV requests any internal body size limit. + ## Others / Manual The Calendar Server is built with **.NET 10** and is compatible with various platforms. Although native installation is possible, the only officially supported environment is the provided **Alpine-based OCI container**. diff --git a/README.md b/README.md index 53c3acc..4332d01 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,8 @@ The **Calendare Server** is built on open standards to ensure seamless compatibi - **Availability Management**: Includes "Free/Busy" support, helping you manage your schedule and share your availability with others. - **Efficient Synchronization**: High-performance syncing that only downloads changes since your last update, saving battery life and data. - **Real-Time Push Notifications**: Support for modern Web Push standards (including encrypted notifications and VAPID keys), so your devices stay updated instantly without constant polling. - +- **Basic WebDAV Storage:** Lightweight file hosting support, allowing you to store personal files backed by either local storage or an external S3-compatible provider (preferred). +- For the full list of supported RFC's and other specification see the [implemented scope](./Doc/SCOPE.md). ## Designed for Collaboration & Scalability From 5790704d9520eb1536e26399e6e137335eea1209 Mon Sep 17 00:00:00 2001 From: Robert Bill <147130488+RobSlgm@users.noreply.github.com> Date: Fri, 17 Jul 2026 12:08:37 +0200 Subject: [PATCH 3/3] Document helm --- deploy/README.md | 24 ++++++++++++++++++++++++ deploy/README.md.gotmpl | 24 ++++++++++++++++++++++++ 2 files changed, 48 insertions(+) diff --git a/deploy/README.md b/deploy/README.md index 88725ce..2c896c1 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -105,6 +105,18 @@ Or include the VAPID keys directly in `values.yaml` with: These defaults are only used if no value is supplied by the user during account creation. The user can change these values later. +## Calendare User Constraints + +| Key | Type | Default | Description | +| ------------------------------------- | ------ | --------------- | ---------------------------------------- | +| calendare.userConstraints | object | `{}` | ... | +| calendare.userConstraints.ApplicationKeySecret | string | undefined | A secret (e.g. 'd9HbXPCSU...Aq5nRk` | + +A missing `ApplicationKeySecret` doesn't allow the use of the recommended client application secrets. + +Changing the secret invalidates all application keys the users have created. + + ## Calendar Clients Feature Configuration | Key | Type | Default | Description | @@ -153,6 +165,18 @@ Disabled features have a higher priority than enabled features. If a client is not configured in `calendare.features` the in-built settings are applied, which are taken from the `appsettings.json` file of the server. +## WebDAV file storage + +| Key | Type | Default | Description | +| ----------------------------------- | ------ | ---------------------- | ------------------------------ | +| webdav.enabled | bool | false | Enable/Disable WebDAV storage | +| webdav.provider | string | `None' | Define S3 or Filestorage | + +The `webdav.s3` supports `Bucket`, `Host`, `AccessKey`, `SecretKey`, `Region` and `PathStyle` (true|false). + +The `webdav.filestorage` supports `PathBase`. + + ## Testing and Debugging Configuration | Key | Type | Default | Description | diff --git a/deploy/README.md.gotmpl b/deploy/README.md.gotmpl index 4e04d24..fd0a55b 100644 --- a/deploy/README.md.gotmpl +++ b/deploy/README.md.gotmpl @@ -105,6 +105,18 @@ Or include the VAPID keys directly in `values.yaml` with: These defaults are only used if no value is supplied by the user during account creation. The user can change these values later. +## Calendare User Constraints + +| Key | Type | Default | Description | +| ------------------------------------- | ------ | --------------- | ---------------------------------------- | +| calendare.userConstraints | object | `{}` | ... | +| calendare.userConstraints.ApplicationKeySecret | string | undefined | A secret (e.g. 'd9HbXPCSU...Aq5nRk` | + +A missing `ApplicationKeySecret` doesn't allow the use of the recommended client application secrets. + +Changing the secret invalidates all application keys the users have created. + + ## Calendar Clients Feature Configuration | Key | Type | Default | Description | @@ -153,6 +165,18 @@ Disabled features have a higher priority than enabled features. If a client is not configured in `calendare.features` the in-built settings are applied, which are taken from the `appsettings.json` file of the server. +## WebDAV file storage + +| Key | Type | Default | Description | +| ----------------------------------- | ------ | ---------------------- | ------------------------------ | +| webdav.enabled | bool | false | Enable/Disable WebDAV storage | +| webdav.provider | string | `None' | Define S3 or Filestorage | + +The `webdav.s3` supports `Bucket`, `Host`, `AccessKey`, `SecretKey`, `Region` and `PathStyle` (true|false). + +The `webdav.filestorage` supports `PathBase`. + + ## Testing and Debugging Configuration | Key | Type | Default | Description |