Python bindings for Cedar, the open-source policy language for access control.
Project description
Cedar Python
Python bindings for Cedar, the open-source policy language for access control. This library lets you define, validate, and evaluate authorization policies directly from Python.
Installation
pip install cedar-python
Quick Start
from cedar import Authorizer, EntityUid, Policy, PolicySet, Request
# Create policies
policies = PolicySet('''
permit(principal == User::"alice", action == Action::"read", resource);
forbid(principal, action == Action::"delete", resource);
''')
# Create and evaluate a request
request = Request(
EntityUid("User", "alice"),
EntityUid("Action", "read"),
EntityUid("Document", "doc1"),
)
authorizer = Authorizer()
response = authorizer.is_authorized(request, policies)
print(response.allowed) # True
Core API
Entities
from cedar import Entity, EntityUid, Context
# Entity identifiers
uid = EntityUid("User", "alice")
uid.entity_type() # "User"
uid.id() # "alice"
# Entities with attributes and hierarchy
user = Entity(
uid=EntityUid("User", "alice"),
attrs={"email": "alice@example.com", "role": "admin"},
parents=[EntityUid("Group", "admins")]
)
# Context for requests
context = Context({"ip_address": "10.0.0.1", "authenticated": True})
Authorization
from cedar import Authorizer, Request, Response
# Authorizer with entity hierarchy
authorizer = Authorizer(entities=[user, group])
# Full request with context
request = Request(
principal=EntityUid("User", "alice"),
action=EntityUid("Action", "read"),
resource=EntityUid("Document", "doc1"),
context=Context({"time": "2024-01-01T00:00:00Z"})
)
response = authorizer.is_authorized(request, policies)
response.allowed # bool
response.decision # "Allow" or "Deny"
response.reason # Policy IDs that contributed to decision
response.errors # Any evaluation errors
Schema Validation
Validate entities, requests, and context against a schema:
from cedar import Authorizer, Context, EntityUid, Request, Schema
schema = Schema.from_json('''...''')
action = EntityUid("Action", "read")
# Validate context against schema (requires action to determine expected shape)
context = Context({"ip_address": "10.0.0.1"}, schema=schema, action=action)
# Validate request components against schema
request = Request(
principal=EntityUid("User", "alice"),
action=action,
resource=EntityUid("Document", "doc1"),
context=context,
schema=schema
)
# Validate entities when creating the authorizer
authorizer = Authorizer(entities=[user, doc], schema=schema)
# Validate request components using stored schema
authorizer.validate_request(principal, action, resource, context)
Dynamic Entity Management
Add, update, or remove entities in an existing authorizer:
from cedar import Authorizer, Entity, EntityUid
authorizer = Authorizer()
# Add a new entity (fails if entity already exists)
alice = Entity(EntityUid("User", "alice"), {"role": "admin"})
authorizer.add_entity(alice)
# Upsert an entity (adds or replaces existing)
alice_updated = Entity(EntityUid("User", "alice"), {"role": "user"})
authorizer.upsert_entity(alice_updated)
# Remove an entity by UID
authorizer.remove_entity(EntityUid("User", "alice"))
# With schema validation
schema = Schema.from_json('''...''')
authorizer = Authorizer(schema=schema)
doc = Entity(EntityUid("Document", "doc1"), {"owner": "alice"})
authorizer.add_entity(doc) # Validates against schema
Policies
from cedar import Policy, PolicySet
# Single policy
policy = Policy('permit(principal, action, resource);', id="policy1")
policy.id() # "policy1"
policy.effect() # "Permit"
policy.annotations() # {"id": "policy1"}
policy.to_cedar() # Formatted Cedar syntax
policy.to_json() # JSON representation
# Policy sets
policy_set = PolicySet('''
@id("read-access")
permit(principal, action == Action::"read", resource);
''')
policy_set.policies() # List of Policy objects
policy_set.policy("read-access") # Get by ID
len(policy_set) # Number of policies
Schemas
from cedar import Schema
# From JSON
schema = Schema.from_json('''{
"": {
"entityTypes": {"User": {}, "Document": {}},
"actions": {
"read": {"appliesTo": {"principalTypes": ["User"], "resourceTypes": ["Document"]}}
}
}
}''')
# From Cedar schema syntax
schema = Schema.from_cedarschema('''
entity User;
entity Document;
action read appliesTo { principal: User, resource: Document };
''')
schema.entity_types() # ["User", "Document"]
schema.actions() # ["read"]
schema.principals() # Entity types that can be principals
schema.resources() # Entity types that can be resources
Validation
Validate policies against a schema for type checking and error detection:
from cedar import PolicySet, Schema
# Create schema and policies
schema = Schema.from_cedarschema('''
entity User;
entity Document;
action read appliesTo { principal: User, resource: Document };
''')
policies = PolicySet('''
permit(principal == User::"alice", action == Action::"read", resource);
''')
# Validate policies against schema
result = schema.validate_policyset(policies)
result.valid # True if validation passed
result.errors # List of ValidationError objects
result.warnings # List of ValidationWarning objects
# ValidationError/ValidationWarning have policy_id and message attributes
for error in result.errors:
print(f"{error.policy_id}: {error.message}")
Schema Module
Pydantic models for building schemas programmatically:
from cedar.schema import CedarSchema, NamespaceDefinition, EntityType, Action, AppliesTo
schema = CedarSchema(root={
"": NamespaceDefinition(
entityTypes={"User": EntityType()},
actions={"read": Action(appliesTo=AppliesTo(principalTypes=["User"]))}
)
})
Lean Module (Formal Verification)
Symbolic policy analysis using cedar-lean-cli:
from cedar.lean import (
check_equivalent,
check_implies,
check_disjoint,
compare_policysets,
analyze_policies,
)
# Check if two policies are equivalent
result = check_equivalent(policy1, policy2, schema)
result.satisfied # True if equivalent
result.counterexample # Example where they differ (if not equivalent)
# Compare policy sets
comparison = compare_policysets(old_policies, new_policies, schema)
comparison.is_equivalent # True if all request signatures are equivalent
comparison.more_permissive # Request envs where source allows more
comparison.less_permissive # Request envs where source allows less
CLI
# Validate a policy against a schema
cedar schema validate policy.cedar schema.json
# Run the MCP server
cedar mcp
MCP Server
For AI coding assistants, Cedar provides an MCP server with policy tools:
pip install cedar-python[mcp]
cedar mcp
Available tools: validate_policy, validate_policy_set, validate_schema, format_policy
License
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distributions
Built Distributions
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file cedar_python-0.1.2-cp314-cp314-macosx_10_12_x86_64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp314-cp314-macosx_10_12_x86_64.whl
- Upload date:
- Size: 4.0 MB
- Tags: CPython 3.14, macOS 10.12+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
4742c9f548fa7f0958c4341f0230819f46a03d6f28d092b812e69b7b64a3ed4b
|
|
| MD5 |
84b1e2f2b3584f851b42d5cee03bc18c
|
|
| BLAKE2b-256 |
0ef4f5d23100ffcb62f9f075d168cf72fb8b083c7c273ee5df0a07e28a692508
|
File details
Details for the file cedar_python-0.1.2-cp313-cp313-win_amd64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp313-cp313-win_amd64.whl
- Upload date:
- Size: 3.7 MB
- Tags: CPython 3.13, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
ba111c448351521eebf2b3c310f3bdee15ab67617b13b11247922cb76b219537
|
|
| MD5 |
27ddab377a9efbc8d7966fb2f528017f
|
|
| BLAKE2b-256 |
5d0001056205b3206411389961a5ba9c45c3dc1e99c276d319c345c9f0877b6b
|
File details
Details for the file cedar_python-0.1.2-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
- Upload date:
- Size: 4.3 MB
- Tags: CPython 3.13, manylinux: glibc 2.17+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
01d15f0a8c5f842da3839a09df59df7b5a13bf43c5d29aa9f8bf8263bcc87d6a
|
|
| MD5 |
f86c81d5ef58ed716a8b571318975ab1
|
|
| BLAKE2b-256 |
a0012c22ea45d2142c01991075b5dcb092e75bd21821a69d473b8ec9a3b4c398
|
File details
Details for the file cedar_python-0.1.2-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
- Upload date:
- Size: 4.2 MB
- Tags: CPython 3.13, manylinux: glibc 2.17+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
fa2a016a38ab782d2abb9e05e01abb487ca7e6d8ec88cf89819e1efbbb82f2f4
|
|
| MD5 |
2843a7b2e1050d66602c1b94e6c17a8b
|
|
| BLAKE2b-256 |
83740d8b2f5e036f76ceeb6c928a164ffe8507493869d690c161ac2e918dfd12
|
File details
Details for the file cedar_python-0.1.2-cp313-cp313-macosx_11_0_arm64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp313-cp313-macosx_11_0_arm64.whl
- Upload date:
- Size: 3.8 MB
- Tags: CPython 3.13, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
aabbe0d2c2b7bbe8ecd583330229cb4fab778f7e8560e098b1d73fc07193a6e7
|
|
| MD5 |
e151b14538109524b312c46878be929d
|
|
| BLAKE2b-256 |
2a39113dead43eb17bd0aa01cfb27541462755440395a53509d3dcaf13c05a90
|
File details
Details for the file cedar_python-0.1.2-cp313-cp313-macosx_10_12_x86_64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp313-cp313-macosx_10_12_x86_64.whl
- Upload date:
- Size: 4.0 MB
- Tags: CPython 3.13, macOS 10.12+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0de1295618fc011331ccb0f939e9e8c710056f2d8413c7d5d5d0adbff12fba75
|
|
| MD5 |
e393f21c8c9d1a241e1f0e4e008ca417
|
|
| BLAKE2b-256 |
f76f31f00b7a7332a74d1207f355d4b674b4a5eb4f77bf8dd99c4fd7fc370808
|
File details
Details for the file cedar_python-0.1.2-cp312-cp312-win_amd64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp312-cp312-win_amd64.whl
- Upload date:
- Size: 3.7 MB
- Tags: CPython 3.12, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
27633cfe50b3a79ed4020cf884f3d1df0a2aef2fcd3638a218aea802c062c80c
|
|
| MD5 |
9a66f343a0d7932967483cde39cdc6e7
|
|
| BLAKE2b-256 |
e2e321dfb6256162ea2883b4d8b472006491b766005d8f0a4bdd3df9f4c400c8
|
File details
Details for the file cedar_python-0.1.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
- Upload date:
- Size: 4.3 MB
- Tags: CPython 3.12, manylinux: glibc 2.17+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a456d043bc9704fbf8c450bf0484c0b8378d7f2879bc34f34c6ee14601883ef6
|
|
| MD5 |
31f7bb20eb781f201eaaa808cb5e7e79
|
|
| BLAKE2b-256 |
bfd15d6f6f4ff0b03604a17d1790a1e81eb833d0800bb9deeff74a52452ae8c3
|
File details
Details for the file cedar_python-0.1.2-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
- Upload date:
- Size: 4.2 MB
- Tags: CPython 3.12, manylinux: glibc 2.17+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
912532b06633f94950b34fa2ce7e577a55af20bb8f54d6b52e1572cef60fcb17
|
|
| MD5 |
2cf29b37a3efd31de146950d5ebc9aca
|
|
| BLAKE2b-256 |
c2843a7203c412302c1a2622d8e82fccaa823c5875655a095810db35e38209c4
|
File details
Details for the file cedar_python-0.1.2-cp312-cp312-macosx_11_0_arm64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp312-cp312-macosx_11_0_arm64.whl
- Upload date:
- Size: 3.8 MB
- Tags: CPython 3.12, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
ecd87f82934363806dc9b2d707d7056dc8247f091d2e3723d758c45f45b63469
|
|
| MD5 |
9ea9016df16baf89255b809957c29247
|
|
| BLAKE2b-256 |
8b4eddd00519f403545480b375df76ee9a4cf343f9d92b11ce4dc1e3ad6a0f15
|
File details
Details for the file cedar_python-0.1.2-cp312-cp312-macosx_10_12_x86_64.whl.
File metadata
- Download URL: cedar_python-0.1.2-cp312-cp312-macosx_10_12_x86_64.whl
- Upload date:
- Size: 4.0 MB
- Tags: CPython 3.12, macOS 10.12+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: maturin/1.11.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
53269c65a6ca8e865479ac54efecb155e47b5c66e5c83193b6d23bc238f460e7
|
|
| MD5 |
3504d5381f9e08ffc7657d289cbe0dad
|
|
| BLAKE2b-256 |
4386e48f0167820cf44c3ae5963a69db7828bb215a6844785fe0078b427b9815
|