The per-member key seed currently runs from /app/data/sync-keys.js — a file on the persistent volume that gets there by hand-push. This branch moves it into the image.
Dockerfile: COPY sync-keys.js /app/code/sync-keys.js, and rule 3 in the header now names the single exception to "image = static assets only".
CloudronManifest.json: the librechat_key_sync scheduler command repoints to /app/code/sync-keys.js.
README.md: the ordering, and the table row moves from the volume layer to the image layer.
Why
The seed is the one member-facing scheduled job in this app: a new member's first login has no key until it runs. On the volume it can vanish with a volume restore, and its repo copy can drift from the live copy with nothing detecting it. In the image it is versioned, immutable and matched to the repo by construction — and sync-keys.js now prints its own md5 prefix on every run, so even that is auditable from the app log.
Ordering matters — build before you deploy
The repointed command ships in the same cloudron update as the new image. Deploying the manifest without the rebuilt image leaves the seed pointing at a file that does not exist, failing every 10 minutes while the app looks healthy.
./release.sh build # on a host with docker + registry login
./release.sh pin <tag> # refuses to deploy until the manifest carries the new tag
./release.sh deploy # runs the verify block automatically
./release.sh verify check 6 exists for exactly this: it fails if the scheduler's command path is not present in the running image.
After the deploy is verified and you are past the rollback window, delete the volume copy (rm /app/data/sync-keys.js) — the previous image tag still runs it, so keep it while a rollback is plausible.
Not deployed. Nothing live changes until someone with docker builds and deploys it.
## What this changes
The per-member key seed currently runs from `/app/data/sync-keys.js` — a file on the persistent volume that gets there by hand-push. This branch moves it into the image.
- `Dockerfile`: `COPY sync-keys.js /app/code/sync-keys.js`, and rule 3 in the header now names the single exception to "image = static assets only".
- `CloudronManifest.json`: the `librechat_key_sync` scheduler command repoints to `/app/code/sync-keys.js`.
- `README.md`: the ordering, and the table row moves from the volume layer to the image layer.
## Why
The seed is the one member-facing scheduled job in this app: a new member's first login has no key until it runs. On the volume it can vanish with a volume restore, and its repo copy can drift from the live copy with nothing detecting it. In the image it is versioned, immutable and matched to the repo by construction — and `sync-keys.js` now prints its own md5 prefix on every run, so even that is auditable from the app log.
## Ordering matters — build before you deploy
The repointed command ships in the same `cloudron update` as the new image. Deploying the manifest without the rebuilt image leaves the seed pointing at a file that does not exist, failing every 10 minutes while the app looks healthy.
```bash
./release.sh build # on a host with docker + registry login
./release.sh pin <tag> # refuses to deploy until the manifest carries the new tag
./release.sh deploy # runs the verify block automatically
```
`./release.sh verify` check 6 exists for exactly this: it fails if the scheduler's command path is not present in the running image.
After the deploy is verified and you are past the rollback window, delete the volume copy (`rm /app/data/sync-keys.js`) — the previous image tag still runs it, so keep it while a rollback is plausible.
Not deployed. Nothing live changes until someone with docker builds and deploys it.
Ready to build, not yet deployed — deploying the repointed scheduler command
without the new image would break the seed on schedule, which is why this sits on
a branch with the ordering written down.
- Dockerfile: COPY sync-keys.js /app/code/sync-keys.js; rule 3 in the header now
states the one exception (operational scripts that must not depend on a volume).
- CloudronManifest.json: scheduler command repointed to /app/code/sync-keys.js.
- README: ordering (build -> deploy -> verify -> delete the volume copy), and the
table row moved from the volume layer to the image layer.
After deploy: delete /app/data/sync-keys.js, but keep it until you are past the
rollback window — the previous image tag still runs the volume copy.
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
What this changes
The per-member key seed currently runs from
/app/data/sync-keys.js— a file on the persistent volume that gets there by hand-push. This branch moves it into the image.Dockerfile:COPY sync-keys.js /app/code/sync-keys.js, and rule 3 in the header now names the single exception to "image = static assets only".CloudronManifest.json: thelibrechat_key_syncscheduler command repoints to/app/code/sync-keys.js.README.md: the ordering, and the table row moves from the volume layer to the image layer.Why
The seed is the one member-facing scheduled job in this app: a new member's first login has no key until it runs. On the volume it can vanish with a volume restore, and its repo copy can drift from the live copy with nothing detecting it. In the image it is versioned, immutable and matched to the repo by construction — and
sync-keys.jsnow prints its own md5 prefix on every run, so even that is auditable from the app log.Ordering matters — build before you deploy
The repointed command ships in the same
cloudron updateas the new image. Deploying the manifest without the rebuilt image leaves the seed pointing at a file that does not exist, failing every 10 minutes while the app looks healthy../release.sh verifycheck 6 exists for exactly this: it fails if the scheduler's command path is not present in the running image.After the deploy is verified and you are past the rollback window, delete the volume copy (
rm /app/data/sync-keys.js) — the previous image tag still runs it, so keep it while a rollback is plausible.Not deployed. Nothing live changes until someone with docker builds and deploys it.