From 91a85f7141af12e95a5c402d623ebe2a1845c8d3 Mon Sep 17 00:00:00 2001 From: shmyga Date: Sun, 2 Aug 2026 16:40:19 +0300 Subject: [PATCH] feat: add task tag --- project_manager/entry.py | 31 +++++++++++++++++++------------ project_manager/manager.py | 11 ++++------- project_manager/preset/entry.py | 6 +++--- project_manager/runner.py | 11 ++++++++--- 4 files changed, 34 insertions(+), 25 deletions(-) diff --git a/project_manager/entry.py b/project_manager/entry.py index 02d6e6a..d5dc20a 100644 --- a/project_manager/entry.py +++ b/project_manager/entry.py @@ -1,11 +1,11 @@ import logging from pathlib import Path -from typing import Iterable +from typing import Iterable, NamedTuple from .common.command import CommandExecutor __all__ = ( - "EntryTaskNotImplementedError", + "TaskKey", "Entry", "EntryDetector", "EntryResolver", @@ -14,8 +14,12 @@ __all__ = ( logger = logging.getLogger("entry") -class EntryTaskNotImplementedError(NotImplementedError): - pass +class TaskKey(NamedTuple): + name: str + tag: str + + def __repr__(self) -> str: + return f"{self.name}:{self.tag}" class Entry: @@ -23,7 +27,7 @@ class Entry: def __init__( self, - tasks: dict[str, list[str]], + tasks: dict[TaskKey, list[str]], basepath: Path, ): self._tasks = tasks @@ -36,15 +40,18 @@ class Entry: for command in commands: self._logger.debug(" %s", command) - def run_task(self, task_name: str): + def run_task(self, task_name: str, tag: str | None = None) -> bool: if task_name == "show": self.show() - return - if task_name not in self._tasks: - raise EntryTaskNotImplementedError(task_name) - self._logger.info("%s %s", task_name, self) - for command in self._tasks[task_name]: - CommandExecutor(command).run(self._basepath) + return True + runned = False + for task_key, commands in self._tasks.items(): + if task_key.name == task_name and (tag is None or tag == task_key.tag): + self._logger.info("%s %s", task_key, self) + runned = True + for command in commands: + CommandExecutor(command).run(self._basepath) + return runned def __repr__(self): return f"{str(self._basepath)}" diff --git a/project_manager/manager.py b/project_manager/manager.py index 268a83f..d249f8d 100644 --- a/project_manager/manager.py +++ b/project_manager/manager.py @@ -4,7 +4,7 @@ from pathlib import Path from typing import Iterable from .common.command import CommandError -from .entry import Entry, EntryResolver, EntryTaskNotImplementedError +from .entry import Entry, EntryResolver from .preset.entry import PresetEntryDetector __all__ = ("ProjectManager",) @@ -26,15 +26,12 @@ class ProjectManager: def _iter_entries(self) -> Iterable[Entry]: return self._resolver.resolve(self._basepaht) - def run_task(self, task_name: str) -> dict[str, int]: + def run_task(self, task_name: str, tag: str | None = None) -> dict[str, int]: counter = Counter() for entry in self._iter_entries(): try: - entry.run_task(task_name) - counter["success"] += 1 - except EntryTaskNotImplementedError: - self._logger.warning("%s %s", task_name, entry) - counter["skipped"] += 1 + if entry.run_task(task_name, tag): + counter["success"] += 1 except CommandError as error: self._logger.error("%s\n%s", entry, error.output) counter["failed"] += 1 diff --git a/project_manager/preset/entry.py b/project_manager/preset/entry.py index ee5253c..2a35afe 100644 --- a/project_manager/preset/entry.py +++ b/project_manager/preset/entry.py @@ -1,7 +1,7 @@ from collections import defaultdict from pathlib import Path -from ..entry import Entry, EntryDetector +from ..entry import Entry, EntryDetector, TaskKey from ..pipe.core import PipeParser, PipeRunner from .resolve import PresetResolver, PresetResolverConfig @@ -21,7 +21,7 @@ class PresetEntryDetector(EntryDetector): return None piperunner = PipeRunner(basepath) tasks = defaultdict(list) - for preset in preset.presets.values(): + for tag, preset in preset.presets.items(): if not piperunner.check_conditions(preset.conditions): continue for task_name, task_pack in preset.tasks.items(): @@ -37,7 +37,7 @@ class PresetEntryDetector(EntryDetector): for k, v in task.variables.items() } ) - tasks[task_name] += [ + tasks[TaskKey(task_name, tag)] += [ command.format(**variables) for command in task.commands ] if tasks: diff --git a/project_manager/runner.py b/project_manager/runner.py index 5d8f478..85aa672 100644 --- a/project_manager/runner.py +++ b/project_manager/runner.py @@ -9,9 +9,10 @@ from .manager import ProjectManager class ProjectManagerRunner: - def __init__(self, path: Path, task: str, verbose: int = 0): + def __init__(self, *, path: Path, task: str, tag: str | None, verbose: int = 0): self._path = path self._task = task + self._tag = tag self._verbose = verbose @classmethod @@ -38,7 +39,7 @@ class ProjectManagerRunner: def run(self): self._setup_logging(self._verbose) manager = ProjectManager(self._path) - result = manager.run_task(self._task) + result = manager.run_task(self._task, self._tag) if result["failed"] > 0: sys.exit(1) @@ -55,4 +56,8 @@ class ProjectManagerRunner: parser.add_argument("-q", "--quiet", action="store_true") args = parser.parse_args() verbose = -1 if args.quiet else args.verbose - return cls(args.path, args.task, verbose) + task = args.task + tag = None + if ":" in task: + task, tag = task.split(":") + return cls(path=args.path, task=task, tag=tag, verbose=verbose)