Skip to content

Security & RBAC

Defence-in-depth at the edge, in transit, at rest, and at the query layer. RBAC policy is centralised in core-svc.

Request flow — security layers

flowchart LR
  IN([User request<br/>Bearer + X-Tenant-Slug])
  ARM[Cloud Armor<br/>WAF · OWASP CRS · geo rules]
  IAP[IAP<br/>officer-only hosts]
  GW[Cloud LB · TLS 1.3 edge]
  MESH[Anthos Service Mesh<br/>mTLS between services]
  APP[SISS service<br/>FastAPI]
  CORE[core-svc<br/>decision cache · Redis<br/>object-level policy]
  GTC[GT Console<br/>module-level RBAC]
  RLS[AlloyDB RLS<br/>tenant_id + department_id]

  IN --> ARM --> IAP --> GW --> MESH --> APP
  APP -->|ingress check| CORE
  CORE -->|cache miss| GTC
  GTC --> CORE
  CORE --> APP
  APP --> RLS

Controls by layer

Layer Control
Edge Cloud Load Balancer + Cloud Armor (WAF, OWASP CRS, geo rules). IAP gates officer-only hosts.
Transport TLS 1.3 at the edge; mTLS between services via Anthos Service Mesh (or Istio).
Secrets Secret Manager only. CMEK on AlloyDB and GCS.
Network Private GKE cluster, VPC Service Controls boundary around BigQuery / GCS / AlloyDB, Private Service Connect for Vertex AI.
Headers / sessions Strict CSP, HSTS, SameSite=Strict cookies, 15-minute idle timeout, session rotated on privilege change.
VAPT Quarterly third-party penetration tests starting at M6.

RBAC

Authorization is split between the CityOS platform (coarse, module-level) and SISS (fine, object-level). See Platform integration for the full contract.

  • GT Console answers "Can this user touch SISS, and in what role?" — module-level siss.* permissions, composed into GT Console roles, granted to users via group-mapping (GCIP claims) or tenant-domain defaults.
  • SISS answers "Can they touch this specific submission / sign this specific perakuan?" — object-level policy enforced in core-svc and at the AlloyDB query layer.

Module-level permissions (GT Console)

Code Meaning
siss.access Baseline — can reach SISS at all
siss.psp External submitter
siss.officer Internal reviewer (CMU / ATD / ATL / SIRP)
siss.officer.sign Authorised to issue a digital signature
siss.admin Workflow config and user management within CMU tenant
siss.auditor Read-only access to the audit BigQuery dataset

The human-facing seed roles used elsewhere on this site (PSP, CMU.Officer, CMU.Admin, ATD/ATL.Officer, SIRP.Officer, Auditor, System.Admin) compose out of these permissions inside GT Console.

Object-level policy (SISS)

Enforced in core-svc and, for query-layer scoping, in AlloyDB via RLS:

  • Tenant scopingtenant_id is part of every WHERE clause via RLS.
  • Department scoping — ATD / ATL officers see only submissions routed to their department (department_id RLS).
  • Per-submission ownership — PSPs see only their firm's submissions (tenant_id + submitter_id RLS).
  • Sign-authority gates — enforced in signing-svc and workflow-svc.
  • Step-up authentication — required for sensitive actions: digital signature, RBAC change, workflow config publish. See Signing.

Permission denial is audited

Every failed authorisation check is an audit event, not just an access log line. This lets auditors see attempts and patterns, not just successes. See Observability.