Skip to content

Commit adb7045

Browse files
schaurianclaude
andcommitted
feat: support S3 SSE-C (customer-provided encryption keys)
Surface the new `sseCustomerKey` field on `s3Credentials` through the ObjectStore CRD so users can enable Server-Side Encryption with Customer-provided keys (SSE-C). This is required by S3-compatible providers that only support SSE-C for encryption at rest, such as Hetzner Object Storage. The field flows through the embedded BarmanObjectStoreConfiguration from the barman-cloud library, so this change is limited to bumping the dependency, regenerating the CRD and the consolidated manifest, and documenting usage in the object stores guide. Depends on cloudnative-pg/barman-cloud#284 (temporarily pinned via a replace directive until that change is released). Closes #646 Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Signed-off-by: Florian Schauer <florian@schauer.to>
1 parent 9967e2c commit adb7045

5 files changed

Lines changed: 116 additions & 2 deletions

File tree

config/crd/bases/barmancloud.cnpg.io_objectstores.yaml

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -315,6 +315,30 @@ spec:
315315
- key
316316
- name
317317
type: object
318+
sseCustomerKey:
319+
description: |-
320+
The reference to the secret containing the key for
321+
Server-Side Encryption with Customer-provided keys (SSE-C).
322+
When set, every object barman-cloud uploads to and downloads from
323+
S3 is encrypted with this key using the AWS SSE-C protocol
324+
(the `--sse-customer-key` barman-cloud option).
325+
The referenced value must be a base64-encoded 256-bit (32-byte)
326+
AES key. This is orthogonal to the bucket-managed `encryption`
327+
field (SSE-S3/SSE-KMS) and is meant for S3-compatible providers
328+
that only support customer-provided keys (e.g. Hetzner Object
329+
Storage). It can be combined with any authentication method,
330+
including inheritFromIAMRole.
331+
properties:
332+
key:
333+
description: The key to select
334+
type: string
335+
name:
336+
description: Name of the referent.
337+
type: string
338+
required:
339+
- key
340+
- name
341+
type: object
318342
type: object
319343
serverName:
320344
description: |-

go.mod

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -137,3 +137,5 @@ require (
137137
sigs.k8s.io/structured-merge-diff/v6 v6.4.0 // indirect
138138
sigs.k8s.io/yaml v1.6.0 // indirect
139139
)
140+
141+
replace github.com/cloudnative-pg/barman-cloud => github.com/schaurian/barman-cloud v0.5.2-0.20260809132550-a30084171954

go.sum

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,6 @@ github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UF
2020
github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
2121
github.com/cloudnative-pg/api v1.30.0 h1:L8hnvV/tPEQA1xYEi41FUBFA7FUNVGju8+SlgFlDDjI=
2222
github.com/cloudnative-pg/api v1.30.0/go.mod h1:XrKBbOWObL33si0FNuwX4uHNf5JShiZyOUqd6LxbJQo=
23-
github.com/cloudnative-pg/barman-cloud v0.5.2-0.20260720143032-950b0f57e122 h1:NuOztBdp+bUr/xYtaAw8o/x880hvWDRhJGl+R1YsZNw=
24-
github.com/cloudnative-pg/barman-cloud v0.5.2-0.20260720143032-950b0f57e122/go.mod h1:ZQLkdpk44FW5/BGWzABTOEcV9qPbwC+rbdscg2I8mBI=
2523
github.com/cloudnative-pg/cloudnative-pg v1.30.0 h1:fnhVq44xXx97MNiuvJsPrX1vSjYbgdyBK5MSGfdHdp0=
2624
github.com/cloudnative-pg/cloudnative-pg v1.30.0/go.mod h1:QkolwBOWZ+GvAiJt6KpDSymwkpf0K19/p4Q6MQlTM8U=
2725
github.com/cloudnative-pg/cnpg-i v0.6.0 h1:LA//DLkFOLIjU0ASOpFkydZhGir9IAIDfgSsTTX9IpU=
@@ -187,6 +185,8 @@ github.com/rogpeppe/go-internal v1.14.1/go.mod h1:MaRKkUm5W0goXpeCfT7UZI6fk/L7L7
187185
github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
188186
github.com/sagikazarmark/locafero v0.11.0 h1:1iurJgmM9G3PA/I+wWYIOw/5SyBtxapeHDcg+AAIFXc=
189187
github.com/sagikazarmark/locafero v0.11.0/go.mod h1:nVIGvgyzw595SUSUE6tvCp3YYTeHs15MvlmU87WwIik=
188+
github.com/schaurian/barman-cloud v0.5.2-0.20260809132550-a30084171954 h1:Y+01J7nOz6jQdrkEEpS8Mq74aECXAdr+DTeY2Lo3DmQ=
189+
github.com/schaurian/barman-cloud v0.5.2-0.20260809132550-a30084171954/go.mod h1:ZQLkdpk44FW5/BGWzABTOEcV9qPbwC+rbdscg2I8mBI=
190190
github.com/sergi/go-diff v1.4.0 h1:n/SP9D5ad1fORl+llWyN+D6qoUETXNZARKjyY2/KVCw=
191191
github.com/sergi/go-diff v1.4.0/go.mod h1:A0bzQcvG0E7Rwjx0REVgAGH58e96+X0MeOfepqsbeW4=
192192
github.com/snorwin/jsonpatch v1.5.0 h1:0m56YSt9cHiJOn8U+OcqdPGcDQZmhPM/zsG7Dv5QQP0=

manifest.yaml

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -314,6 +314,30 @@ spec:
314314
- key
315315
- name
316316
type: object
317+
sseCustomerKey:
318+
description: |-
319+
The reference to the secret containing the key for
320+
Server-Side Encryption with Customer-provided keys (SSE-C).
321+
When set, every object barman-cloud uploads to and downloads from
322+
S3 is encrypted with this key using the AWS SSE-C protocol
323+
(the `--sse-customer-key` barman-cloud option).
324+
The referenced value must be a base64-encoded 256-bit (32-byte)
325+
AES key. This is orthogonal to the bucket-managed `encryption`
326+
field (SSE-S3/SSE-KMS) and is meant for S3-compatible providers
327+
that only support customer-provided keys (e.g. Hetzner Object
328+
Storage). It can be combined with any authentication method,
329+
including inheritFromIAMRole.
330+
properties:
331+
key:
332+
description: The key to select
333+
type: string
334+
name:
335+
description: Name of the referent.
336+
type: string
337+
required:
338+
- key
339+
- name
340+
type: object
317341
type: object
318342
serverName:
319343
description: |-

web/docs/object_stores.md

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,70 @@ spec:
194194
[...]
195195
```
196196

197+
### Server-Side Encryption with Customer Keys (SSE-C)
198+
199+
Some S3-compatible providers — most notably **Hetzner Object Storage** — do
200+
not offer bucket-managed server-side encryption (SSE-S3 / SSE-KMS) and instead
201+
only support **Server-Side Encryption with Customer-provided keys (SSE-C)**.
202+
With SSE-C the encryption key never leaves your control: it is supplied with
203+
every request, and the provider uses it to encrypt and decrypt objects without
204+
storing it.
205+
206+
To enable SSE-C, set the `sseCustomerKey` field in the `s3Credentials` block to
207+
a secret reference holding a **base64-encoded 256-bit (32-byte) AES key**.
208+
209+
Generate the key and store it in a Kubernetes secret:
210+
211+
```sh
212+
# Generate a random 256-bit key, base64-encoded
213+
openssl rand 32 | base64 > sse-c.key
214+
215+
kubectl create secret generic aws-sse-c \
216+
--from-file=key=sse-c.key
217+
```
218+
219+
:::warning
220+
Keep this key safe and backed up **outside** the object store. If you lose
221+
it, your backups and WAL files become permanently unrecoverable — the
222+
provider cannot decrypt them for you.
223+
:::
224+
225+
Reference it in your `ObjectStore` definition:
226+
227+
```yaml
228+
apiVersion: barmancloud.cnpg.io/v1
229+
kind: ObjectStore
230+
metadata:
231+
name: hetzner-store
232+
spec:
233+
configuration:
234+
destinationPath: "s3://BUCKET_NAME/path/to/folder"
235+
endpointURL: "https://fsn1.your-objectstorage.com"
236+
s3Credentials:
237+
accessKeyId:
238+
name: aws-creds
239+
key: ACCESS_KEY_ID
240+
secretAccessKey:
241+
name: aws-creds
242+
key: ACCESS_SECRET_KEY
243+
sseCustomerKey:
244+
name: aws-sse-c
245+
key: key
246+
[...]
247+
```
248+
249+
The same key is applied to **every** operation — base backups, WAL archiving,
250+
WAL restore, and data restore — so it must remain unchanged and available for
251+
the whole lifetime of the backups it protects. `sseCustomerKey` is independent
252+
of the bucket-managed `encryption` field (SSE-S3 / SSE-KMS) and can be combined
253+
with any authentication method, including `inheritFromIAMRole`.
254+
255+
:::note
256+
SSE-C support requires a sidecar image whose `barman-cloud` build includes
257+
the `--sse-customer-key` option
258+
(see [barman#973](https://github.com/EnterpriseDB/barman/issues/973)).
259+
:::
260+
197261
### Using Object Storage with a Private CA
198262

199263
For object storage services (e.g., MinIO) that use HTTPS with certificates

0 commit comments

Comments
 (0)