Skip to content

[feat] Extend access controls and billing settings#4330

Draft
junaway wants to merge 8 commits into
release/v0.99.8from
feat/add-access-controls-in-env-vars
Draft

[feat] Extend access controls and billing settings#4330
junaway wants to merge 8 commits into
release/v0.99.8from
feat/add-access-controls-in-env-vars

Conversation

@junaway
Copy link
Copy Markdown
Contributor

@junaway junaway commented May 14, 2026

No description provided.

Copilot AI review requested due to automatic review settings May 14, 2026 15:16
@vercel
Copy link
Copy Markdown

vercel Bot commented May 14, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
agenta-documentation Error Error May 14, 2026 3:52pm

Request Review

@dosubot dosubot Bot added size:XXL This PR changes 1000+ lines, ignoring generated files. Backend labels May 14, 2026
@junaway junaway changed the base branch from main to release/v0.99.8 May 14, 2026 15:16
@junaway junaway marked this pull request as draft May 14, 2026 15:17
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 14, 2026

Important

Review skipped

Draft detected.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 07d4d7b1-3273-43bc-85fc-d4b6dd349bf4

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/add-access-controls-in-env-vars

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR generalizes plan/role definitions from closed Python enums into runtime-configurable env vars (AGENTA_ACCESS_*, AGENTA_BILLING_*), splits the previous /admin/billing/usage/flush span retention endpoint into independent /admin/spans/flush and /admin/events/flush admin routers (each with its own service, DAO, cron, and Redis lock), and updates the frontend to treat plan slugs as plain strings while keeping a DefaultPlan enum for code-side conditionals. Backend Plan/WorkspaceRole enums are largely replaced with string slugs validated against the effective access-controls catalog at startup.

Changes:

  • New AccessControls/BillingSettings env layers parsed at startup with strict cross-reference validation; legacy STRIPE_PRICING removed and migration script provided.
  • New Counter.EVENTS plus EventsService/EventsDAO/EventsRouter/SpansRouter and events.sh cron; BillingRouter no longer owns retention.
  • Frontend Plan widened to string with DefaultPlan enum retained for known constants; updates to billing UI, banners, and useEntitlements.

Reviewed changes

Copilot reviewed 67 out of 72 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
api/oss/src/utils/env.py Adds AccessControls + BillingSettings env models with JSON loaders; drops StripeConfig.pricing.
api/ee/src/core/entitlements/types.py Renames PlanDefaultPlan, adds DefaultRole/Counter.EVENTS/Period; renames CATALOG/ENTITLEMENTS→DEFAULT_*.
api/ee/src/core/subscriptions/{settings,service,types}.py New billing settings module with strict validation; service uses dynamic free/trial accessors; types use string plans.
api/ee/src/core/entitlements/{service,controls(*not in diff)}.py Entitlements service consumes get_plan_entitlements.
api/ee/src/core/{events,tracing}/service.py New EventsService.flush_events; TracingService.flush_spans iterates dynamic plans.
api/ee/src/dbs/postgres/events/{init,dao}.py New EE retention DAO independent from OSS events DAO.
api/ee/src/apis/fastapi/{spans,events}/router.py New independent admin routers replacing /admin/billing/usage/flush.
api/ee/src/apis/fastapi/billing/router.py Drops tracing_service dep + flush endpoint; uses dynamic catalog/pricing/free-plan accessors.
api/ee/src/main.py Wires new spans/events services and routers.
api/ee/src/services/{throttling_service,workspace_manager,db_manager_ee,converters,admin_manager}.py Switch to controls accessors and string slugs.
api/ee/src/utils/{permissions,entitlements}.py Resolve role permissions and entitlements via controls module.
api/ee/src/routers/workspace_router.py Validates assigned role against effective workspace catalog.
api/ee/src/models/{db_models, api/api_models, api/workspace_models}.py Org-member default role memberviewer; widens role types to str.
api/ee/src/core/workspaces/types.py WorkspacePermission.role_name: str.
api/oss/src/core/{accounts,auth}/service.py, api/oss/src/routers/workspace_router.py Remove enum coupling; validate plan/role via EE controls.
api/ee/src/dbs/postgres/subscriptions/mappings.py Drop Plan enum coercion.
api/ee/databases/postgres/migrations/.../*.py Inline literal FREE_PLAN constants; new migration to unify memberviewer.
api/ee/src/crons/{spans.sh,events.sh,events.txt}, api/ee/docker/Dockerfile.{dev,gh}, hosting/docker-compose/ee/* Cron + image wiring for new events flush job and EE env examples.
api/ee/tests/pytest/unit/test_{access_controls,billing_settings,billing_router,controls_env_override,events_retention,admin_retention_routers}.py New/updated tests for parsers, env wiring, retention services, and admin routers.
docs/docs/self-host/{02-configuration,04-dynamic-access-controls,05-dynamic-billing-settings}.mdx Operator-facing documentation for the new env surface.
docs/designs/dynamic-access-and-billing/{research,gap,proposal,tasks,findings,migrate_stripe_pricing.py}.* Design folder + legacy STRIPE_PRICING converter.
docs/designs/data-retention/*, docs/design/ee-self-hosting/research.md, docs/openapi-cleanup/endpoints.md Updated to reference the split admin endpoints.
web/oss/src/lib/Types.ts, web/oss/src/lib/helpers/useEntitlements.ts Plan enum renamed PlanDefaultPlan; runtime plan typed as string.
web/ee/src/services/billing/types.d.ts, web/ee/src/components/SidebarBanners/state/atoms.ts, web/ee/src/components/pages/settings/Billing/* Frontend updated to use DefaultPlan constants and string plan slugs.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +90 to +94
`traces` and `events` are independent: each has its own counter, its own
retention period, its own admin flush endpoint (`/admin/spans/flush` and
`/admin/events/flush`), and its own cron schedule. Setting one does not
affect the other. The default for `events.retention` is `null` (kept
forever); opt in by setting it via overlay or full plan override.
Comment on lines +147 to +209
## `AGENTA_ACCESS_ROLES`

JSON **object** keyed by scope. Scope values are non-empty arrays of custom
role entries. The `owner` and `viewer` minima are platform-managed and
always synthesized for every scope — env can only **add** roles, never
redefine the minima.

### Top-level shape

```text
{
"<scope>": [<RoleEntry>, ...],
...
}
```

Recognized scopes: `organization`, `workspace`, `project`. Unknown scopes
fail startup. Omitted scopes keep their full code defaults.

### `RoleEntry` fields

| Field | Type | Required | Description |
|-------|------|----------|-------------|
| `role` | string | yes | Slug; cannot be `owner` or `viewer` (reserved). |
| `description` | string | no | Human-readable description for UIs. |
| `permissions` | string[] | yes | `Permission` enum slugs, or `"*"` for full access. |

### Platform minima (always present)

The platform always synthesizes `owner` and `viewer` in every scope. Their
permission sets are code-defined:

| Scope | `owner` | `viewer` |
|-------|---------|----------|
| `organization` | `["*"]` | `[]` (membership marker, no permissions) |
| `workspace` | `["*"]` | Read-only set (sourced from the code-default `WorkspaceRole.VIEWER`) |
| `project` | `["*"]` | Same read-only set |

Org-scope `viewer` having no permissions is intentional: organizations don't
have a permission concept today — `viewer` is purely a membership marker.

### Example

Add a `reviewer` role at the project scope:

```json
{
"project": [
{
"role": "reviewer",
"description": "Can inspect runs and annotate traces.",
"permissions": ["read_system", "view_evaluation_runs", "edit_annotations"]
}
]
}
```

After applying that override, `/workspace/roles/` and member serialization
return `owner`, `viewer`, and `reviewer` for the project scope. Workspace
and organization scopes are untouched.

The `permissions` array entries must be valid `Permission` enum members or
the wildcard `"*"`. Unknown permissions fail startup.
Copilot AI review requested due to automatic review settings May 14, 2026 15:50
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 241 out of 256 changed files in this pull request and generated 1 comment.

Comment on lines 89 to 92
OrganizationRole = Literal[
"owner",
"member",
"viewer",
]
@junaway junaway changed the title [fix] Extend access controls and billing settings to env vars (+ clean-up) [fix] Extend access controls and billing settings May 15, 2026
@junaway junaway changed the title [fix] Extend access controls and billing settings [feat] Extend access controls and billing settings May 15, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Backend size:XXL This PR changes 1000+ lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants