schema_version = "railiance.app.v1" [app] id = "qonto-assistant" name = "Qonto Governed Assistant" repo = "qonto-assistant" owner = "binky-tenant-owner" criticality = "critical" description = "Sole holder of the Binky Qonto bank API credential; governed read-only REST+MCP finance surface for agent harnesses, reachable via a facade (QONTO-WP-0004-T05, not yet built)." [source] revision = "git:main" artifact = "image" digest_policy = "required" [rollback] strategy = "manual-runbook" command = "kubectl -n qonto-assistant scale deployment/qonto-assistant --replicas=0" verification = "Facade reports the backend unreachable; no traffic proxied until re-woken against a known-good image digest." [[platform.dependencies]] name = "openbao" kind = "other" required = true stage = "stage2" evidence = "ExternalSecret qonto-assistant-qonto-api syncs API_KEY/API_USER without error (depends on CCR-2026-0009 approval)." [[secrets.references]] name = "qonto-api-credential" route = "openbao-workload-kv-read" target = "ExternalSecret/qonto-assistant-qonto-api" stage = "stage2" required = true [[observability.health_endpoints]] name = "local-health" url = "http://127.0.0.1:8080/v1/health" stage = "stage1" expected_status = 200 [[observability.health_endpoints]] name = "cluster-health" url = "http://qonto-assistant.qonto-assistant.svc.cluster.local:8080/v1/health" stage = "stage2" expected_status = 200 [stages.stage1] enabled = true namespace = "local" release = "qonto-assistant-local" commands = ["make test", "kubectl kustomize deploy/k8s/qonto-assistant"] checks = ["unit-tests", "kustomize-render", "local-health"] evidence = ["pytest output", "kustomize render success", "local health 200"] requires_approval = false [stages.stage2] enabled = true namespace = "qonto-assistant" release = "qonto-assistant-canary" commands = ["kubectl apply -k deploy/k8s/qonto-assistant --dry-run=server", "kubectl -n qonto-assistant scale deployment/qonto-assistant --replicas=1"] checks = ["server-dry-run", "canary-ready", "cluster-health", "operator-approval"] evidence = ["dry-run diff", "pod readiness", "health 200", "State Hub progress id"] requires_approval = true canary_mode = "isolated" observation_minutes = 60 [stages.stage3] enabled = true namespace = "qonto-assistant" release = "qonto-assistant" commands = ["kubectl apply -k deploy/k8s/qonto-assistant", "kubectl -n qonto-assistant scale deployment/qonto-assistant --replicas=0"] checks = ["stage2-accepted", "rollback-target", "cluster-health", "operator-approval"] evidence = ["promotion commit", "new stable digest", "post-promotion smoke, then scale back to 0 -- the facade (T05) owns wake/idle from here on"] requires_approval = true promotion_mode = "release-replace" previous_stable = "kubectl:qonto-assistant:previous-digest" [[checks]] id = "unit-tests" type = "command" stage = "stage1" description = "Run repository unit tests." required = true run = "make test" timeout_seconds = 600 [[checks]] id = "kustomize-render" type = "command" stage = "stage1" description = "Render the kustomize manifest set locally, no cluster contact." required = true run = "kubectl kustomize deploy/k8s/qonto-assistant" [[checks]] id = "local-health" type = "http" stage = "stage1" description = "Confirm local service health." required = true url = "http://127.0.0.1:8080/v1/health" expected_status = 200 timeout_seconds = 10 [[checks]] id = "server-dry-run" type = "kubernetes" stage = "stage2" description = "Server-side dry run of the full manifest set before scaling the canary up." required = true namespace = "qonto-assistant" resource = "kustomization/deploy/k8s/qonto-assistant" condition = "DryRunAccepted" [[checks]] id = "canary-ready" type = "kubernetes" stage = "stage2" description = "Canary deployment reaches Available after being scaled to 1." required = true namespace = "qonto-assistant" resource = "deploy/qonto-assistant" condition = "Available" [[checks]] id = "cluster-health" type = "http" stage = "stage2" description = "Cluster health endpoint returns 200." required = true url = "http://qonto-assistant.qonto-assistant.svc.cluster.local:8080/v1/health" expected_status = 200 timeout_seconds = 10 [[checks]] id = "operator-approval" type = "manual" stage = "stage2" description = "Human approval is recorded before this internet-facing, credential-holding workload takes traffic -- criticality=critical per app.toml." required = true evidence_required = "State Hub approval note id, candidate digest, rollback target, confirmation that CCR-2026-0009 is approved." [[checks]] id = "stage2-accepted" type = "manual" stage = "stage3" description = "Stage 2 gates passed for the same candidate artifact." required = true evidence_required = "State Hub Stage 2 acceptance progress id." [[checks]] id = "rollback-target" type = "manual" stage = "stage3" description = "Previous stable release is recorded before promotion." required = true evidence_required = "Previous image digest or kustomize revision."