From e37c3778cfd6a854f29a813cd035acf4803c4c56 Mon Sep 17 00:00:00 2001 From: Colin Barber Date: Fri, 27 Feb 2026 16:18:15 -0400 Subject: [PATCH] feat: add resource_type_slug to permissions, environment and organization roles --- src/workos/authorization.py | 14 ++++++ .../types/authorization/environment_role.py | 1 + .../types/authorization/organization_role.py | 1 + src/workos/types/authorization/permission.py | 1 + tests/test_authorization.py | 45 +++++++++++++++++++ tests/utils/fixtures/mock_environment_role.py | 1 + .../utils/fixtures/mock_organization_role.py | 1 + tests/utils/fixtures/mock_permission.py | 1 + 8 files changed, 65 insertions(+) diff --git a/src/workos/authorization.py b/src/workos/authorization.py index 6e12f035..7ade6d78 100644 --- a/src/workos/authorization.py +++ b/src/workos/authorization.py @@ -50,6 +50,7 @@ def create_permission( slug: str, name: str, description: Optional[str] = None, + resource_type_slug: Optional[str] = None, ) -> SyncOrAsync[Permission]: ... def list_permissions( @@ -133,6 +134,7 @@ def create_environment_role( slug: str, name: str, description: Optional[str] = None, + resource_type_slug: Optional[str] = None, ) -> SyncOrAsync[EnvironmentRole]: ... def list_environment_roles(self) -> SyncOrAsync[EnvironmentRoleList]: ... @@ -174,10 +176,13 @@ def create_permission( slug: str, name: str, description: Optional[str] = None, + resource_type_slug: Optional[str] = None, ) -> Permission: json: Dict[str, Any] = {"slug": slug, "name": name} if description is not None: json["description"] = description + if resource_type_slug is not None: + json["resource_type_slug"] = resource_type_slug response = self._http_client.request( AUTHORIZATION_PERMISSIONS_PATH, @@ -359,10 +364,13 @@ def create_environment_role( slug: str, name: str, description: Optional[str] = None, + resource_type_slug: Optional[str] = None, ) -> EnvironmentRole: json: Dict[str, Any] = {"slug": slug, "name": name} if description is not None: json["description"] = description + if resource_type_slug is not None: + json["resource_type_slug"] = resource_type_slug response = self._http_client.request( "authorization/roles", @@ -450,10 +458,13 @@ async def create_permission( slug: str, name: str, description: Optional[str] = None, + resource_type_slug: Optional[str] = None, ) -> Permission: json: Dict[str, Any] = {"slug": slug, "name": name} if description is not None: json["description"] = description + if resource_type_slug is not None: + json["resource_type_slug"] = resource_type_slug response = await self._http_client.request( AUTHORIZATION_PERMISSIONS_PATH, @@ -635,10 +646,13 @@ async def create_environment_role( slug: str, name: str, description: Optional[str] = None, + resource_type_slug: Optional[str] = None, ) -> EnvironmentRole: json: Dict[str, Any] = {"slug": slug, "name": name} if description is not None: json["description"] = description + if resource_type_slug is not None: + json["resource_type_slug"] = resource_type_slug response = await self._http_client.request( "authorization/roles", diff --git a/src/workos/types/authorization/environment_role.py b/src/workos/types/authorization/environment_role.py index a73d8ed5..750de5ca 100644 --- a/src/workos/types/authorization/environment_role.py +++ b/src/workos/types/authorization/environment_role.py @@ -9,6 +9,7 @@ class EnvironmentRole(WorkOSModel): name: str slug: str description: Optional[str] = None + resource_type_slug: str permissions: Sequence[str] type: Literal["EnvironmentRole"] created_at: str diff --git a/src/workos/types/authorization/organization_role.py b/src/workos/types/authorization/organization_role.py index 2e343ad6..dbece55d 100644 --- a/src/workos/types/authorization/organization_role.py +++ b/src/workos/types/authorization/organization_role.py @@ -9,6 +9,7 @@ class OrganizationRole(WorkOSModel): name: str slug: str description: Optional[str] = None + resource_type_slug: str permissions: Sequence[str] type: Literal["OrganizationRole"] created_at: str diff --git a/src/workos/types/authorization/permission.py b/src/workos/types/authorization/permission.py index 13f9d7a8..516d4f73 100644 --- a/src/workos/types/authorization/permission.py +++ b/src/workos/types/authorization/permission.py @@ -9,6 +9,7 @@ class Permission(WorkOSModel): slug: str name: str description: Optional[str] = None + resource_type_slug: str system: bool created_at: str updated_at: str diff --git a/tests/test_authorization.py b/tests/test_authorization.py index cd78a3e2..56b0f954 100644 --- a/tests/test_authorization.py +++ b/tests/test_authorization.py @@ -53,6 +53,7 @@ def test_create_permission( assert permission.id == "perm_01ABC" assert permission.slug == "documents:read" + assert permission.resource_type_slug == "organization" assert request_kwargs["method"] == "post" assert request_kwargs["url"].endswith("/authorization/permissions") assert request_kwargs["json"] == { @@ -60,6 +61,27 @@ def test_create_permission( "name": "Read Documents", } + def test_create_permission_with_resource_type_slug( + self, mock_permission, capture_and_mock_http_client_request + ): + request_kwargs = capture_and_mock_http_client_request( + self.http_client, mock_permission, 201 + ) + + syncify( + self.authorization.create_permission( + slug="documents:read", + name="Read Documents", + resource_type_slug="project", + ) + ) + + assert request_kwargs["json"] == { + "slug": "documents:read", + "name": "Read Documents", + "resource_type_slug": "project", + } + def test_create_permission_with_description( self, mock_permission, capture_and_mock_http_client_request ): @@ -205,6 +227,7 @@ def test_create_organization_role( assert role.id == "role_01ABC" assert role.type == "OrganizationRole" + assert role.resource_type_slug == "organization" assert request_kwargs["method"] == "post" assert request_kwargs["url"].endswith( "/authorization/organizations/org_01EHT88Z8J8795GZNQ4ZP1J81T/roles" @@ -366,10 +389,32 @@ def test_create_environment_role( assert role.id == "role_01DEF" assert role.type == "EnvironmentRole" + assert role.resource_type_slug == "organization" assert request_kwargs["method"] == "post" assert request_kwargs["url"].endswith("/authorization/roles") assert request_kwargs["json"] == {"slug": "member", "name": "Member"} + def test_create_environment_role_with_resource_type_slug( + self, mock_environment_role, capture_and_mock_http_client_request + ): + request_kwargs = capture_and_mock_http_client_request( + self.http_client, mock_environment_role, 201 + ) + + syncify( + self.authorization.create_environment_role( + slug="member", + name="Member", + resource_type_slug="project", + ) + ) + + assert request_kwargs["json"] == { + "slug": "member", + "name": "Member", + "resource_type_slug": "project", + } + def test_list_environment_roles( self, mock_environment_roles, capture_and_mock_http_client_request ): diff --git a/tests/utils/fixtures/mock_environment_role.py b/tests/utils/fixtures/mock_environment_role.py index 6063f3ff..b3914929 100644 --- a/tests/utils/fixtures/mock_environment_role.py +++ b/tests/utils/fixtures/mock_environment_role.py @@ -12,6 +12,7 @@ def __init__(self, id: str): name="Member", slug="member", description="Default environment member role", + resource_type_slug="organization", permissions=["documents:read"], type="EnvironmentRole", created_at=now, diff --git a/tests/utils/fixtures/mock_organization_role.py b/tests/utils/fixtures/mock_organization_role.py index f2b5ac8c..e66607e9 100644 --- a/tests/utils/fixtures/mock_organization_role.py +++ b/tests/utils/fixtures/mock_organization_role.py @@ -17,6 +17,7 @@ def __init__( name="Admin", slug="admin", description="Organization admin role", + resource_type_slug="organization", permissions=["documents:read", "documents:write"], type="OrganizationRole", created_at=now, diff --git a/tests/utils/fixtures/mock_permission.py b/tests/utils/fixtures/mock_permission.py index b1e639bf..277a4fd7 100644 --- a/tests/utils/fixtures/mock_permission.py +++ b/tests/utils/fixtures/mock_permission.py @@ -12,6 +12,7 @@ def __init__(self, id: str, slug: str = "documents:read"): slug=slug, name="Read Documents", description="Allows reading documents", + resource_type_slug="organization", system=False, created_at=now, updated_at=now,