Security
What holds, what each control defends against, and what does not hold yet
The guarantee comes from where the keys sit. No service has to behave well for it to hold. The limits are stated as plainly as the properties.
Trust tiers
Three identities take part in every call, and each is proved differently. The attestation carries the tier of the agent hops, so policy can branch on them.
| Identity | Tier | What proves it |
|---|---|---|
| The customer | verified | Their Entra access token, validated by PingFederate as the RFC 8693 subject against the tenant JWKS. |
| Copilot Studio agent to its mirror | connection | The caller held that agent's provisioned connection secret. Microsoft cannot assert which agent is calling, so this is deliberately labelled below entra_token. |
| The mirror identity | entra_token | A tenant-signed Entra Agent ID token verified at the attestation service. |
The agent to mirror binding is routing configuration backed by a secret. Everything after it is cryptographic.
Security properties
| Property | Defends against |
|---|---|
Key custody split: the gateway signs nothing, the bridge holds only fed_entity keys, the attestation service holds only attester and instance keys | One compromised service producing a usable attestation on its own keys. |
| The attestation service verifies the raw mirror token itself | A compromised or faulty bridge fabricating Entra evidence. |
| The attestation service is on internal ingress and authenticates its caller by managed identity | Anything outside the environment calling /attest and skipping the gateway's connection check. |
| Header allow-list at the gateway. An inbound mirror token header is dropped. | A caller supplying its own mirror token. Connection credentials travelling further than the gateway. |
| One 401 for every authentication failure, with a comparison against a dummy fingerprint for unknown key ids | Telling "wrong secret" from "no such agent". |
| Fingerprints only in the registry | A leaked registry yielding usable connection keys. |
metadata_policy on the subordinate statement | A leaf claiming looser client terms than the bridge vouches for. |
| Fresh proof of possession per exchange, 60 seconds, with PingFederate's replay cache | Replaying a captured attestation and PoP. |
| Agents resolved through the trust chain, absent from PingFederate's static file | Copying agent key material into PingFederate configuration, or redeploying PingFederate per agent. |
| PingFederate validates the subject token itself | The gateway or bridge vouching for a customer without PingFederate checking. |
| Mock material is refused by name in real mode | A mock-signed token being accepted in a real deployment. |
If one service is compromised
Splitting signing keys across services limits what each service can do alone. It does not stop every single-service compromise, and the design review says so.
| Service | It can | It cannot |
|---|---|---|
| gateway | Obtain mirror tokens for every registered agent, because it holds the blueprint's credential. Read every connection secret and user token sent to it. Create agent identities under our blueprint, which get no attestation unless they are registered. | Sign anything. Produce an attestation without the attestation service accepting its mirror token. |
| bridge | Sign federation statements. Read the mirror and user tokens it receives and reuse them until they expire. Ask the attestation service for attestations for any agent whose mirror token it holds. | Sign an attestation or PoP itself. |
| attestation service | Skip its own evidence checks and sign an attestation and PoP for any registered agent. Combined with the bridge's public federation statements, this forges the agent's client credential. | Forge a customer token. A bank token still needs a customer token PingFederate accepts. |
Stronger resistance to an attestation service compromise needs a check it cannot fabricate, for example PingFederate verifying the Entra mirror token itself as the RFC 8693 actor_token.
Known limits
None of these is hidden from the demonstration. Each one has an owner in the change plan or is a Microsoft platform limit.
The agent to mirror hop is a shared secret
It proves who holds the connection key, not which agent Microsoft ran. The attestation labels it connection.
Consent is assumed
Any registered agent holding a valid customer token can act for that customer. One sign-in app per agent, adopted from the review, gives a Microsoft-signed link between customer and agent.
Issued tokens are bearer tokens
Client authentication uses proof of possession. The access token itself is not sender-constrained. Short lifetimes and per-operation policy decisions limit the exposure.
The authority ceiling is attested but not yet enforced
The token exchange does not request it by default. PingFederate enforces requested ⊆ attested when both are sent.
Customer token checks are incomplete
PingFederate checks issuer, signature and expiry. It does not yet check audience, scope, the client the token was issued to, or a link from the Entra user to a bank customer. The demo keys the customer on preferred_username, which is mutable. A real deployment resolves the tenant and object id to an internal customer id.
250 agents per blueprint
Entra caps a customer-owned blueprint at 250 agent identities. Past that, you add another blueprint, and nothing else in the chain changes.
The namespace is enforced by the bridge
naming_constraints is not implemented in PingFederate's validator, so the /agents/* namespace is not enforced cryptographically. The federation list endpoint is open in the demo.
The Copilot Studio connection is set up by hand
It must be consented by the maker and show Connected. Changing the connector's authentication type leaves it Stale. None of this can be provisioned without a person.
The gateway is reachable from the internet
The August deployment uses public ingress. The network design removes it with Power Platform Virtual Network support.
No infrastructure-as-code for Azure
The Azure resources were created by hand. The change plan adds code for the network, the Container Apps, the app registrations and the agent identities.