Django Production Deployment on Sealos
Launch Django on Sealos with an immutable image, same-image migration, two hardened Gunicorn replicas, WhiteNoise static assets, HTTPS, operations guidance, and A-B-A-B recovery.
This guide completes the continuous Django Task Board series with a production
release contract. The protected
stage-3-production
tag resolves to commit
8e372f93e1a7bb72880be5198430a065d38d65f5. It pins Python 3.12, Django
5.2.16, psycopg 3.3.4, Gunicorn 26.0.0, and WhiteNoise 6.12.0.
Start with the PostgreSQL guide when you
need to establish tasks.0001_initial, schema-aware readiness, CSRF writes,
restart persistence, and native admin readback. This stage keeps that data
contract and adds immutable releases, hardened replicas, static assets,
operational checks, and rehearsed recovery.
Evidence boundary
The production conclusions come from three explicit authorities:
| Authority | What it establishes |
|---|---|
| Protected Stage 3 source | Dependency versions, manifests, same-image migration, two replicas, Gunicorn, WhiteNoise, security context, and Host contracts |
| Fresh Phase 27 current practice | Baseline digest migration, 2/2 Ready, public HTTPS /health, Task Board continuity, and WhiteNoise CSS behavior |
| Checksum-valid Phase 26 evidence | Final-digest migration, final admin readback, final Gunicorn identity, final release logs, and the complete A-B-A-B history |
The fresh current observation used this baseline image:
The sealed final-state records use this Stage 3 image:
Keep these roles separate when reviewing a new deployment. Current live checks describe the environment you are operating. Protected source and sealed records define the release contract and its previously accepted final-state proof.
Production launch model
Use this release order:
Migration completion is the readiness boundary. The migration Job and
application Deployment consume the same image digest, PostgreSQL Secret, and
run identity. The public Sealos host terminates TLS while the upstream adapter
preserves the protected Django localhost Host contract.
Production scorecard
| Control | Required result |
|---|---|
| Source identity | Protected stage-3-production at the recorded 40-character commit |
| Execution identity | Full immutable image digest shared by Job and Deployment |
| Database gate | Migration Job Complete=True at tasks.0001_initial |
| Availability | 2/2 Ready before public acceptance |
| Process identity | UID/GID 10001, one Gunicorn master and one sync worker per Pod |
| Public surface | HTTPS health 200, Task Board, native admin, and static CSS |
| Recovery | Rollout undo plus explicit final-manifest recovery |
Step 1: Clone and validate the protected Stage 3 source
Open the installed Sealos plugin with $sealos, the Codex App plugin picker,
or /sealos, then clone the immutable source tag:
Reproduce the exact Python dependency graph and runtime export:
Inspect the production contracts before rendering them:
Require the exact Stage 3 commit shown above. The protected application
contract contains two replicas, port 8000, the localhost readiness Host,
WhiteNoise static collection, and the hardened Pod settings described below.
Step 2: Resolve immutable production state
The image publisher exposes a lookup tag for every complete source SHA. Resolve that tag once, then use the returned digest as the execution identity:
Render deploy/migration-job.yaml and deploy/application.yaml into a private
temporary directory. Replace every tracked __TOKEN__, keep each file at mode
0600, and supply one run-owned application name, migration Job name,
PostgreSQL Secret name, image reference, and source release. The protected
README includes the exact token-safe Python renderer.
Validate both rendered documents against the active cluster API:
The protected source identity and checksum-valid final image record join the Stage 3 commit to this digest:
Protected Django Stage 3 commit resolved to an immutable digest with redacted PostgreSQL state and one shared same-image migration contractStep 3: Run the same-image migration before readiness
Apply the migration Job first:
Read the Job log and require tasks.0001_initial to be current. The fresh
Phase 27 current check proves this sequence with the baseline image and a
successful Job. Checksum-valid Phase 26 evidence independently proves that the
final Job used the exact final application digest and completed before
readiness at the same migration.
Step 4: Roll out two hardened Gunicorn replicas
Apply the Deployment after migration completion:
Require 2/2 Ready. Protected Stage 3 gives each Pod this runtime contract:
- UID/GID
10001 - One Gunicorn
26.0.0master and one sync WSGI worker - Bind address
0.0.0.0:8000 - Read-only root filesystem
- Every Linux capability dropped
- Privilege escalation disabled
RuntimeDefaultseccomp- Service-account token mounting disabled
- A memory-backed
/tmplimited to64Mi
The fresh Phase 27 observation proves 2/2 Ready on the baseline digest.
Checksum-valid Phase 26 evidence proves the final two-Pod identity: UID/GID
10001, one Gunicorn master and one worker in each Pod, and zero restarts.
Django production evidence showing tasks.0001_initial before fresh baseline 2 of 2 Ready and sealed final UID GID 10001 Gunicorn identitiesStep 5: Verify HTTPS, the Task Board, WhiteNoise, admin, and logs
The public edge keeps the generated Sealos hostname in the browser and sends
Host: localhost upstream. Accept the public application through HTTPS:
The fresh Phase 27 baseline returned public HTTPS health 200 with
{"status":"ok"} and rendered the retained Task Board. Checksum-valid Phase
26 final-state HTTP records supply the authenticated admin authority: the
native admin login returned 200, and its Task changelist and change form read
Task 1.
Extract the manifest-named stylesheet from the board and inspect it through the same public host:
The fresh current check resolved
/static/tasks/styles.852e61e8064c.css and received HTTP 200,
Content-Type: text/css, and
Cache-Control: max-age=315360000, public, immutable.
Correlate final release identity through credential-free service logs:
Checksum-valid Phase 26 logs record one event=service_start match from each
of the two final Pods. This log statement uses sealed final-state authority;
the fresh Phase 27 current record supplies the baseline HTTPS, board, and
WhiteNoise results above.
Fresh public Django HTTPS and WhiteNoise styles 852e61e8064c CSS proof beside checksum-sealed two-Pod service_start logsMonitoring and incident signals
Monitor the same surfaces used for release acceptance:
- Public HTTPS
/healthstatus and latency - Deployment Ready and Available replica counts
- Pod restart and replacement counts
- Service endpoint inventory
- Migration Job completion and
tasks.0001_initial - WhiteNoise CSS status, media type, and immutable cache policy
event=service_startidentity for each newly started Pod- A CSRF Task create/read smoke check for the PostgreSQL data path
- PostgreSQL availability, storage, backup age, and resource saturation
Assign every alert to an owner and record the first diagnostic commands in the runbook. The health endpoint is a lightweight availability signal. The Task smoke check exercises the full application, CSRF, ORM, and PostgreSQL path.
Backup and migration safety
Before a schema-changing release:
- Create or verify a PostgreSQL recovery point
- Record the current source SHA, image digest, and migration state
- Review compatibility with the retained application digest
- Rehearse restore or forward repair in a separate environment
- Keep the baseline and final digests available through the recovery window
- Assign application rollback and database recovery ownership
Image rollback restores application code. Database recovery follows the schema and data decision recorded for that release.
UPDATE workflow
Use UPDATE after .sealos/state.json and current resource truth identify
the same live application. Resolve the new complete-source-SHA tag, run its
same-image migration, apply the retained application manifest, wait for 2/2 Ready, and repeat the public and operational checks. Use DEPLOY for a new
application identity and record accepted state only after runtime verification.
Keep this release record:
Step 6: Roll back and explicitly recover
Checksum-valid Phase 26 evidence owns the complete recovery history. It exercised four states against one PostgreSQL Task:
| Sequence | State | Controller revision | Task witness |
|---|---|---|---|
| 1 | baseline | 1 | Create Task 1 through the CSRF form |
| 2 | final | 2 | Board and authenticated admin read Task 1 |
| 3 | baseline rollback | 3 | Board and authenticated admin read Task 1 |
| 4 | final recovered | 4 | Board and authenticated admin read Task 1 |
Run the immediate application rollback:
Recover by explicitly reapplying the retained final manifest:
The sealed A-B-A-B record covers Deployment revisions 1, 2, 3, and 4.
It passed rollout undo, explicit final recovery, and Task 1 continuity across
all four states.
Checksum-sealed Django A-B-A-B revisions 1 2 3 4 preserving Task 1 through rollout undo and explicit final recoveryProduction runbook
Record this sequence for every release:
- Confirm protected Stage 3 and reproduce the exact lock.
- Resolve the complete source-SHA image tag to an immutable digest.
- Verify architecture plus source and revision labels.
- Create a PostgreSQL recovery point for a schema-changing release.
- Render Job and Deployment with the same digest and Secret reference.
- Run the migration Job and verify
Complete=Trueattasks.0001_initial. - Roll out two replicas and verify image IDs, UID/GID, Gunicorn, and restarts.
- Run public health, Task Board, admin, WhiteNoise, endpoint, and log checks.
- Observe stable runtime state and write the accepted release record.
- Keep rollout undo and explicit final-manifest recovery ready.
Failure guide
Migration completes and the app remains unready
Confirm the Job and Deployment read the same Secret-backed DATABASE_URL and
use the same image digest. Inspect showmigrations tasks from that image and
require [X] 0001_initial.
Public health succeeds and the browser receives a Host or CSRF error
Inspect the edge adapter. Preserve the generated public hostname for the
browser and send Host: localhost upstream together with the protected Origin
and Referer policy.
Static CSS returns HTML or a generic media type
Read the stylesheet path from rendered board HTML. Confirm WhiteNoise loaded the collected manifest and that the request reaches the Django application with the expected upstream Host.
One Pod has a different process or image identity
Compare the Deployment digest, both Pod image IDs, UID/GID, and process lists. Resume acceptance after both Pods match the intended release tuple.
Rollback restores code and Task readback fails
Check PostgreSQL reachability, migration compatibility, and the retained Task ID. Follow the database recovery decision stored with the release.
Recorded Sealos state points at stale resources
Reconcile .sealos/state.json with current workloads, Services, endpoints,
Ingress, and logs. Select UPDATE after identities agree or DEPLOY for a fresh
application identity.
Final checklist
- The checkout points at protected
stage-3-production - The complete source SHA resolves to one immutable digest
- Image architecture and source/revision labels pass
- Migration and application manifests use the same digest and Secret source
- The migration Job reaches
Complete=Trueattasks.0001_initial - The Deployment reaches
2/2 Ready - Both Pods run as UID/GID 10001 with one Gunicorn master and one worker
- Both image IDs match the intended digest and restart counts remain zero
- The public Host edge and HTTPS
/healthpass - Task Board, native admin, and Task continuity pass
- WhiteNoise CSS returns
200,text/css, and immutable caching - Both final Pods emit the credential-free
event=service_startmarker - Monitoring, backup, restore, and incident ownership are recorded
- UPDATE or DEPLOY follows live resource identity
- Rollout undo and explicit final recovery preserve Task
1 - The production runbook is stored with the release
The Django Framework Tutorial Series now follows one continuous Task Board from local SQLite through PostgreSQL and a rehearsed production release.
FAQ
Previous
Deploy Django with PostgreSQL on Sealos
Keep building
Continue this Sealos path
Unify Your Entire Workflow.
Code in a ready-to-use cloud environment, deploy with a click. Sealos combines the entire dev-to-prod lifecycle into one seamless platform. No more context switching.
Explore with AI
Get AI insights on this article