Files
adcloud-server/src/adcloud_server/container_entrypoint.py
T
codex-bot 789ab64013
Docker test deployment / test-build-deploy (push) Successful in 4m5s
Add Docker test deployment on Gitea Actions
2026-09-16 01:27:57 +08:00

70 lines
2.1 KiB
Python

"""Persist per-deployment secrets in a Docker volume before starting uvicorn."""
import fcntl
import os
import re
import secrets
import sys
import tempfile
from pathlib import Path
from dotenv import dotenv_values
SECRET_NAMES = ("IDENTITY_SECRET", "SERVICE_TOKEN")
def bootstrap(path: Path):
path.parent.mkdir(parents=True, exist_ok=True)
lock = path.with_suffix(".lock")
descriptor = os.open(lock, os.O_WRONLY | os.O_CREAT, 0o600)
with os.fdopen(descriptor, "w") as handle:
fcntl.flock(handle, fcntl.LOCK_EX)
existing = dotenv_values(path) if path.exists() else {}
selected = {
name: os.environ.get(name)
or existing.get(name)
or secrets.token_urlsafe(48)
for name in SECRET_NAMES
}
if any(
not re.fullmatch(r"[A-Za-z0-9_-]{32,}", value)
for value in selected.values()
):
raise ValueError("Container secrets must have 32+ URL-safe characters")
if any(existing.get(name) != value for name, value in selected.items()):
temporary = None
try:
with tempfile.NamedTemporaryFile(
mode="w", dir=path.parent, prefix=".identity-", delete=False
) as output:
temporary = Path(output.name)
os.chmod(temporary, 0o600)
for name, value in selected.items():
output.write(name + "=" + value + "\n")
output.flush()
os.fsync(output.fileno())
os.replace(temporary, path)
finally:
if temporary is not None:
temporary.unlink(missing_ok=True)
os.chmod(path, 0o600)
return selected
def main():
path = Path(os.getenv("IDENTITY_BOOTSTRAP_FILE", "/config/identity.env"))
os.environ.update(bootstrap(path))
command = sys.argv[1:] or [
"uvicorn",
"adcloud_server.main:app",
"--host",
"0.0.0.0",
"--port",
"8000",
]
os.execvp(command[0], command)
if __name__ == "__main__":
main()