Skip to content

feat(connectors)!: AAuth connectors with Cedar policy entities, and member policy attributes - #171

Merged
brightsparc merged 3 commits into
mainfrom
feat/aauth-policy-fields
Oct 14, 2026
Merged

brightsparc merged 3 commits into
mainfrom
feat/aauth-policy-fields

Conversation

@brightsparc

@brightsparc brightsparc commented Oct 14, 2026 •

Copy link
Copy Markdown
Contributor

What changed

  • ConnectorAuthMode.AAUTH (aauth). An aauth connector sets person_server_url and application_id; the server validates both.
  • Connectors carry policy_entities on read (Connector), create (ConnectorCreateRequest / connectors.create) and update (ConnectorUpdateRequest / connectors.update), sync and async. They are typed as PolicyEntity (uid: EntityUid, attrs: dict[str, Any] = {}, parents: list[EntityUid] = []), which is Cedar's JSON entity format. Callers can pass the models or plain dicts.
  • Members carry policy_attributes: dict[str, Any] | None on read (Member), create and update (MemberUpdateRequest / members.update), sync and async. Values may reference an entity as {"__entity": {"type": ..., "id": ...}}.
  • members.create() takes either a BusinessMemberCreate (email and name required, plus optional role) or a CustomerMemberCreate (external_user_id of the form user:{id} or anon:{id}, optional name/email, no role). Customer creates are owner-only. Both carry tags, metadata and policy_attributes, and both refuse unknown fields. A plain dict is validated through the MemberCreate discriminated union, and a dict without member_type is a business member. member_type is always sent. This mirrors the Rust SDK's MemberCreateParams.

Why

This brings the SDK in line with the control plane's current API: introspection-cloud #3272 (AAuth connectors, policy entities, member policy attributes) and #3391 (policy_attributes on member create, pending). It is the Python counterpart of introspection-rust-sdk #115, and PolicyEntity / EntityUid mirror that SDK's types.

Breaking change

approval_policy and person_server_mode are removed from Connector, ConnectorCreateRequest and connectors.create(). The ConnectorApprovalPolicy and ConnectorPersonServerMode enums are removed as well. The control plane no longer accepts or returns these fields; Cedar entities and member attributes replace them. No backwards-compatibility shim is kept.

members.create() and AsyncMembers.create() no longer take keyword arguments. Pass a BusinessMemberCreate, a CustomerMemberCreate or a dict. MemberCreateRequest is replaced by BusinessMemberCreate, CustomerMemberCreate and the MemberCreate union.

Tests

New responses-style contract tests in tests/rest/test_connectors.py and tests/rest/test_members.py:

  • creating an aauth connector serializes typed policy_entities exactly, and dict input gets the defaults filled in
  • creating an aauth connector without a person server raises the server's 422 as ValidationError
  • reading a connector parses policy_entities, and a connector without them reads as None
  • updating a connector replaces policy_entities, sync and async
  • the removed fields are gone from all three connector models
  • member read, create and update carry policy_attributes, sync and async, and a 403 is surfaced
  • member create: a business create sends member_type: "business"; the customer body is serialized exactly; a dict without member_type is sent as business; a dict with member_type: "customer" works too
  • member create rejects these before any request is sent: a customer without external_user_id, a business member without email, a customer with role, and an unknown member_type

Results:

  • uv run pytest tests/ --cov=introspection_sdk: 761 passed, 93.38% coverage (floor 80%)
  • ruff format, ruff check and ty check pass
  • Pre-commit hooks pass on the changed files except the hook-pinned ty. That hook reports the same 36 diagnostics on untouched main files (otel, events, run-stream tests), none of them in files this PR changes.

🤖 Generated with Claude Code

…ember policy attributes

Match the control plane's connector and member API:

- ConnectorAuthMode gains `aauth`; an aauth connector names its
  person_server_url and application_id.
- Connectors carry `policy_entities`, typed as PolicyEntity / EntityUid
  (Cedar's JSON entity format), on read, create and update.
- Members carry `policy_attributes` on read, create and update.

BREAKING CHANGE: `approval_policy` and `person_server_mode` are removed
from Connector, ConnectorCreateRequest and `connectors.create()`, along
with the ConnectorApprovalPolicy and ConnectorPersonServerMode enums. The
control plane no longer accepts or returns either field; AAuth policy
(Cedar entities and member attributes) replaces them.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The control plane now lets an owner create a customer member by its
external_user_id. `members.create()` takes a BusinessMemberCreate or a
CustomerMemberCreate (or a plain dict validated through the same
discriminated union, where a missing member_type means business) and
always sends member_type, mirroring the Rust SDK's MemberCreateParams.
Both variants refuse unknown fields and carry policy_attributes.

BREAKING CHANGE: `members.create()` / `AsyncMembers.create()` no longer
take keyword arguments; pass a BusinessMemberCreate, a
CustomerMemberCreate or a dict. MemberCreateRequest is replaced by
BusinessMemberCreate, CustomerMemberCreate and the MemberCreate union.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@brightsparc
brightsparc merged commit f2c0510 into main Oct 14, 2026
5 checks passed
@brightsparc
brightsparc deleted the feat/aauth-policy-fields branch October 14, 2026 22:03

This branch was successfully deployed

1 active deployment
build — 55c00052 Deployed Oct 14, 2026 by brightsparc via Unit Tests #464
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant