feat: complete cluster self-sufficiency hardening
All checks were successful
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 1s
Build and Publish Multi-Context Image / build-and-push (push) Successful in 45s

Assistant: codex
Assistant-Model: gpt-5.6-sol
Assistant-Session: 01a06d83-1cbc-71f2-b0dc-e0f48cedae43
This commit is contained in:
tegwick 2026-09-04 22:23:42 +02:00
parent 87047faa8e
commit 0b44cf12f5
14 changed files with 232 additions and 40 deletions

View file

@ -21,7 +21,7 @@ boundaries used for the actual cluster rollout.
The current image is pinned to:
```text
forgejo.coulomb.social/coulomb/state-hub:f2e042a
forgejo.coulomb.social/coulomb/state-hub:main-cdff3b7
```
railiance01 has already pulled this tag with `crictl`, and the image serves
@ -87,4 +87,4 @@ DATABASE_URL=postgresql+asyncpg://state_hub:<url-encoded-password>@state-hub-db-
Optional runtime settings such as `CORS_ORIGINS` can live in the chart
ConfigMap. The default chart keeps public ingress disabled; access should use
the existing private tunnel/ops-bridge path until a separate exposure decision
is recorded.
is recorded.

View file

@ -25,8 +25,9 @@ spec:
{{- with .Values.imagePullSecrets }}
imagePullSecrets: {{- toYaml . | nindent 8 }}
{{- end }}
{{- if or .Values.sweep.enabled .Values.classificationAllowed.enabled .Values.forgeRead.enabled }}
volumes:
- name: runtime-tmp
emptyDir: {}
{{- if .Values.sweep.enabled }}
- name: sweep-repos
hostPath:
@ -57,7 +58,6 @@ spec:
{{- end }}
expirationSeconds: {{ .Values.forgeRead.openbao.expirationSeconds }}
{{- end }}
{{- end }}
containers:
- name: state-hub
image: {{ include "statehub.image" . | quote }}
@ -76,8 +76,9 @@ spec:
- -c
- git config --global --add safe.directory '*'
{{- end }}
{{- if or .Values.sweep.enabled .Values.classificationAllowed.enabled .Values.forgeRead.enabled }}
volumeMounts:
- name: runtime-tmp
mountPath: /tmp
{{- if .Values.sweep.enabled }}
- name: sweep-repos
mountPath: {{ .Values.sweep.hostPath | quote }}
@ -96,6 +97,8 @@ spec:
readOnly: true
{{- end }}
env:
- name: HOME
value: /tmp
{{- if .Values.sweep.enabled }}
- name: STATE_HUB_SWEEP_HOSTNAME
value: {{ .Values.sweep.hostname | quote }}
@ -122,7 +125,6 @@ spec:
- name: FORGE_READ_SECRET_KEY
value: {{ .Values.forgeRead.openbao.secretKey | quote }}
{{- end }}
{{- end }}
envFrom:
{{- if .Values.config.enabled }}
- configMapRef:

View file

@ -21,6 +21,9 @@ spec:
{{- with .Values.imagePullSecrets }}
imagePullSecrets: {{- toYaml . | nindent 8 }}
{{- end }}
volumes:
- name: runtime-tmp
emptyDir: {}
containers:
- name: state-hub-mcp
image: {{ include "statehub.image" . | quote }}
@ -30,11 +33,16 @@ spec:
# Use -m so the WORKDIR (/app) lands on sys.path — invoking the file
# directly would put /app/mcp_server there and break its own imports.
command: ["/app/.venv/bin/python", "-m", "mcp_server.server"]
volumeMounts:
- name: runtime-tmp
mountPath: /tmp
ports:
- name: sse
containerPort: {{ .Values.mcp.service.targetPort }}
protocol: TCP
env:
- name: HOME
value: /tmp
- name: MCP_TRANSPORT
value: {{ .Values.mcp.transport | quote }}
- name: MCP_PORT

View file

@ -21,14 +21,25 @@ spec:
labels: {{- include "statehub.labels" . | nindent 8 }}
spec:
restartPolicy: Never
securityContext: {{- toYaml .Values.podSecurityContext | nindent 8 }}
{{- with .Values.imagePullSecrets }}
imagePullSecrets: {{- toYaml . | nindent 8 }}
{{- end }}
volumes:
- name: runtime-tmp
emptyDir: {}
containers:
- name: migrate
image: {{ include "statehub.image" . | quote }}
imagePullPolicy: {{ .Values.image.pullPolicy }}
securityContext: {{- toYaml .Values.securityContext | nindent 12 }}
command: ["/app/.venv/bin/python", "-m", "alembic", "upgrade", "head"]
volumeMounts:
- name: runtime-tmp
mountPath: /tmp
env:
- name: HOME
value: /tmp
envFrom:
{{- if .Values.config.enabled }}
- configMapRef:

View file

@ -162,14 +162,29 @@ probes:
timeoutSeconds: 5
failureThreshold: 3
podSecurityContext: {}
securityContext: {}
# STATE-WP-0081-T04. The image and all writable runtime state are independent
# of root. Keep these defaults restrictive so API, MCP, and migration pods have
# the same security posture in every installation.
podSecurityContext:
runAsNonRoot: true
runAsUser: 10001
runAsGroup: 10001
fsGroup: 10001
seccompProfile:
type: RuntimeDefault
securityContext:
allowPrivilegeEscalation: false
capabilities:
drop:
- ALL
readOnlyRootFilesystem: true
nodeSelector: {}
tolerations: []
affinity: {}
# Consistency sweep: mount railiance01 clone tree and match host_paths hostname.
# Legacy consistency sweep settings. Kept only for rollback compatibility;
# production uses Forge-derived reconciliation and must leave this disabled.
sweep:
enabled: false
hostname: ""

View file

@ -6,7 +6,7 @@ namespace:
image:
repository: forgejo.coulomb.social/coulomb/state-hub
tag: "main-5dd04dc"
tag: "main-cdff3b7"
ingress:
enabled: false