Files
govoplan-policy/tests/test_definition_governance.py

148 lines
4.5 KiB
Python

from __future__ import annotations
import unittest
from govoplan_core.core.access import PrincipalRef
from govoplan_core.core.policy import (
DefinitionGovernanceRequest,
DefinitionScopeRef,
)
from govoplan_policy.backend.definition_governance import (
DefinitionGovernancePolicyProvider,
)
class DefinitionGovernancePolicyTests(unittest.TestCase):
def setUp(self) -> None:
self.policy = DefinitionGovernancePolicyProvider()
self.actor = PrincipalRef(
account_id="account-1",
membership_id="user-1",
tenant_id="tenant-1",
group_ids=frozenset({"group-1"}),
)
def _resolve(self, **overrides):
values = {
"module_id": "dataflow",
"definition_ref": "pipeline:1",
"tenant_id": "tenant-1",
"definition_scope": DefinitionScopeRef(
"tenant",
"tenant-1",
),
"target_scope": DefinitionScopeRef("tenant", "tenant-1"),
"definition_kind": "flow",
"action": "view",
"actor": self.actor,
"status": "active",
"inherit_to_lower_scopes": False,
"allow_run": True,
"allow_reuse": False,
"allow_automation": False,
}
values.update(overrides)
return self.policy.resolve_definition_action(
request=DefinitionGovernanceRequest(**values)
)
def test_system_definition_is_read_only_when_inherited(self) -> None:
view = self._resolve(
definition_scope=DefinitionScopeRef("system"),
inherit_to_lower_scopes=True,
)
edit = self._resolve(
definition_scope=DefinitionScopeRef("system"),
inherit_to_lower_scopes=True,
action="edit",
)
self.assertTrue(view.allowed)
self.assertFalse(edit.allowed)
self.assertEqual(
["system", "tenant:tenant-1"],
[step.path for step in view.source_path],
)
def test_templates_cannot_run_or_be_automated(self) -> None:
run = self._resolve(
definition_kind="template",
action="run",
allow_run=True,
)
automated = self._resolve(
definition_kind="template",
action="automate",
allow_run=True,
allow_automation=True,
)
self.assertFalse(run.allowed)
self.assertFalse(automated.allowed)
def test_reuse_and_automation_are_independent_narrowing_grants(self) -> None:
reuse = self._resolve(action="reuse", allow_reuse=True)
automated = self._resolve(
action="automate",
allow_run=True,
allow_automation=False,
)
self.assertTrue(reuse.allowed)
self.assertFalse(automated.allowed)
def test_ancestor_limits_cannot_be_broadened(self) -> None:
decision = self._resolve(
action="reuse",
allow_reuse=True,
context={
"ancestor_limits": {"allow_reuse": False},
"ancestor_source": {
"scope_type": "system",
"label": "System template",
},
},
)
self.assertFalse(decision.allowed)
self.assertFalse(
decision.details["effective_limits"]["allow_reuse"]
)
self.assertEqual("system", decision.source_path[0].path)
def test_ancestor_inheritance_limit_controls_visibility(self) -> None:
decision = self._resolve(
definition_scope=DefinitionScopeRef("system"),
inherit_to_lower_scopes=True,
context={
"ancestor_limits": {
"inherit_to_lower_scopes": False,
},
"ancestor_source": {
"scope_type": "system",
"label": "Restricted ancestor",
},
},
)
self.assertFalse(decision.allowed)
self.assertEqual(
"The system definition is not inherited by lower scopes.",
decision.reason,
)
def test_group_and_user_scopes_are_visible_only_to_the_actor(self) -> None:
group = self._resolve(
definition_scope=DefinitionScopeRef("group", "group-1")
)
user = self._resolve(
definition_scope=DefinitionScopeRef("user", "user-2")
)
self.assertTrue(group.allowed)
self.assertFalse(user.allowed)
if __name__ == "__main__":
unittest.main()