Introduce yourself. Slot 11:30-11:55, hard cap 25 min including demo. Questions after. Minute map: title ~1 · argument ~14 · demo ~5 · wrap ~4 · closer ~1. Thesis: people collaborating through agents, not the agent becoming a shared key.
The whole talk hangs on this. Single-player AI: obvious. Your tokens, your repos, your Drive. Second person joins the thread. Three people tagging the same agent. Whose access?
This is the assumption most agent auth still makes: one human, one identity (Claude.ai chat, Copilot session, coding agent on your laptop). Multiplayer agents break that. The "session" is a room: developers, operators, security, all steering the same agent.
Multiplayer is the product; the auth model didn't get the memo. Adding the on-call to the thread doesn't open a new identity boundary, it just adds them. Channel identity: the old session object with a Slack channel stuffed into it.
Not a dunk, Claude Tag makes the room/action tradeoff explicit: in a channel, Claude acts as itself using connections configured for that channel, not as the person who tagged it. Anyone in the channel gets the same capability.
Anthropic documents this: configure the channel once, connections don't change based on who asked. The mitigation, treat the channel as trusted as its most-restricted member, only works if you actually do it, and it punishes whoever has the access the incident needs. Source: Anthropic, "How agent identity works," Claude Tag docs, accessed Sept 2026. Scope the claim to the documented channel-connection model, not every Claude deployment.
Honest mitigation, but mixed rooms break it: starve Denis (who has access) or over-grant Nick (who doesn't). Fine for peer channels with equal clearance; incident threads aren't peer channels.
Paraphrase of Anthropic's own writeup, not a gotcha: the agent is allowed to do what the channel is allowed to do, the asking human isn't in the authorization path. Fine for peer channels with equal clearance; not fine once the room is mixed.
This is how people actually work: no new identity boundary opens every time a specialist joins the investigation.
There is no fourth option inside channel identity. That is why mixed rooms matter. Union: Nick asked, the agent could, so Nick got Denis's reach. Intersection: you scoped to Nick, Denis cannot pull prod logs. Service account: you invented a principal none of them hold, and anyone in the thread can wield it.
Classic confused deputy, but helpful and sitting in Slack. Nick didn't get Denis's laptop, he got Denis's access, mediated by the agent.
Not a Hollywood breach, three quiet failures: attribution, stickiness, disclosure. Plus a fourth: the tools don't end when the question does.
Security asks who pulled customer logs: the warehouse says the agent's account, Slack says a thread. "Just paste what it said" isn't provenance, the identity bound to the tool call is the agent's.
Stickiness: membership is the ACL. Leaving might be the revoke, but incident channels linger. Contractor example is illustrative, not a real incident.
Run identity governs the action, not Slack history. What gets pasted back is still shared context, that's sharing work, that's the point.
Not just Pomerium: ChatGPT's Slack app defaults to per-user permission inheritance, Copilot Studio offers per-user OAuth in Teams, Claude Tag added personal connectors on top of its channel default. Run identity goes one step further: bind the executor too, not just the person. Source: OpenAI, "Using Slack in ChatGPT"; Microsoft, Copilot Studio docs, "Configure user authentication"; Anthropic, "Personal connectors in channels," Claude Tag docs (accessed Sept 2026).
Binding to the approving person is what the industry already does. Alone it stops nothing: the right person's credential replayed from the wrong workload still gets through if nothing checks which pod uses it. Run identity adds the second binding: one attested executor pod.
Quick grounding beat, not a new argument. Some of the room won't have this term loaded; the rest of the talk leans on it hard (audit row later, "Pomerium enforces it" next slide). IAP in one line: identity and policy checked per request, at the proxy, before traffic reaches the app. Contrast with network-perimeter trust (VPN, "you're on the LAN so you're trusted") and session-based trust (log in once, trusted for the rest of the session). Always verify, never assume trust just because a request arrived. Existing use cases the room may already know Pomerium for: fronting internal web apps/APIs, SSH access, and as an MCP gateway mediating tool calls. This talk pushes the same enforcement point one layer further, onto the agent run itself, that's the bridge into "Run identity" next. Keep this short, it's context for what's coming, not a beat that needs its own reaction.
The concept the talk introduces: not a session, not a channel, the action. Person: the IdP subject that approved the run. Executor: the one attested pod that can act (Nick's Slack run isn't interchangeable with a headless cron agent). Prompt/context: only a useful authorization input when the harness/route carries and enforces it, a prompt is not a grant. This states the target design, both bindings. The demo proves the person half live; executor-pod attestation is the next milestone, not yet wired into AgentOps (see architecture slide, demo caveat). Don't imply the executor binding is already enforced in the running demo. Source: "Agentic Run Identity" reference design PDF, pp. 1-2 (confirm page numbers before citing live). Hard binding is person + executor; route policy supplies the resource/credential boundary.
First two are the run's core binding. Context/task can narrow policy only when the system carries them as trusted inputs, conversation text alone can't do that.
Channel identity answers "what connections are available in this room?" Run identity answers "which person approved this execution, and which executor is acting?" Audit row: not something to build. Pomerium as an IAP already logs human access out of the box; binding the run to person + executor gets agent traffic the same audit trail for free, ties to the "two hard parts, already built" framing later. Source: "Agentic Run Identity," pp. 1-2 and 15-20 (confirm page numbers before citing live). A run isn't itself a route grant, a route must accept run tokens and its policy decides access. Demo is the mixed-room version: Nick then Denis, same investigation, different runs. It proves the person half live (tells Nick from Denis); don't claim the executor half was demonstrated, it wasn't wired into the running demo.
Anthropic's architecture: the channel session sandbox holds no credential, Agent Proxy injects it at the network boundary, same shape as the sidecar coming up. The gap isn't isolation, it's that neither binding (channel default or personal connector) ties the credential to an attested executor pod. Source: Anthropic, "How agent identity works," Claude Tag docs, accessed Sept 2026.
Two independent Slack threads/runs, two sandboxes, not one per channel. AgentOps binds a thread to one multi-turn session, only its starter drives it. The agent container doesn't hold the upstream credential. The sidecar presents the person's own delegated OAuth token (per-user connect); Pomerium holds and brokers the credentials, not AgentOps. The pod authenticates to Pomerium via its own Kubernetes service account, and the access layer enforces what that person can do. Run identity's next step: bind the executor pod itself, not just the person. Warm pools may cut startup cost, but the security boundary is the executor pod attached to this run.
Denis's framing: "do people really care that much?" Depends where they are. Most builders go ad hoc (service account first, security later) not because they weighed and rejected identity, but because they were tasked with shipping, not designing an authorization model, and ad hoc already clears the bar of "it works." Same adoption question as Pomerium generally: being the technically better security solution isn't, by itself, why people show up. Meet people at "this already ships," don't scold them for not prioritizing security.
What you've got probably works fine for now. Getting to something more secure isn't the uphill climb you'd expect, most of the hard part's already done. Denis, verbatim in spirit: "it does not limit you, and it will also let you skip writing quite a bit of code and debugging it." That's the pitch, not "you should care more about security." Two hard parts he named: air-gap the agent (sandbox + sidecar, architecture slide) and bind it to a real user (delegated OAuth token, same slide). Both take real time to build yourself; we already did both. If you already run Kubernetes and want the agent substrate, adding Pomerium on top is not a big lift, per Denis.
Industry didn't stop at "put the rule in the system prompt": Claude Tag scopes tools/credentials per channel via an admin bundle, Agentforce scopes actions via permission sets and a dedicated agent user record. Both moved the check into a config layer the model can't rewrite, real progress. Both still resolve the check once, for the room or service user, not per run. Same gap as Claude Tag's credential-outside-the-sandbox point, one level up: the grant is scoped to who's in the room, not the run inside it. Source: Anthropic, "Introducing Claude Tag," blog post, https://www.anthropic.com/news/introducing-claude-tag; Salesforce Help, "Configure Service Agent Access," Agentforce permission-set docs (accessed Sept 2026).
Wrap starts here. Demo next (5 min), then ~1 min through the table and closer. Getting the check out of the model and into config is mostly done industry-wide. Still missing: binding that check to the specific approved run, not the channel, workspace, or service user it's acting through. The check belongs on the way out: the tool call carries the approving person and attested executor as metadata, a policy decision outside the model evaluates the request. Any identity-aware proxy can enforce this, the pattern isn't proprietary.
Real snippet from sdk/ts/examples/hello-session.ts in AgentOps as of the 2026-09-22 call. Confirm the path and parameter names still match before presenting, Denis restructured the ~50k LOC repo toward fresh experimental Pomerium images right after that call, so it may have moved. Deliberately just the client construction, not the session/event-loop code that follows (that's `client.createSession({ template, conversationRef, approvalPrompt })`, then subscribing to the event feed). Point of showing this: not much code, and token handling (a rotated, projected ServiceAccount token, not a static secret) is already done for you.
Live Slack. Same investigation, separate threads. Two runs, two sandboxes. github.com/pomerium/agentops, work in progress. Five minutes. Kubernetes-only for now. One sandbox per run in the thread. The agent container doesn't receive the upstream credential, the sidecar and access layer handle the protected connection. Reality check: the demo proves the person half of run identity (per-user delegated OAuth, enforced live), not executor-pod attestation, that binding is designed but not yet wired into AgentOps (see architecture slide). If asked in Q&A: today's binding is person-to-token, attested-executor is the next milestone. The Nick/Denis distinction still holds since it only needs the person binding. Nick: no production log access. Denis: on-call, has it. Nick tags the bot in a thread, asks for production logs. Starts Nick's run/sandbox with Nick's approval. Denied. Denis (D-E-N-I-S), same channel/investigation, separate thread and run, doesn't inherit Nick's run. Allowed, logs come back under Denis's authority. Nick can see whatever's posted to the shared channel but didn't inherit the grant. Nick retries: still denied. Shared the investigation, not the credential. Caveat: if Denis's result is sitting in the thread, Nick can read the message, that's a data-in-the-room problem, not a tool-call problem. Source: Pomerium AgentOps repo, github.com/pomerium/agentops. Confirm current Kubernetes/Slack demo behavior before presenting, it's WIP. If the demo flakes, this slide is the story, don't narrate a success that didn't happen. Same scene under channel identity: if the channel has a production-logs connection, Nick's ask succeeds; if scoped to Nick, Denis can't do the job. Either way, sharing access or blocking work.
This slide plus the last two punches are the wrap. If demo ran long, skip straight to the closer. Middle column: where most shipping products sit (Claude Tag's channel bundle, Copilot Studio's app registration, Agentforce's permission set). Real enforcement, wrong grain, answers "is this room allowed to," not "did this person, on this executor, get approved." Right column: the target model, person + executor, checked per request. The demo (Nick denied, Denis allowed) showed the person half live; don't credit it with proving the executor half, that's Pomerium core's concept (union of user + workload identity), not yet wired into this demo. "Scoped to the run" means the tool call carries the approving person and attested executor as metadata the infrastructure reads, not model-written text. A policy engine outside the model decides. Today the demo's tool calls carry the person; executor metadata is next to wire in. Pomerium is how I work on this; the pattern isn't proprietary. If the check stops at the room, two different people in it look identical to the policy.
Multiplayer is the point, keep the shared thread and investigation. Bind each action to a run identity (approving person + attested executor), let route policy decide the resource/credential boundary. Ties back to the "Run identity" slide's thesis (identity-aware agents, primitives, not something you build yourself) and the title. The future of multiplayer agents is people collaborating, not a group-sized service account. End of talk, target ~11:50 for a few minutes of Q&A. QR slide is for lingering.
Four codes: Pomerium, agentops (the Kubernetes Slack bot from the demo, WIP), the deck, nickyt.co. Find-me slide, not a second ending, the last line of the talk happens on the previous punch.