diff --git a/.github/workflows/main.yaml b/.github/workflows/main.yaml index a7d6cca4d..8dd157443 100644 --- a/.github/workflows/main.yaml +++ b/.github/workflows/main.yaml @@ -28,7 +28,7 @@ env: WEAVIATE_134: 1.34.19 WEAVIATE_135: 1.35.16-efdedfa WEAVIATE_136: 1.36.9-d905e6c - WEAVIATE_137: 1.37.0-rc.1-bc3891e + WEAVIATE_137: 1.37.1 jobs: lint-and-format: diff --git a/integration/test_rbac.py b/integration/test_rbac.py index d98d238a7..0f8657a2d 100644 --- a/integration/test_rbac.py +++ b/integration/test_rbac.py @@ -14,6 +14,7 @@ CollectionsPermissionOutput, DataPermissionOutput, GroupsPermissionOutput, + MCPPermissionOutput, NodesPermissionOutput, Role, ReplicatePermissionOutput, @@ -44,6 +45,7 @@ backups_permissions=[ BackupsPermissionOutput(collection="Test", actions={Actions.Backups.MANAGE}) ], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -62,6 +64,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -84,6 +87,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -104,6 +108,7 @@ DataPermissionOutput(collection="*", tenant="*", actions={Actions.Data.CREATE}) ], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -137,6 +142,7 @@ ), ], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -155,6 +161,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[ NodesPermissionOutput( verbosity="verbose", actions={Actions.Nodes.READ}, collection="Test" @@ -177,6 +184,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[ NodesPermissionOutput( verbosity="minimal", actions={Actions.Nodes.READ}, collection="*" @@ -203,6 +211,7 @@ ], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -221,6 +230,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[ TenantsPermissionOutput( @@ -247,6 +257,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[ TenantsPermissionOutput( @@ -290,6 +301,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -310,6 +322,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[ @@ -355,6 +368,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -379,6 +393,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -403,6 +418,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], @@ -410,6 +426,48 @@ ), 32, # Minimum version for alias permissions ), + ( + Permissions.mcp(create=True, read=True, update=True), + Role( + name="MCPAll", + alias_permissions=[], + cluster_permissions=[], + users_permissions=[], + collections_permissions=[], + roles_permissions=[], + data_permissions=[], + backups_permissions=[], + mcp_permissions=[ + MCPPermissionOutput( + actions={Actions.MCP.CREATE, Actions.MCP.READ, Actions.MCP.UPDATE} + ) + ], + nodes_permissions=[], + tenants_permissions=[], + replicate_permissions=[], + groups_permissions=[], + ), + 37, # Minimum version for MCP permissions + ), + ( + Permissions.mcp(read=True), + Role( + name="MCPRead", + alias_permissions=[], + cluster_permissions=[], + users_permissions=[], + collections_permissions=[], + roles_permissions=[], + data_permissions=[], + backups_permissions=[], + mcp_permissions=[MCPPermissionOutput(actions={Actions.MCP.READ})], + nodes_permissions=[], + tenants_permissions=[], + replicate_permissions=[], + groups_permissions=[], + ), + 37, # Minimum version for MCP permissions + ), ( Permissions.Groups.oidc(group="MyGroup", read=True), Role( @@ -421,6 +479,7 @@ roles_permissions=[], data_permissions=[], backups_permissions=[], + mcp_permissions=[], nodes_permissions=[], tenants_permissions=[], replicate_permissions=[], diff --git a/weaviate/rbac/models.py b/weaviate/rbac/models.py index df5a230a5..8e0989542 100644 --- a/weaviate/rbac/models.py +++ b/weaviate/rbac/models.py @@ -252,6 +252,16 @@ def values() -> List[str]: return [action.value for action in BackupsAction] +class MCPAction(str, _Action, Enum): + CREATE = "create_mcp" + READ = "read_mcp" + UPDATE = "update_mcp" + + @staticmethod + def values() -> List[str]: + return [action.value for action in MCPAction] + + class ReplicateAction(str, _Action, Enum): CREATE = "create_replicate" READ = "read_replicate" @@ -407,6 +417,16 @@ def _to_weaviate(self) -> List[WeaviatePermission]: ] +class _MCPPermission(_Permission[MCPAction]): + def _to_weaviate(self) -> List[WeaviatePermission]: + return [ + { + "action": action, + } + for action in self.actions + ] + + class _ClusterPermission(_Permission[ClusterAction]): def _to_weaviate(self) -> List[WeaviatePermission]: return [ @@ -470,6 +490,10 @@ class BackupsPermissionOutput(_BackupsPermission): pass +class MCPPermissionOutput(_MCPPermission): + pass + + class NodesPermissionOutput(_NodesPermission): pass @@ -486,6 +510,7 @@ class TenantsPermissionOutput(_TenantsPermission): RolesPermissionOutput, UsersPermissionOutput, BackupsPermissionOutput, + MCPPermissionOutput, NodesPermissionOutput, TenantsPermissionOutput, ReplicatePermissionOutput, @@ -507,6 +532,7 @@ class Role(RoleBase): roles_permissions: List[RolesPermissionOutput] users_permissions: List[UsersPermissionOutput] backups_permissions: List[BackupsPermissionOutput] + mcp_permissions: List[MCPPermissionOutput] nodes_permissions: List[NodesPermissionOutput] tenants_permissions: List[TenantsPermissionOutput] replicate_permissions: List[ReplicatePermissionOutput] @@ -522,6 +548,7 @@ def permissions(self) -> List[PermissionsOutputType]: permissions.extend(self.roles_permissions) permissions.extend(self.users_permissions) permissions.extend(self.backups_permissions) + permissions.extend(self.mcp_permissions) permissions.extend(self.nodes_permissions) permissions.extend(self.tenants_permissions) permissions.extend(self.replicate_permissions) @@ -537,6 +564,7 @@ def _from_weaviate_role(cls, role: WeaviateRole) -> "Role": roles_permissions: List[RolesPermissionOutput] = [] data_permissions: List[DataPermissionOutput] = [] backups_permissions: List[BackupsPermissionOutput] = [] + mcp_permissions: List[MCPPermissionOutput] = [] nodes_permissions: List[NodesPermissionOutput] = [] tenants_permissions: List[TenantsPermissionOutput] = [] replicate_permissions: List[ReplicatePermissionOutput] = [] @@ -605,6 +633,10 @@ def _from_weaviate_role(cls, role: WeaviateRole) -> "Role": actions={BackupsAction(permission["action"])}, ) ) + elif permission["action"] in MCPAction.values(): + mcp_permissions.append( + MCPPermissionOutput(actions={MCPAction(permission["action"])}) + ) elif permission["action"] in NodesAction.values(): nodes = permission.get("nodes") if nodes is not None: @@ -658,6 +690,7 @@ def _from_weaviate_role(cls, role: WeaviateRole) -> "Role": groups_permissions=_join_permissions(groups_permissions), data_permissions=_join_permissions(data_permissions), backups_permissions=_join_permissions(backups_permissions), + mcp_permissions=_join_permissions(mcp_permissions), nodes_permissions=_join_permissions(nodes_permissions), tenants_permissions=_join_permissions(tenants_permissions), replicate_permissions=_join_permissions(replicate_permissions), @@ -710,6 +743,7 @@ class Actions: Cluster = ClusterAction Nodes = NodesAction Backups = BackupsAction + MCP = MCPAction Tenants = TenantsAction Users = UsersAction Replicate = ReplicateAction @@ -1020,6 +1054,21 @@ def backup( permissions.append(permission) return permissions + @staticmethod + def mcp( + *, create: bool = False, read: bool = False, update: bool = False + ) -> PermissionsCreateType: + actions: Set[MCPAction] = set() + if create: + actions.add(MCPAction.CREATE) + if read: + actions.add(MCPAction.READ) + if update: + actions.add(MCPAction.UPDATE) + if len(actions) > 0: + return [_MCPPermission(actions=actions)] + return [] + @staticmethod def cluster(*, read: bool = False) -> PermissionsCreateType: if read: