lablup / lablup/backend.ai

Stop project scope from cascading permissions into member users' virtual scopes

Open
#13,705 0 comments 0 reactions 0 assignees View on GitHub
Dominant language
Python
Stars
670
Forks
183
Avg merge
17h 7m
Merged PRs (30d)
358

Description

Permission cascade in the virtual scope model is expressed by a `scope -> VS_member` scope binding. The binding opens the whole target virtual scope, so it must only be created where a cascade is actually wanted.

### Requirement

Upper-scope permissions cascade downward, but the hierarchy is not a single chain:

- `domain -> project` — cascade required
- `domain -> user` — cascade required
- `project -> user` — cascade MUST NOT happen. Holding vfolder delete permission on a project must not allow deleting a member's personal vfolder.

### Current behavior

`RBACWriteOps.add_bulk_members` performs three writes per member: membership of the member entity in the scope's virtual scope, the legacy scope association, and `_bind_scope_to_member_vs`, which binds the enrolling scope into the member's own virtual scope. The same helper serves every enrollment, so project member enrollment also creates `project -> VS_user`. The project member enrollment path passes no permission_cap, so the binding has no ceiling.

Permission resolution walks `entity -> entity_memberships -> scope_bindings -> scope` and OR-combines the grant at every reachable scope. Once entities owned by a user are enrolled as members of their owner's virtual scope, an entity such as a personal vfolder resolves through VS_user to the bound project scope, and project-scope role permissions apply to it.

This does not leak today only because ordinary resource entities are not yet written into entity_memberships; the backfill migration would expose it.

### Decision

Do not create the `project -> VS_user` binding at all, rather than capping it. A project's visibility of its members is already satisfied by the member user entity being a membership of VS_project; the binding adds nothing for that purpose and additionally exposes everything else the user owns.

### Scope of work

- Separate the cascade binding from member enrollment so that creating it is an explicit decision per relation kind, not a side effect shared by every caller.
- Keep the binding for domain -> project and domain -> user; drop it for project -> user.
- Audit the remaining add_bulk_members callers (container registry, group, user, resource group) for which of them intend a cascade.
- Remove any project -> VS_user bindings already written, as part of the virtual scope backfill migration.
- Add regression coverage asserting that a project-scope grant does not resolve onto an entity owned by a member user.

JIRA Issue: BA-7327

Contributor guide

Open the contributing guide

Research direction

Start with RBACWriteOps.add_bulk_members and its _bind_scope_to_member_vs helper to trace each caller and relation kind. Review the virtual scope backfill migration and add regression coverage for project grants on member-owned entities. Done means domain cascades remain, project-to-user bindings are absent, existing bindings are removed, and the regression passes.

Written by the indexing model from the issue text.

Assessment

Tech stack
python
Domain
authorization, backend
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
52/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.