Set up a team with RBAC
Create a team, define roles with scoped permissions, and invite members.
What you’ll build
A team with role-based access control: an Admin with full access, a Pentester who can run pentests and triage findings, and a read-only Viewer. You will list the available permissions, attach them to roles, invite a member into each role, and share an agent with the team.
Roles bundle permission IDs under a name and color. Permissions are added to a role with
add_permissions; a member receives a role when invited, or later with
client.teams.roles.assign_to_member.
Prerequisites
- A Rank account that can create teams, and an API token (see Authentication).
pip install rank-sdk
export RANK_API_KEY=rk_...
Steps
-
Create the team.
team = client.teams.create( name="Red Team Alpha", description="Offensive security team for quarterly pentests.", ) -
List the platform permissions. Every permission has an
idand aname; you assign them to roles by ID.permissions = client.permissions.list().items all_ids = [p.id for p in permissions] -
Create roles. Give each role a name and color, then attach its permissions.
admin = client.teams.roles.create(team.id, role_name="Admin", color="#E74C3C") client.teams.roles.add_permissions(team.id, admin.id, permission_ids=all_ids) pentester = client.teams.roles.create(team.id, role_name="Pentester", color="#3498DB") client.teams.roles.add_permissions(team.id, pentester.id, permission_ids=all_ids[:6]) viewer = client.teams.roles.create(team.id, role_name="Viewer", color="#95A5A6") client.teams.roles.add_permissions(team.id, viewer.id, permission_ids=all_ids[:2]) -
Invite members. Pass a
role_idto assign the role on acceptance (the Administrator role cannot be granted by invitation).client.teams.invitations.create(team.id, email="pentester@example.com", role_id=pentester.id) -
See the team’s agents. List the agents available to the team — its own custom agents plus the defaults. Add a new shared agent with
client.teams.agents.create(name=..., instructions=..., agent_type=...).team_agents = client.teams.agents.list(team.id) print(len(team_agents.team_agents), "custom,", len(team_agents.default_agents), "default")
Run it
Save the following as team_rbac.py, set RANK_API_KEY, then run
python team_rbac.py.
"""Set up a team with role-based access control using the Rank SDK.
What this script does:
1. Creates a team.
2. Lists the permissions available on the platform.
3. Creates three roles with different permission levels:
- Admin : every permission.
- Pentester : run pentests and triage vulnerabilities.
- Viewer : read-only access.
4. Invites a member for each role.
5. Lists the agents available to the team (custom + default).
Roles map permission IDs to a name and color. Permissions are assigned to a
role with `add_permissions`; members receive a role when they are invited (or
later, with `client.teams.roles.assign_to_member`). A team gets its own shared
agents by creating them with `client.teams.agents.create(...)`.
Run:
pip install rank-sdk
export RANK_API_KEY=rk_...
python team_rbac.py
Optional environment variables:
RANK_TEAM_NAME Name for the new team (default: Red Team Alpha).
"""
from __future__ import annotations
import os
import rank
TEAM_NAME = os.environ.get("RANK_TEAM_NAME", "Red Team Alpha")
# Substrings used to pick a realistic subset of permissions for each role.
# Permission tags vary by account, so we match defensively and fall back to a
# slice of the catalog when nothing matches.
PENTESTER_KEYWORDS = ("pentest", "vulnerability", "agent", "chat")
VIEWER_KEYWORDS = ("view", "read", "list", "show")
def pick_permissions(permissions: list, keywords: tuple[str, ...], fallback: int) -> list[int]:
"""Return permission IDs whose name matches any keyword, else a fallback."""
matched = [
p.id for p in permissions
if any(k in (p.name or "").lower() for k in keywords)
]
return matched or [p.id for p in permissions[:fallback]]
def main() -> None:
with rank.Rank() as client:
team = client.teams.create(
name=TEAM_NAME,
description="Offensive security team for quarterly pentests.",
)
print(f"Created team #{team.id}: {team.name}")
permissions = client.permissions.list().items
all_ids = [p.id for p in permissions]
print(f"Platform exposes {len(all_ids)} permissions")
pentester_ids = pick_permissions(permissions, PENTESTER_KEYWORDS, fallback=6)
viewer_ids = pick_permissions(permissions, VIEWER_KEYWORDS, fallback=2)
roles = {
"Admin": ("#E74C3C", "Full access to every team resource.", all_ids),
"Pentester": ("#3498DB", "Run pentests and triage findings.", pentester_ids),
"Viewer": ("#95A5A6", "Read-only access to team resources.", viewer_ids),
}
created_roles = {}
for role_name, (color, description, permission_ids) in roles.items():
role = client.teams.roles.create(
team.id,
role_name=role_name,
color=color,
description=description,
)
client.teams.roles.add_permissions(
team.id, role.id, permission_ids=permission_ids,
)
created_roles[role_name] = role
print(f" Role {role_name} (#{role.id}): {len(permission_ids)} permissions")
invitations = [
("lead@example.com", created_roles["Admin"].id),
("pentester@example.com", created_roles["Pentester"].id),
("manager@example.com", created_roles["Viewer"].id),
]
for email, role_id in invitations:
try:
client.teams.invitations.create(team.id, email=email, role_id=role_id)
print(f" Invited {email} (role #{role_id})")
except rank.APIError as exc:
print(f" Could not invite {email}: {exc.message}")
# Review the agents available to the team. This returns the team's own
# custom agents plus the default agents everyone can use. Add a new
# shared agent with client.teams.agents.create(name=..., instructions=...,
# agent_type=..., phase_id=..., model_id=...).
team_agents = client.teams.agents.list(team.id)
print(f" Team agents: {len(team_agents.team_agents)} custom, "
f"{len(team_agents.default_agents)} default")
for agent in team_agents.team_agents[:5]:
print(f" [{agent.id}] {agent.name} ({agent.agent_type})")
print(f"\nTeam #{team.id} is ready. Manage it from the dashboard.")
if __name__ == "__main__":
try:
main()
except rank.AuthenticationError:
print("ERROR: invalid or missing API key. Set RANK_API_KEY.")
except rank.APIError as exc:
print(f"API error ({exc.status_code}): {exc.message}")
For the bigger picture on roles, permissions, and tiers, see Teams & tiers.