Source code for behave_priority.config

"""Immutable configuration for priority execution."""

from __future__ import annotations

from dataclasses import dataclass
from typing import Literal

ReportFormat = Literal["text", "json", "csv"]

_VALID_FORMATS: frozenset[str] = frozenset({"text", "json", "csv"})


[docs] @dataclass(frozen=True, slots=True) class PriorityConfig: """Immutable configuration for priority execution. All configuration is programmatic — no CLI flags. Attributes: order: Sort scenarios by priority (highest first). reverse: Reverse sort order (lowest priority first). priority_tag: Tag name to run first (e.g. ``"smoke"``). stop_after_failures: Stop after N failed scenarios, or None to disable. stop_on_critical: Stop if any critical scenario fails. critical_tag: Tag name that marks a scenario as critical. default_priority: Priority for scenarios without a priority tag. report: Print execution report after run. report_format: Output format for the report (``"text"``, ``"json"``, or ``"csv"``). parallel_coord: Enable cross-process fail-fast coordination via ``BEHAVE_PRIORITY_COORD_DIR`` env var. When True and the env var is set, workers share failure state via a file-based coordinator. Raises: ValueError: If ``stop_after_failures`` is not a positive integer (or None), if ``critical_tag`` or ``priority_tag`` is an empty string, if ``default_priority`` is negative, or if ``report_format`` is not one of ``"text"``, ``"json"``, ``"csv"``. """ order: bool = False reverse: bool = False priority_tag: str | None = None stop_after_failures: int | None = None stop_on_critical: bool = False critical_tag: str = "critical" default_priority: int = 999 report: bool = False report_format: ReportFormat = "text" parallel_coord: bool = False def __post_init__(self) -> None: """Validate configuration fields after initialization.""" if self.stop_after_failures is not None and self.stop_after_failures <= 0: raise ValueError( f"stop_after_failures must be a positive integer or None, " f"got {self.stop_after_failures}" ) if not self.critical_tag: raise ValueError("critical_tag must not be empty") if self.priority_tag is not None and not self.priority_tag: raise ValueError("priority_tag must not be empty if provided") if self.default_priority < 0: raise ValueError( f"default_priority must be non-negative, got {self.default_priority}" ) if self.report_format not in _VALID_FORMATS: raise ValueError( f"report_format must be one of 'text', 'json', 'csv', " f"got {self.report_format!r}" )