Skip to content

install.sh 26.10.0: SeaweedFS KEK migration fails with PermissionError on /data/.mini_kek_passphrase (sentry image is non-root now) #4577

Open

Description

@futureweb

Self-Hosted Version

26.10.0 (upgrading from 26.7.0, which we reached via the 26.7.0 hard stop from 26.6.0)

CPU Architecture

x86_64

Docker Version

29.9.2

Docker Compose Version

5.6.1

Machine Specification

  • My system meets the minimum system requirements of Sentry

Installation Type

upgrading from 26.7.0, which we reached via the 26.7.0 hard stop from 26.6.0

Steps to Reproduce

  1. Run a version without the KEK migration (here 26.7.0, which already runs weed mini and created /data/.mini_kek_passphrase and /data/.mini_sse_kek), with a legacy filer (/data/filerldb2 present) whose stored KEK is wrapped (not plain hex).
  2. git checkout 26.10.0 && ./install.sh

Expected Result

Migrating the SeaweedFS encryption key ... recovers the legacy KEK and install continues.

Actual Result

▶ Migrating the SeaweedFS encryption key ...
...
  File "/recover_seaweedfs_kek.py", line 67, in main
    passphrase = args.passphrase_file.read_bytes() if args.passphrase_file.is_file() else None
...
PermissionError: [Errno 13] Permission denied: '/data/.mini_kek_passphrase'
Error in install/migrate-seaweedfs-kek.sh:84.

In the volume both files are owned by root with mode 0600 (written by the seaweedfs container, which runs as root):

-rw-------    1 root     root            64 ... .mini_kek_passphrase
-rw-------    1 root     root            64 ... .mini_sse_kek
drwxr-xr-x   10 seaweed  seaweed       4096 ... filerldb2

The recovery step runs recover_seaweedfs_kek.py in sentry-self-hosted-local via --volumes-from. Since 26.10.0 that image runs as the non-root sentry user (uid 999), so it can't read the root-only passphrase file. When the migration was introduced (#4461, 26.8.0) the image still ran as root, so this only surfaces when upgrading from before 26.8.0 straight to 26.10.0 (we went 26.7.0 → 26.10.0), as long as the filer KEK is wrapped. With a plain-hex KEK the Python path is skipped entirely.

Nothing gets changed before the failure: the migration marker isn't written, and Postgres hasn't been touched yet at this point. So a re-run after the fix is safe.

Fix

Run the one-shot recovery container as root. It only reads the volume (--volumes-from ...:ro) and prints the key:

         printf '%s' "$stored_kek" | $CONTAINER_ENGINE run --rm -i \
+          --user 0 \
           --entrypoint python3 \
           -v "$(pwd)/scripts/recover_seaweedfs_kek.py:/recover_seaweedfs_kek.py:ro" \
           --volumes-from "${migration_container}:ro" \
           sentry-self-hosted-local \
           /recover_seaweedfs_kek.py /data/.mini_kek_passphrase

With this change applied locally, a second ./install.sh run went through. (Podman rootless might need --userns/--user handling of its own; not tested.)

Event ID

No response

Activity

  1. moved this to Waiting for: Product Owner in GitHub Issues with 👀 3on Oct 21, 2026
  2. teddy931130 commented on Oct 27, 2026

    @teddy931130

    Thank you so much! You're a lifesaver! Sentry tech writers should definitely add 26.8.0 as a hard stop in their docs... We upgraded from 26.7.2 -> 26.10.0 and hit the exact same thing.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions