Files
cyclone/backend/tests/test_auth_permissions_matrix.py
Nora cc02cb99c5 fix(sp37-followup): remove dead /api/resubmit permissions entry
Followup #1 from the SP37 final-state tracker. The pre-existing
('POST', '/api/resubmit'): WRITE_ROLES entry only matched the exact
path /api/resubmit (no children — the prefix-match logic requires
the trailing slash for sub-paths). No route is registered at that
path; the actual resubmit lives at /api/inbox/rejected/resubmit
(which has its own entry).

Removing the dead entry is fail-closed: any future request to
/api/resubmit (or its descendants) returns None from allowed_roles,
which means deny. Without this cleanup, the matrix silently granted
WRITE_ROLES to a non-existent route.

Tests (test_auth_permissions_matrix.py, 5 cases):
  * Exact path /api/resubmit not in PERMISSIONS
  * allowed_roles('POST', '/api/resubmit') is None
  * /api/resubmit/, /api/resubmit/anything all deny

Pin the invariant so a future contributor can't re-add a dead prefix.

TDD: tests written first, watched fail (5 fail with the dead entry),
removed the line, tests pass (5 pass). Full SP37 chain (36 tests)
passes with the change.
2026-07-07 12:17:14 -06:00

50 lines
1.9 KiB
Python

"""SP37 follow-up #1: Fail-closed for unregistered paths.
The permissions matrix is fail-closed — endpoints not listed are denied
(None). The pre-existing ``("POST", "/api/resubmit"): WRITE_ROLES``
entry was a dead prefix that ONLY matched the exact path ``/api/resubmit``
(which is not a registered route). The actual resubmit lives at
``/api/inbox/rejected/resubmit`` (already covered by its own entry).
This test pins the fail-closed invariant: ``/api/resubmit`` MUST have
no granted permission because no route is registered there. Without
this test, a future contributor could re-add the dead entry (or any
similar dead prefix) and the auth system would silently grant access
to a non-existent path.
"""
from __future__ import annotations
import pytest
from cyclone.auth.permissions import PERMISSIONS, allowed_roles
def test_api_resubmit_exact_path_not_in_matrix():
"""``/api/resubmit`` (exact, no children) must NOT be in the matrix.
The actual resubmit endpoint is ``/api/inbox/rejected/resubmit``,
which has its own entry. The pre-existing
``("POST", "/api/resubmit"): WRITE_ROLES`` entry only matched the
exact path ``/api/resubmit`` and never any real route.
"""
assert ("POST", "/api/resubmit") not in PERMISSIONS
def test_api_resubmit_returns_none_via_allowed_roles():
"""Fail-closed: ``allowed_roles("POST", "/api/resubmit")`` is None.
The matrix default is DENY. A registered entry that matches the
path would return a non-empty set of roles; the absence of any
entry should return None.
"""
assert allowed_roles("POST", "/api/resubmit") is None
@pytest.mark.parametrize("path", [
"/api/resubmit",
"/api/resubmit/",
"/api/resubmit/anything",
])
def test_api_resubmit_prefix_variants_all_deny(path):
"""No path under ``/api/resubmit`` should match any permission entry."""
assert allowed_roles("POST", path) is None