OIDC handles authentication, meaning it verifies the user and issues tokens such as JWTs. OPA handles authorization, meaning it evaluates the token, the request, and the policy to decide whether the specific GraphQL operation is allowed. In practice, that separation lets teams keep identity proofing distinct from policy enforcement and makes complex access rules easier to govern.
OIDC authentication and OPA authorization serve different jobs in a GraphQL gateway
OpenID Connect is the identity layer: it proves who the caller is and produces an identity token that the gateway can trust. OPA is the policy layer: it makes a decision about whether that caller may perform a particular GraphQL action, often after combining token claims, request context, and business rules. That separation keeps authentication and authorization from collapsing into one brittle control.
Why the split matters in a GraphQL gateway
GraphQL gateways often front many backend services and expose a flexible query surface, so a single login decision is not enough to govern access safely. The gateway usually needs to validate the caller once, then evaluate field-level, operation-level, or tenant-specific rules repeatedly as requests change.
OIDC is well suited to the first step because it standardises federation, identity proofing, and token issuance. OPA is well suited to the second step because policy can be expressed independently of application code and can incorporate claims, scopes, roles, and request attributes without embedding access logic into every resolver.
In practice, that means a caller can be authenticated successfully but still denied a specific query, mutation, or nested field if policy says the request exceeds the caller’s rights. This is the key design advantage in GraphQL, where one endpoint can represent many different resource combinations and business actions.
How the two controls interact at runtime
A typical gateway flow is: authenticate the caller with OIDC, extract trusted claims from the token, and pass the request context to OPA for a decision. OPA can then answer questions such as whether this user may access this object, invoke this mutation, or read this field in this environment.
The important design point is that OIDC does not decide business permission, and OPA should not be asked to prove identity from scratch. OIDC establishes the caller’s identity and trust context, while OPA enforces the policy that uses that context. Keeping those responsibilities separate reduces duplicated logic and makes policy changes safer to review.
This pattern is especially valuable when access rules depend on more than just a role. For example, the same authenticated user may be allowed to query one tenant, one environment, or one data class but blocked from another, and those decisions are easier to maintain when the gateway treats identity and policy as distinct layers.
Standards & Framework Alignment
This section maps relevant standards and security frameworks to the operational risks and controls described in this guidance.
OWASP API Security Top 10 addresses the attack and risk surface, while OWASP ASVS and NIST SP 800-53 Rev 5 set the governance and control requirements practitioners need to meet.
| Framework | Control / Reference | Relevance |
|---|---|---|
| OWASP API Security Top 10 | API5 — Broken Function Level Authorization | GraphQL gateway authorization decisions depend on per-operation permission checks. |
| Recommendation — Enforce operation-level authorization for every GraphQL action. | ||
| OWASP ASVS | V8 — Authorization | Separates authentication from authorization decisions in a gateway design. |
| Recommendation — Implement distinct authorization checks after authentication is established. | ||
| NIST SP 800-53 Rev 5 | IA-2 — Identification and Authentication (Organizational Users) | OIDC is the identity-verification layer for authenticated callers. |
| AC-3 — Access Enforcement | OPA enforces the policy decision that allows or denies the requested GraphQL action. | |
| AC-6 — Least Privilege | GraphQL gateways should permit only the minimum authorized operations for each caller. | |
| Recommendation — Use IA-2 to establish caller identity before applying access policy. Apply AC-3 to enforce policy decisions on each requested operation. Restrict GraphQL access to the minimum permissions required. | ||
Practitioner Guidance
What to verify: Make sure the gateway verifies the OIDC token before any policy evaluation, and ensure OPA receives only the claims and request attributes it actually needs. If policy depends on scopes, audience, tenant, or environment, those values should be explicit and consistent rather than inferred in code.
Decision rule: If the control question is “who is this caller?”, use OIDC. If the control question is “may this authenticated caller perform this specific GraphQL operation?”, use OPA. When the boundary is unclear, treat it as a design smell because blurred responsibilities usually create authorization drift.
What practitioners underestimate: GraphQL’s flexibility makes authorization failures easier to hide than in simpler APIs, because a single endpoint can expose many data paths. The safest design is to authenticate once at the edge, authorize repeatedly at the operation or field boundary, and keep those checks observable and testable.
Practitioner takeaway: OIDC establishes trustworthy identity context, but OPA is what turns that context into a precise permission decision for each GraphQL request.
Related resources from NHI Mgmt Group
- What is the difference between gateway-level authentication and fine-grained authorization for APIs?
- What is the difference between OIDC authentication and an app-specific login flow in mobile identity design?
- What is the difference between authentication and authorization in multi-tenant app design?
- What is the difference between authentication and authorization in GraphQL access control?