Skip to content

find_superseded_score_set_tail returns a score set it never checked permission on #856

Description

@bencap

find_superseded_score_set_tail in lib/score_sets.py walks forward to the end of the supersession chain, and when the next score set in the chain fails the permission check it returns the current score set directly:

if action is not None and not has_permission(user_data, next_score_set_in_chain, action).permitted:
    return score_set

The score set it returns is never itself checked against action. The check below the loop — the one that walks back through superseded_score_set looking for something the caller may see — is skipped entirely on that path.

Not reachable on current data, since a score set must be published before it can be superseded, so any score set with a superseding_score_set is public and passes READ. It becomes reachable the moment supersession is permitted on a private score set, and the failure mode is a silently widened read rather than an error.

Proposed behavior

break instead of return score_set, so the path falls through to the permission check below the loop and the backward walk applies.

Acceptance criteria

  • a caller with no permission on any score set in the chain receives None
  • a caller permitted on an earlier link receives that link, not an unchecked one
  • a test covers a private score set carrying a superseding_score_set the caller cannot read

Metadata

Metadata

Assignees

No one assigned

    Labels

    app: backendTask implementation touches the backend

    Type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions