feat(orchestrator+egress): slice 8 — multi-tenant egress via the resolver #363
Open
didericis-claude
wants to merge 1 commits from
orchestrator-slice8 into orchestrator-slice7
pull from: orchestrator-slice8
merge into: didericis:orchestrator-slice7
didericis:main
didericis:orchestrator-registration
didericis:orchestrator-lifecycle
didericis:orchestrator-supervise-writers
didericis:orchestrator-supervise-multitenant
didericis:orchestrator-gitgate-multitenant
didericis:orchestrator-rename-gateway
didericis:orchestrator-slice7
didericis:orchestrator-slice6
didericis:prd-orchestrator
didericis:orchestrator-slice5
didericis:orchestrator-slice4
didericis:orchestrator-slice3
didericis:orchestrator-slice2
didericis:ci-kvm-runner
didericis:post-build-image-smoke-test
didericis:firecracker-backend
didericis:issue-330-cached-images
didericis:forge-native-integration
didericis:prd-smolmachines-linux
didericis:claude-forward-host-credentials
didericis:fold-orchestrator-subpackage
didericis:prd-egress-control-plane
didericis:manifest-break-import-cycle
didericis:dlp-supervise-quality-fixes
didericis:table-drive-dlp-tests
didericis:fix-integration-test-failures
didericis:fix/macos-container-relative-dockerfile
didericis:prd-0054-install-script
didericis:commit-bottle-state
didericis:pr-211
didericis:move-codex-auth-to-contrib
didericis:feat/pipelock-skip-scan-extensions
didericis:prd-0049-named-labelled-agents
didericis:harden-git-gate-shell-rendering
Labels
Clear labels
Compat/Breaking
Kind/Bug
Kind/Documentation
Kind/Enhancement
Kind/Feature
Kind/Security
Kind/Testing
Breaking change that won't be backward compatible
Something is not working
Documentation changes
Improve existing functionality
New functionality
This is security issue
Issue or pull request related to testing
Priority
Critical
1
The priority is critical
Priority
High
2
The priority is high
Priority
Low
4
The priority is low
Priority
Medium
3
The priority is medium
Reviewed
Confirmed
1
Issue has been confirmed
Reviewed
Duplicate
2
This issue or pull request already exists
Reviewed
Invalid
3
Invalid issue
Reviewed
Won't Fix
3
This issue won't be fixed
Status
Abandoned
3
Somebody has started to work on this but abandoned work
Status
Blocked
1
Something is blocking this issue or pull request
Status
Need More Info
2
Feedback is required to reproduce issue or to continue work
No Label
Milestone
No items
No Milestone
Projects
Clear projects
No project
No Assignees
Notifications
Due Date
No due date set.
Dependencies
No dependencies set.
Reference: didericis/bot-bottle#363
Reference in New Issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Delete Branch "orchestrator-slice8"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Slice 8 of PRD 0070, stacked on #362. The egress addon now selects each request's
Configby the calling bottle's source IP, so one shared sidecar serves every bottle. Opt-in and fail-closed; single-tenant behaviour is unchanged (all 182 existing egress tests still pass).Orchestrator side (source-IP-primary attribution, per the PRD invariant):
registry.by_source_ip(single active bottle at a source IP — network-layer attribution);attributenow composes it + the token.service.resolve(source_ip, token="")— with a token, strict; without, source IP alone.POST /resolve'sidentity_tokenis now optional (absent → source-IP-only); split cleanly from the token-required/attribute.policy_resolver.resolvetoken optional.Egress side:
egress_addon_core.resolve_client_config(...)— fetches + parses the client'sConfig, fail-closed: unattributed / resolver error / unparseable policy all → deny-all (no routes). Host-testable; aPolicyResolverLikeProtocol keeps it import-free.egress_addon: consolidated mode whenBOT_BOTTLE_ORCHESTRATOR_URLis set →_active_config(flow)resolves per client IP (reads + strips thex-bot-bottle-identityheader);request()uses it. Unset → the static routes file, exactly as before.Security note: source-IP-only resolution is safe where the IP is unspoofable (Firecracker
/31+ nft) and the control plane is reachable only by the trusted sidecar; the identity token, when the agent injects it, strengthens it on weaker backends.Scope note: the egress data plane is now multi-tenant. Remaining to be fully live: the network topology routing every bottle's proxy to the one shared sidecar, git-gate multitenancy, and agent-side identity-token injection.
Merge order: #352 → #356 → #357 → #358 → #360 → #361 → #362 → this.
🤖 Generated with Claude Code
The egress addon now selects each request's Config by the calling bottle's source IP, so one shared sidecar serves every bottle. Opt-in and fail-closed; single-tenant behaviour is unchanged. Orchestrator side (source-IP-primary attribution, per the PRD invariant): * registry: `by_source_ip` (the single active bottle at a source IP — network-layer attribution); `attribute` now composes it + the token. * service: `resolve(source_ip, token="")` — with a token, strict attribution; without, source IP alone. * control_plane: `POST /resolve`'s identity_token is now OPTIONAL (absent → source-IP-only); split cleanly from the token-required `/attribute`. * policy_resolver: `resolve` token now optional. Egress side: * egress_addon_core: `resolve_client_config(resolver, client_ip, token)` — fetches + parses the client's Config, **fail-closed**: unattributed, a resolver error, or an unparseable policy all yield deny-all (no routes). Host-testable; `PolicyResolverLike` Protocol keeps it import-free. * egress_addon: consolidated mode when `BOT_BOTTLE_ORCHESTRATOR_URL` is set → `_active_config(flow)` resolves per client IP (reads + strips the `x-bot-bottle-identity` header); `request()` uses it. Unset → the static routes file, exactly as before. `PolicyResolver` added to the bundle. Security note: source-IP-only resolution is safe where the IP is unspoofable (Firecracker /31 + nft) AND the control plane is reachable only by the trusted sidecar; the identity token, when the agent injects it, strengthens it on weaker backends. Scope note: the egress data plane is now multi-tenant. Remaining to be fully live: the network topology routing every bottle's proxy to the one shared sidecar, git-gate multitenancy, and agent-side identity-token injection. Tests: registry by_source_ip; orchestrator resolve (with/without token); control-plane /resolve token-optional; resolver token-optional; resolve_client_config fail-closed matrix. All 182 egress tests still pass (single-tenant unchanged). Full suite green. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WBMWTEtQdJ4W5UrWuLHCckView command line instructions
Checkout
From your project repository, check out a new branch and test the changes.