---
schema_version: "1"
id: 72792784eee68b99640f943d83a6eb6a02d129b483c521866a175697d3b380a6
title: GraphQL Access Control Policy
collection: mulesoft
version: current
locale: en-us
portal_url: https://docs.salesforce.com/mulesoft/current/en-us/gateway/latest/policies-included-graphql-access-control.md
canonical_url: https://docs.mulesoft.com/gateway/latest/policies-included-graphql-access-control
source_site: docs.mulesoft.com
content_type: documentation
content_hash: ccc5f83e4812dd722afc52d900ab04a8bdaccf9255574583ef6a4205a2d0abca
description: MuleSoft Documentation Site
release: "1.14"
latest: true
---
---
product: Omni Gateway
version: 1.14
is-latest-version: true
keywords: graphql, access control, authorization, cedar, api gateway, flex gateway, gateway, policy
---

# GraphQL Access Control Policy

> For the full documentation index, see: https://docs.mulesoft.com/llms.txt

<table><colgroup><col> <col></colgroup><tbody><tr><td><p><strong>Policy Name</strong></p></td><td><p>GraphQL Access Control</p></td></tr><tr><td><p><strong>Summary</strong></p></td><td><p>Authorizes incoming GraphQL requests by evaluating Cedar rules</p></td></tr><tr><td><p><strong>Category</strong></p></td><td><p>Security</p></td></tr><tr><td><p><strong>First Omni Gateway version available</strong></p></td><td><p>v1.14.0</p></td></tr><tr><td><p><strong>Release Notes</strong></p></td><td><p><a href="https://docs.mulesoft.com/release-notes/gateway/policies/graphql-access-control-release-notes">GraphQL Access Control</a></p></td></tr><tr><td><p><strong>Returned status codes</strong></p></td><td><p>403 Forbidden — No rule authorizes the request. The response body is a JSON object with an <code>error</code> message such as <code>GraphQL request denied by access control policy</code>.</p></td></tr></tbody></table>

## Summary

The GraphQL Access Control policy authorizes each incoming GraphQL request against a set of
[Cedar](https://www.cedarpolicy.com/) rules that you define. Cedar is an open-source policy language
that expresses authorization as `permit` and `forbid` statements. Omni Gateway allows a request only
when at least one `permit` rule matches it and no `forbid` rule matches.

Use this policy to enforce fine-grained, attribute-based authorization on GraphQL traffic. For
example, you can restrict mutations to privileged clients, allow specific named operations, or gate
access by request header, SLA tier, or source IP address.

To make identity-based decisions, apply an upstream authentication policy, such as Basic
Authentication, Client ID Enforcement, JWT Validation, OAuth 2.0 Token Introspection, or OpenID
Connect, before this policy. The authentication policy populates the `principal` that the rules
evaluate. When no authentication policy runs, Omni Gateway evaluates the request against the
`Client::"None"` principal. For the attributes that each authentication policy provides, see
[Attributes Available to Cedar Rules](#attributes-available-to-cedar-rules).

After Omni Gateway extracts the GraphQL operation text, the policy evaluates your rules against the
request. The policy skips persisted queries and passes them to the upstream service without
authorization checks, because Omni Gateway doesn’t inspect their operation text. Non-GraphQL
requests also pass through.

## Configuring Policy Parameters

### Omni Gateway Local Mode

When you apply the policy via declarative configuration files, Refer to the following policy
definition and table of parameters:

\- policyRef: name: graphql-access-control-flex config: rules: <array> // REQUIRED, list of Cedar
policy statements; can't be empty

<table><colgroup><col> <col> <col> <col></colgroup><thead><tr><th>Parameter</th><th>Required</th><th>Default Value</th><th>Description</th></tr></thead><tbody><tr><td><div><div><p><code>rules</code></p></div></div></td><td><div><div><p>Yes</p></div></div></td><td><div><div><p>None</p></div></div></td><td><div><div><p>A list of Cedar policy statements that authorize requests. Each statement must be a valid Cedar <code>permit</code> or <code>forbid</code> rule that ends with a semicolon. The list can’t be empty.</p></div></div></td></tr></tbody></table>

### Managed Omni Gateway and Omni Gateway Connected Mode

When you apply the policy from the UI, the following parameters are displayed:

<table><colgroup><col> <col> <col> <col></colgroup><thead><tr><th>Field</th><th>Description</th><th>Default Value</th><th>Required</th></tr></thead><tbody><tr><td><div><div><p>Rules</p></div></div></td><td><div><div><p>The list of Cedar policy statements that authorize requests. Add one entry per <code>permit</code> or <code>forbid</code> rule. Each rule must be valid Cedar and end with a semicolon.</p></div></div></td><td><div><div><p>None</p></div></div></td><td><div><div><p>Yes</p></div></div></td></tr></tbody></table>

## Attributes Available to Cedar Rules

Cedar rules authorize a request by matching against attributes of the `principal`, which is the
authenticated client, and the request `context`. Use these attributes in the `when` clause of a rule
to make fine-grained decisions.

Cedar rules can match requests against these `context` attributes:

<table><colgroup><col> <col></colgroup><thead><tr><th>Attribute</th><th>Description</th></tr></thead><tbody><tr><td><div><div><p><code>context.headers["&lt;name&gt;"]</code></p></div></div></td><td><div><div><p>The value of a request header. Use bracket notation to access header names that contain characters such as dashes, for example, <code>context.headers["x-internal"]</code>.</p></div></div></td></tr><tr><td><div><div><p><code>context.graphqlQuery</code></p></div></div></td><td><div><div><p>The raw GraphQL operation text.</p></div></div></td></tr><tr><td><div><div><p><code>context.operationName</code></p></div></div></td><td><div><div><p>The name of the resolved operation. If the request provides an <code>operationName</code>, Omni Gateway resolves that operation. Otherwise, Omni Gateway resolves the first operation in the document. Empty when the operation is anonymous.</p></div></div></td></tr><tr><td><div><div><p><code>context.operationType</code></p></div></div></td><td><div><div><p>The type of the resolved operation: <code>query</code>, <code>mutation</code>, or <code>subscription</code>. Shorthand documents resolve to <code>query</code>.</p></div></div></td></tr><tr><td><div><div><p><code>context.rootField</code></p></div></div></td><td><div><div><p>The name of the first top-level field in the resolved operation.</p></div></div></td></tr><tr><td><div><div><p><code>context.ipAddress</code></p></div></div></td><td><div><div><p>The source IP address of the request, when available.</p></div></div></td></tr></tbody></table>

Cedar rules can also match requests against these `principal` attributes. You must apply an
authentication policy before the GraphQL Access Control policy to populate these values. To learn
what policies update which attributes, see
[Authentication Policies Principal Attributes](#authentication-policies-principal-attributes).

<table><colgroup><col> <col></colgroup><thead><tr><th>Attribute</th><th>Description</th></tr></thead><tbody><tr><td><div><div><p><code>principal.principal</code></p></div></div></td><td><div><div><p>The authenticated principal identifier, such as the Basic Authentication username or the raw token.</p></div></div></td></tr><tr><td><div><div><p><code>principal.client_id</code></p></div></div></td><td><div><div><p>The client ID resolved by the upstream authentication policy, when available.</p></div></div></td></tr><tr><td><div><div><p><code>principal.client_name</code></p></div></div></td><td><div><div><p>The client application name resolved by the upstream authentication policy, when available.</p></div></div></td></tr><tr><td><div><div><p><code>principal.properties.&lt;name&gt;</code></p></div></div></td><td><div><div><p>Additional properties published by the upstream authentication policy. For example, JWT Validation exposes <code>principal.properties.claims.&lt;claim&gt;</code>, and OAuth 2.0 Token Introspection exposes <code>principal.properties.scope</code>.</p></div></div></td></tr><tr><td><div><div><p><code>principal.properties.slaId</code></p></div></div></td><td><div><div><p>The SLA tier ID of the client, when an upstream policy publishes it.</p></div></div></td></tr><tr><td><div><div><p><code>principal.properties.slaName</code></p></div></div></td><td><div><div><p>The human-readable SLA tier name that corresponds to <code>slaId</code>, resolved from the API instance metadata.</p></div></div></td></tr></tbody></table>

When no authentication policy runs, Omni Gateway evaluates the request against the `Client::"None"`
principal, and these `principal` attributes are empty.

## Authentication Policies Principal Attributes

Apply an authentication policy before this policy to populate the `principal` attributes that your
Cedar rules evaluate.

### Included Authentication Policies

The authentication policy you apply affects the available Cedar `principal` bindings:

- Multiple policies can validate Client ID:

  - [Client ID Enforcement Policy](https://docs.mulesoft.com/gateway/latest/policies-included-client-id-enforcement)

  - [Rate Limiting: SLA-Based Policy](https://docs.mulesoft.com/gateway/latest/policies-included-rate-limiting-sla)

  - [OAuth 2.0 Token Introspection Policy](https://docs.mulesoft.com/gateway/latest/policies-included-oauth-token-introspection) (If Client
    ID enforcement is configured)

  - [OpenID Connect OAuth 2.0 Token Enforcement Policy](https://docs.mulesoft.com/gateway/latest/policies-included-openid-token-enforcement)
    (If Client ID enforcement is configured)

  - [JWT Validation Policy](https://docs.mulesoft.com/gateway/latest/policies-included-jwt-validation) (If Client ID enforcement is
    configured)

    Policies validating Client ID provide these Cedar bindings:

  - `principal.client_name`: Name of the contract’s client application

  - `principal.principal`: ID of the contract’s client application

  - `principal.properties.slaId`: SLA ID assigned to the contract

- [JWT Validation Policy](https://docs.mulesoft.com/gateway/latest/policies-included-jwt-validation):

  - `principal.properties.claims.<claimName>`: All claims provided by the JWT

- Multiple policies validate basic authentication credentials:

  - [Basic Authentication: Simple Policy](https://docs.mulesoft.com/gateway/latest/policies-included-basic-auth-simple)

  - [Basic Authentication: LDAP Policy](https://docs.mulesoft.com/gateway/latest/policies-included-basic-auth-ldap)

    Policies validating basic authentication credentials provide these Cedar bindings:

  - `principal.principal`: Username passed as basic auth user

### Custom Authentication Policies

For custom authentication policies, the custom policy must authenticate by using the
`Authentication` injectable. To configure the `Authentication` injectable, see
[Accessing Request Authentication Information](https://docs.mulesoft.com/pdk/latest/policies-pdk-configure-features-authentication).

For the Rust `AuthenticationData` structure:

```rust
pub struct AuthenticationData {
    pub principal: Option<String>,
    pub client_id: Option<String>,
    pub client_name: Option<String>,
    pub properties: Value,
}
```

The `AuthenticationData` parameters map to these Cedar bindings:

- `principal`: `principal.principal`

- `client_name`: `principal.client_name`

- `properties`: `principal.properties.*`

## Configuration Examples

These examples are valid whether you configure the policy in a Local Mode resource file or through
the Omni Gateway UI.

This example permits queries from any client but restricts mutations to clients that authenticate as
`admin`:

```yaml
- policyRef:
    name: graphql-access-control-flex
  config:
    rules:
      - permit(principal, action, resource) when { context.operationType == "query" };
      - permit(principal, action, resource) when { principal.principal == "admin" };
```

This example permits requests only from internal callers that a request header identifies, and
blocks introspection-style queries against the `__schema` root field:

```yaml
- policyRef:
    name: graphql-access-control-flex
  config:
    rules:
      - permit(principal, action, resource) when { context.headers["x-internal"] == "true" };
      - forbid(principal, action, resource) when { context.rootField == "__schema" };
```

## See Also

- [Inbound Policies Directory](https://docs.mulesoft.com/gateway/latest/policies-included-directory)

- [GraphQL Introspection Control Policy](https://docs.mulesoft.com/gateway/latest/policies-included-graphql-introspection-control)

- [GraphQL Schema Validation Policy](https://docs.mulesoft.com/gateway/latest/policies-included-graphql-schema-validation)

- [Securing Omni Gateway Instances with Policies](https://docs.mulesoft.com/gateway/latest/gateway-secure-apis)

- [Cedar policy language](https://www.cedarpolicy.com/)
