Cedar Authorization
Cedar policies control three authorization domains in Lattice: cluster access, secret access, and security overrides. All domains use default-deny semantics — access must be explicitly granted.
This guide covers Cedar authorization patterns and examples. For the CedarPolicy CRD spec and field reference, see the CedarPolicy API reference.
Overview
Controls which users and groups can connect to Kubernetes clusters via the auth proxy.
Controls which services can retrieve secrets from providers during service compilation.
Controls which services can relax Pod Security Standards (capabilities, privileged mode, host networking).
Entity Model
Cedar policies reference six entity types that map to Lattice authorization concepts.
Individual users from OIDC. Referenced by email, e.g. "alice@example.com".
User groups from the OIDC groups claim. Referenced by group name, e.g. "sre-team".
Pod/service identity as "namespace/name". Attributes: namespace, name.
Kubernetes cluster. Attributes: environment, region, tier.
Secret identity as "provider:path". Attributes: path, provider.
Security feature as "category:id". Attributes: category, override_id.
Actions
Three Cedar actions map to the authorization domains.
Cluster Access Policies
Cluster access policies control which users and groups can connect to clusters. The principal is a Lattice::User or Lattice::Group, and the resource is a Lattice::Cluster.
// SRE team can access all production clusters
permit (
principal in Lattice::Group::"sre-team",
action == Lattice::Action::"AccessCluster",
resource
) when {
resource.environment == "production"
};
// Developers can access staging clusters in their region
permit (
principal in Lattice::Group::"developers",
action == Lattice::Action::"AccessCluster",
resource
) when {
resource.environment == "staging"
}; Secret Access Policies
Secret access policies control which services can retrieve secrets during compilation. The principal is a Lattice::Service and the resource is a Lattice::SecretPath. Use resource.path like for wildcard matching.
Namespace-Scoped Access
// Payments namespace services can access payments/* secrets
permit (
principal,
action == Lattice::Action::"AccessSecret",
resource
) when {
principal is Lattice::Service &&
principal.namespace == "payments" &&
resource.path like "secret/data/payments/*"
}; Provider Isolation
// Only platform namespace can use the vault-admin provider
forbid (
principal,
action == Lattice::Action::"AccessSecret",
resource
) when {
resource.provider == "vault-admin" &&
!(principal is Lattice::Service && principal.namespace == "platform")
}; Environment Boundaries
// Staging clusters cannot access production secrets
forbid (
principal,
action == Lattice::Action::"AccessSecret",
resource
) when {
resource.path like "secret/data/production/*"
}; Security Override Policies
Security override policies control which services can relax Pod Security Standards. The principal is a Lattice::Service and the resource is a Lattice::SecurityOverride.
Override types: capability:NET_ADMIN,
capability:SYS_MODULE,
privileged,
runAsRoot,
hostNetwork,
shareProcessNamespace
Specific Service Override
// Grant NET_ADMIN capability to the nzbget service for VPN sidecar
permit (
principal == Lattice::Service::"media/nzbget",
action == Lattice::Action::"OverrideSecurity",
resource == Lattice::SecurityOverride::"capability:NET_ADMIN"
); Namespace-Wide Override
// Legacy namespace gets broad security overrides
permit (
principal,
action == Lattice::Action::"OverrideSecurity",
resource
) when {
principal is Lattice::Service &&
principal.namespace == "legacy"
}; Category-Based Filtering
// Allow all capability overrides but forbid privileged mode
permit (
principal,
action == Lattice::Action::"OverrideSecurity",
resource
) when {
resource.category == "capability"
};
forbid (
principal,
action == Lattice::Action::"OverrideSecurity",
resource == Lattice::SecurityOverride::"privileged"
); Policy Inheritance
When propagate: true is set on a CedarPolicy, it is distributed to all child clusters in the hierarchy. Inherited policies receive the lattice.dev/inherited label on child clusters.
Distributed from parent clusters. Evaluated in a separate phase before local policies. Labeled with lattice.dev/inherited.
Defined directly on the cluster. Evaluated after inherited policies. Can further restrict or extend access within the inherited baseline.
apiVersion: lattice.dev/v1alpha1
kind: CedarPolicy
metadata:
name: secret-access-baseline
spec:
description: "Baseline secret access policies for all clusters"
policies: |
// Every service can read its own namespace secrets
permit (
principal,
action == Lattice::Action::"AccessSecret",
resource
) when {
principal is Lattice::Service &&
resource.path like "secret/data/" + principal.namespace + "/*"
};
priority: 0
propagate: true # distributed to all child clusters Evaluation Semantics
Cedar evaluation follows strict rules to produce deterministic authorization decisions.
If no policy matches, the request is denied. Access must be explicitly permitted.
If any forbid statement matches, the request is denied regardless of any permit statements.
Policies are evaluated in priority order (higher values first). Within the same priority, inherited policies are evaluated before local policies.
All matching policies are collected and evaluated together. The final decision is the aggregate result across all applicable policies.