diff --git a/src/cleveragents/cli/commands/invariant.py b/src/cleveragents/cli/commands/invariant.py index f0c2541be..b80233905 100644 --- a/src/cleveragents/cli/commands/invariant.py +++ b/src/cleveragents/cli/commands/invariant.py @@ -20,7 +20,7 @@ Each invariant belongs to exactly one scope. Pass the matching flag: - ``--action ACTION``: Action-template invariant - ``--plan PLAN_ID``: Plan-specific invariant -Exactly one scope flag must be provided; commands error when omitted. +If no scope flag is given, ``--global`` is assumed. ## Examples @@ -81,18 +81,15 @@ def _resolve_scope( flags_set = sum( [is_global, project is not None, plan is not None, action is not None] ) - if flags_set == 0: - raise typer.BadParameter( - "Exactly one scope flag is required: " - "--global, --project, --plan, or --action" - ) if flags_set > 1: raise typer.BadParameter( - "Specify only one scope flag: --global, --project, --plan, or --action" + "Specify at most one scope flag: --global, --project, --plan, or --action" ) + # Explicit global check (handles the case where --global is set) if is_global: return InvariantScope.GLOBAL, "system" + if project is not None: return InvariantScope.PROJECT, project if plan is not None: @@ -100,10 +97,8 @@ def _resolve_scope( if action is not None: return InvariantScope.ACTION, action - # This line is unreachable because flags_set == 0 already raises BadParameter. - raise typer.BadParameter( - "Exactly one scope flag is required: --global, --project, --plan, or --action" - ) + # Default to global when no scope flag is provided + return InvariantScope.GLOBAL, "system" def _invariant_dict(inv: Invariant) -> dict[str, object]: @@ -190,20 +185,8 @@ def list_invariants( try: service = _get_service() - scope: InvariantScope | None = None - source_name: str | None = None - - if is_global: - scope = InvariantScope.GLOBAL - elif project is not None: - scope = InvariantScope.PROJECT - source_name = project - elif plan is not None: - scope = InvariantScope.PLAN - source_name = plan - elif action is not None: - scope = InvariantScope.ACTION - source_name = action + # Use shared scope resolver for consistent mutual-exclusion validation + scope, source_name = _resolve_scope(is_global, project, plan, action) invariants = service.list_invariants( scope=scope,