Story-1203 — AgentCore networking: resolve networkMode: "PUBLIC", decide + spec VPC mode

pramaan-io/pramaan-spec#1203 · pramaan-agents · 2026-06-12 · parent EPIC-006

Decision. VPC mode is required for the Atlas runtime (and every future product agent) before it touches the shared Postgres cluster or any real privileged data — with no NAT gateway, so agents have zero internet egress, exactly as pramaan-docs ADR-070 demands. networkMode: "PUBLIC" is tolerated only for the current state (staging Atlas, no DB, no privileged data, Bedrock-only) and is never copied to new runtimes.
Scope change honored, conflict surfaced. Founder direction (2026-06-12): agent-infra IaC moves from CDK to Terraform; the CDK clause of pramaan-docs ADR-108 is to be superseded. Therefore this PR ships the decision and a Terraform-ready parameter spec (docs/notes/agentcore-networking-terraform-spec.md) instead of an agentcore.json/CDK change. Conflict noted rather than silently absorbed: pramaan-docs ADR-108 (accepted) still mandates the CDK path and this repo's AGENTS.md still lists Terraform-here as an anti-pattern — so a superseding ADR in pramaan-docs must land before any *.tf is written (in pramaan-infra per pramaan-docs ADR-067, never in this repo).

1. What PUBLIC vs VPC actually means (official AWS docs, fetched 2026-06-12)

Sources: AgentCore devguide agentcore-vpc.html, control-plane API reference (NetworkConfiguration, VpcConfig), Bedrock PrivateLink guide (vpc-interface-endpoints.html).

PUBLIC todayVPC required before real data
InboundIdentical in both modes: the SigV4 InvokeAgentRuntime AWS API, called by the pramaan-functions broker. The runtime never exposes a public listener — network mode is purely an egress question.
EgressContainer runs in an AWS-managed service network with open internet egress — a standing ADR-070 violation, and it cannot reach the private Postgres.ENIs in our subnets via service-linked role AWSServiceRoleForBedrockAgentCoreNetwork. AWS: “When you connect AgentCore Runtime to a VPC, it does not have internet access by default.” Public subnets don't change that — ENIs get private IPs only; internet would need NAT, which we deliberately do not provision.
ConfignonenetworkModeConfig: subnets (1–16, required) + securityGroups (1–16, required); subnets must be in supported AZ IDs (ap-south-1: aps1-az1/az2/az3).

Two facts that shaped the spec:

2. Account inventory (read-only AWS, profile default, ap-south-1, 2026-06-12)

ResourceFound
VPCvpc-06b42e2cb2e9f2936 — default VPC tagged stg-pramaan-vpc, CIDR 172.31.0.0/16
Subnetssubnet-0aff595f086a3c26c (aps1-az1), subnet-05c5a5875be47b344 (aps1-az2), subnet-0c0ca0f2c4b27c7c6 (aps1-az3) — all in supported AZ IDs; all “public”, which is harmless: agent ENIs carry private IPs and there is no NAT, so VPC mode here yields zero internet egress
NAT gatewaysnone — and we keep it that way for agents
VPC endpointsonly SES (…​.email); bedrock-runtime, logs, and the S3 gateway must all be created
Shared PostgresRDS pramaan-dev-db — same VPC, not publicly accessible, pramaan-dev-db.cjsgoq2287fa.ap-south-1.rds.amazonaws.com:5432, subnet group spans all 3 subnets, SGs sg-0f42f9153947e2ebf, sg-04db969701da47672

Everything VPC mode needs already exists or is a small additive change — no new VPC, no re-homing of the database.

3. Before / after

ArtifactBeforeAfter this PR
agentcore/agentcore.json"networkMode": "PUBLIC"Unchanged by design (scope change: no CDK-path wiring). Flips to VPC with the Terraform migration; target config recorded in the spec: networkMode: "VPC" + the 3 subnets + the new agent SG.
agentcore/AGENTS.md“⚠️ OPEN: networkMode: "PUBLIC"… mandatory follow-up”“DECIDED (Story-1203…): VPC mode required before Postgres/real data; no NAT ever; wiring spec in docs/notes/agentcore-networking-terraform-spec.md; lands via Terraform in pramaan-infra after the superseding ADR.”
Root AGENTS.md“OPEN FOLLOW-UP: … VPC-mode decision is a mandatory follow-up story”“DECIDED (Story-1203)…” pointing at the spec.
Spec—docs/notes/agentcore-networking-terraform-spec.md — decision, doc evidence, inventory, and the full Terraform parameter set.

4. The Terraform-ready parameters (summary — full detail in the spec)

{
  "networkMode": "VPC",
  "networkModeConfig": {
    "subnets": [
      "subnet-0aff595f086a3c26c",
      "subnet-05c5a5875be47b344",
      "subnet-0c0ca0f2c4b27c7c6"
    ],
    "securityGroups": ["<agentcore-atlas-runtime-stg id>"]
  }
}

5. What remains (outside this Story)

Verification performed: official AWS docs fetched (not guessed); AWS account access read-only throughout; no agentcore deploy executed; rails (src/) and Atlas behavior (app/atlas/) untouched.