zrb 0.9.3__py3-none-any.whl → 0.10.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. zrb/__init__.py +2 -0
  2. zrb/builtin/generator/docker_compose_task/template/src/kebab-zrb-task-name/image/pyproject.toml +1 -1
  3. zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/loadtest/pyproject.toml +1 -1
  4. zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/pyproject.toml +1 -1
  5. zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/cmd/publish.sh +1 -1
  6. zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/local.py +1 -9
  7. zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/pyproject.toml +1 -1
  8. zrb/builtin/generator/plugin/template/_cmd/publish.sh +1 -1
  9. zrb/builtin/generator/plugin/template/pyproject.toml +1 -1
  10. zrb/builtin/generator/plugin/template/zrb_init.py +1 -9
  11. zrb/builtin/generator/project/template/pyproject.toml +1 -1
  12. zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/pyproject.toml +1 -1
  13. zrb/config/config.py +10 -7
  14. zrb/shell-scripts/ensure-podman-is-installed.sh +55 -0
  15. zrb/task/any_task.py +83 -0
  16. zrb/task/base_remote_cmd_task.py +2 -0
  17. zrb/task/base_task/base_task.py +53 -15
  18. zrb/task/base_task/component/base_task_model.py +2 -0
  19. zrb/task/base_task/component/common_task_model.py +26 -0
  20. zrb/task/checker.py +2 -0
  21. zrb/task/cmd_task.py +2 -0
  22. zrb/task/docker_compose_task.py +27 -21
  23. zrb/task/flow_task.py +2 -0
  24. zrb/task/http_checker.py +2 -0
  25. zrb/task/notifier.py +2 -0
  26. zrb/task/path_checker.py +2 -0
  27. zrb/task/path_watcher.py +2 -0
  28. zrb/task/port_checker.py +2 -0
  29. zrb/task/recurring_task.py +2 -0
  30. zrb/task/remote_cmd_task.py +2 -0
  31. zrb/task/resource_maker.py +2 -0
  32. zrb/task/rsync_task.py +2 -0
  33. zrb/task/time_watcher.py +2 -0
  34. zrb/task/wiki_task.py +119 -0
  35. {zrb-0.9.3.dist-info → zrb-0.10.0.dist-info}/METADATA +1 -1
  36. {zrb-0.9.3.dist-info → zrb-0.10.0.dist-info}/RECORD +39 -37
  37. {zrb-0.9.3.dist-info → zrb-0.10.0.dist-info}/LICENSE +0 -0
  38. {zrb-0.9.3.dist-info → zrb-0.10.0.dist-info}/WHEEL +0 -0
  39. {zrb-0.9.3.dist-info → zrb-0.10.0.dist-info}/entry_points.txt +0 -0
zrb/__init__.py CHANGED
@@ -28,6 +28,7 @@ from zrb.task.resource_maker import Replacement, ReplacementMutator, ResourceMak
28
28
  from zrb.task.rsync_task import RsyncTask
29
29
  from zrb.task.task import Task
30
30
  from zrb.task.time_watcher import TimeWatcher
31
+ from zrb.task.wiki_task import create_wiki_tasks
31
32
  from zrb.task_env.env import Env
32
33
  from zrb.task_env.env_file import EnvFile
33
34
  from zrb.task_group.group import Group
@@ -40,6 +41,7 @@ from zrb.task_input.password_input import PasswordInput
40
41
  from zrb.task_input.str_input import StrInput
41
42
  from zrb.task_input.task_input import Input
42
43
 
44
+ assert create_wiki_tasks
43
45
  assert runner
44
46
  assert AnyTask
45
47
  assert OnTriggered
@@ -13,7 +13,7 @@ uvicorn = "==0.20.0"
13
13
 
14
14
  [tool.poetry.dev-dependencies]
15
15
  flake8 = "~7.0.0"
16
- black = "~24.2.0"
16
+ black = "~24.3.0"
17
17
  isort = "~5.13.2"
18
18
  pytest = "~7.4.0"
19
19
  pytest-cov = "~4.1.0"
@@ -13,7 +13,7 @@ locust = "==2.16.1"
13
13
 
14
14
  [tool.poetry.dev-dependencies]
15
15
  flake8 = "~6.0.0"
16
- black = "~23.12.1"
16
+ black = "~24.3.0"
17
17
  isort = "~5.13.2"
18
18
 
19
19
  [build-system]
@@ -30,7 +30,7 @@ opentelemetry-instrumentation-fastapi= "==0.44b0"
30
30
 
31
31
  [tool.poetry.dev-dependencies]
32
32
  flake8 = "~7.0.0"
33
- black = "~24.2.0"
33
+ black = "~24.3.0"
34
34
  isort = "~5.13.2"
35
35
  pytest = "~7.4.0"
36
36
  pytest-cov = "~4.1.0"
@@ -1,2 +1,2 @@
1
1
  echo "Publish"
2
- poetry publish --repository {{input.snake_zrb_package_name_repo}}
2
+ poetry publish
@@ -1,6 +1,6 @@
1
1
  import os
2
2
 
3
- from zrb import CmdTask, StrInput, runner
3
+ from zrb import CmdTask, runner
4
4
  from zrb.builtin.group import project_group
5
5
 
6
6
  CURRENT_DIR = os.path.dirname(__file__)
@@ -49,14 +49,6 @@ publish_snake_zrb_package_name = CmdTask(
49
49
  name="publish-kebab-zrb-package-name",
50
50
  description="Publish human readable zrb package name",
51
51
  group=project_group,
52
- inputs=[
53
- StrInput(
54
- name="kebab-zrb-package-name-repo",
55
- prompt="Pypi repository for human readable zrb package name",
56
- description="Pypi repository for human readalbe zrb package name",
57
- default="pypi",
58
- )
59
- ],
60
52
  upstreams=[build_snake_zrb_package_name],
61
53
  cwd=RESOURCE_DIR,
62
54
  cmd_path=[
@@ -16,7 +16,7 @@ zrb = ">=zrbVersion"
16
16
 
17
17
  [tool.poetry.dev-dependencies]
18
18
  flake8 = "~7.0.0"
19
- black = "~24.2.0"
19
+ black = "~24.3.0"
20
20
  isort = "~5.13.2"
21
21
  pytest = "~7.4.0"
22
22
  pytest-cov = "~4.1.0"
@@ -1,2 +1,2 @@
1
1
  echo "Publish"
2
- poetry publish --repository {{input.plugin_repo}}
2
+ poetry publish
@@ -16,7 +16,7 @@ zrb = ">=zrbVersion"
16
16
 
17
17
  [tool.poetry.dev-dependencies]
18
18
  flake8 = "~7.0.0"
19
- black = "~24.2.0"
19
+ black = "~24.3.0"
20
20
  isort = "~5.13.2"
21
21
  pytest = "~7.4.0"
22
22
  pytest-cov = "~4.1.0"
@@ -1,6 +1,6 @@
1
1
  import os
2
2
 
3
- from zrb import CmdTask, StrInput, runner
3
+ from zrb import CmdTask, runner
4
4
  from zrb.builtin.group import plugin_group
5
5
 
6
6
  PROJECT_DIR = os.path.dirname(__file__)
@@ -46,14 +46,6 @@ publish_plugin = CmdTask(
46
46
  name="publish",
47
47
  group=plugin_group,
48
48
  description="Publish plugin",
49
- inputs=[
50
- StrInput(
51
- name="plugin-repo",
52
- prompt="Pypi repository for plugin",
53
- description="Pypi repository for human readalbe zrb package name",
54
- default="pypi",
55
- )
56
- ],
57
49
  upstreams=[build_plugin],
58
50
  cwd=PROJECT_DIR,
59
51
  cmd_path=[
@@ -14,7 +14,7 @@ zrb = ">=zrbVersion"
14
14
 
15
15
  [tool.poetry.dev-dependencies]
16
16
  flake8 = "~7.0.0"
17
- black = "~24.2.0"
17
+ black = "~24.3.0"
18
18
  isort = "~5.13.2"
19
19
 
20
20
  [tool.poetry.scripts]
@@ -14,7 +14,7 @@ uvicorn = "==0.20.0"
14
14
 
15
15
  [tool.poetry.dev-dependencies]
16
16
  flake8 = "~7.0.0"
17
- black = "~24.2.0"
17
+ black = "~24.3.0"
18
18
  isort = "~5.13.2"
19
19
  pytest = "~7.4.0"
20
20
  pytest-cov = "~4.1.0"
zrb/config/config.py CHANGED
@@ -7,13 +7,7 @@ from zrb.helper.typecheck import typechecked
7
7
 
8
8
  @typechecked
9
9
  def get_version() -> str:
10
- try:
11
- return metadata.version("zrb")
12
- except metadata.PackageNotFoundError:
13
- import flit
14
-
15
- meta = flit.read_module_metadata("zrb")
16
- return str(meta["module"]["version"])
10
+ return metadata.version("zrb")
17
11
 
18
12
 
19
13
  @typechecked
@@ -24,6 +18,12 @@ def get_current_shell() -> str:
24
18
  return "bash"
25
19
 
26
20
 
21
+ def _get_valid_container_backend(container_backend: str) -> str:
22
+ if container_backend.lower().strip() == "podman":
23
+ return "podman"
24
+ return "docker"
25
+
26
+
27
27
  default_shell = os.getenv("ZRB_SHELL", get_current_shell())
28
28
  init_script_str = os.getenv("ZRB_INIT_SCRIPTS", "")
29
29
  init_scripts = init_script_str.split(":") if init_script_str != "" else []
@@ -34,3 +34,6 @@ show_advertisement = to_boolean(os.getenv("ZRB_SHOW_ADVERTISEMENT", "1"))
34
34
  show_prompt = to_boolean(os.getenv("ZRB_SHOW_PROMPT", "1"))
35
35
  show_time = to_boolean(os.getenv("ZRB_SHOW_TIME", "1"))
36
36
  version = get_version()
37
+ container_backend = _get_valid_container_backend(
38
+ os.getenv("ZRB_CONTAINER_BACKEND", "docker")
39
+ )
@@ -0,0 +1,55 @@
1
+ set -e
2
+ if command_exists podman
3
+ then
4
+ log_info "Podman is already installed."
5
+ else
6
+ log_info "Installing Podman..."
7
+ if [ "$OS_TYPE" = "Darwin" ]
8
+ then
9
+ if command_exists brew
10
+ then
11
+ brew install --cask podman
12
+ log_info "Please start Podman before proceeding."
13
+ else
14
+ log_info "Homebrew not found. Please install Homebrew and try again."
15
+ exit 1
16
+ fi
17
+ elif [ "$OS_TYPE" = "Linux" ]
18
+ then
19
+ if command_exists apt
20
+ then
21
+ try_sudo apt update
22
+ try_sudo apt install -y podman
23
+ elif command_exists yum
24
+ then
25
+ try_sudo yum install -y podman
26
+ elif command_exists dnf
27
+ then
28
+ try_sudo dnf install -y podman
29
+ elif command_exists pacman
30
+ then
31
+ try_sudo pacman -Syu --noconfirm podman
32
+ else
33
+ log_info "No known package manager found. Please install Podman manually."
34
+ exit 1
35
+ fi
36
+ else
37
+ log_info "Unsupported OS type. Please install Podman manually."
38
+ exit 1
39
+ fi
40
+ fi
41
+
42
+ if ! command_exists podman-compose
43
+ then
44
+ log_info "Installing Podman Compose plugin..."
45
+ pip install podman-compose
46
+ fi
47
+
48
+ # Check Podman Compose plugin installation
49
+ if command_exists podman && command_exists podman-compose
50
+ then
51
+ log_info "Podman Compose plugin is already installed."
52
+ else
53
+ log_info "Podman Compose plugin is not installed or podman is not running. Please check your installation."
54
+ exit 1
55
+ fi
zrb/task/any_task.py CHANGED
@@ -384,6 +384,44 @@ class AnyTask(ABC):
384
384
  """
385
385
  pass
386
386
 
387
+ @abstractmethod
388
+ def insert_fallback(self, *fallbacks: TAnyTask):
389
+ """
390
+ Inserts one or more `AnyTask` instances at the beginning of the current task's fallback list.
391
+
392
+ This method is used to define dependencies for the current task. Tasks in the fallback list are executed when the task is failed.
393
+ Adding a task to the beginning of the list means it will be
394
+ executed earlier than those already in the list.
395
+
396
+ Args:
397
+ fallbacks (TAnyTask): One or more task instances to be added to the fallback list.
398
+
399
+ Examples:
400
+ >>> from zrb import Task
401
+ >>> task = Task(name='task')
402
+ >>> fallback_task = Task(name='fallback-task')
403
+ >>> task.insert_fallback(fallback_task)
404
+ """
405
+ pass
406
+
407
+ @abstractmethod
408
+ def add_fallback(self, *fallbacks: TAnyTask):
409
+ """
410
+ Adds one or more `AnyTask` instances to the end of the current task's fallback list.
411
+
412
+ This method appends tasks to the fallback list, indicating that these tasks should be executed when the task is failed.
413
+
414
+ Args:
415
+ fallbacks (TAnyTask): One or more task instances to be added to the fallback list.
416
+
417
+ Examples:
418
+ >>> from zrb import Task
419
+ >>> task = Task(name='task')
420
+ >>> fallback_task = Task(name='fallback-task')
421
+ >>> task.add_fallback(fallback_task)
422
+ """
423
+ pass
424
+
387
425
  @abstractmethod
388
426
  def add_upstream(self, *upstreams: TAnyTask):
389
427
  """
@@ -519,6 +557,20 @@ class AnyTask(ABC):
519
557
  """
520
558
  pass
521
559
 
560
+ @abstractmethod
561
+ def _lock_upstreams(self):
562
+ """
563
+ Lock upstreams so that it cannot be altered anymore
564
+ """
565
+ pass
566
+
567
+ @abstractmethod
568
+ def _lock_fallbacks(self):
569
+ """
570
+ Lock fallbacks so that it cannot be altered anymore
571
+ """
572
+ pass
573
+
522
574
  @abstractmethod
523
575
  def _set_execution_id(self, execution_id: str):
524
576
  """
@@ -885,6 +937,37 @@ class AnyTask(ABC):
885
937
  """
886
938
  pass
887
939
 
940
+ @abstractmethod
941
+ def inject_fallbacks(self):
942
+ """
943
+ Injects fallback tasks into the current task.
944
+
945
+ This method is used for programmatically adding fallback to the task.
946
+ fallback tasks are those that must be completed when the task is failed.
947
+ Override this method in subclasses to specify such dependencies.
948
+
949
+ Examples:
950
+ >>> from zrb import Task
951
+ >>> class MyTask(Task):
952
+ >>> def inject_fallbacks(self):
953
+ >>> self.add_fallback(another_task)
954
+ """
955
+ pass
956
+
957
+ @abstractmethod
958
+ def _get_fallbacks(self) -> Iterable[TAnyTask]:
959
+ """
960
+ Retrieves the fallback tasks of the current task.
961
+
962
+ An internal method to get the list of fallback tasks that have been set for the
963
+ task, either statically or through `inject_fallbacks`. This is essential for task
964
+ fallback scenario.
965
+
966
+ Returns:
967
+ Iterable[TAnyTask]: An iterable of fallback tasks.
968
+ """
969
+ pass
970
+
888
971
  @abstractmethod
889
972
  def _get_combined_inputs(self) -> Iterable[AnyInput]:
890
973
  """
@@ -78,6 +78,7 @@ class SingleBaseRemoteCmdTask(CmdTask):
78
78
  post_cmd_path: CmdVal = "",
79
79
  cwd: Optional[Union[str, pathlib.Path]] = None,
80
80
  upstreams: Iterable[AnyTask] = [],
81
+ fallbacks: Iterable[AnyTask] = [],
81
82
  on_triggered: Optional[OnTriggered] = None,
82
83
  on_waiting: Optional[OnWaiting] = None,
83
84
  on_skipped: Optional[OnSkipped] = None,
@@ -110,6 +111,7 @@ class SingleBaseRemoteCmdTask(CmdTask):
110
111
  cmd_path=cmd_path,
111
112
  cwd=cwd,
112
113
  upstreams=upstreams,
114
+ fallbacks=fallbacks,
113
115
  on_triggered=on_triggered,
114
116
  on_waiting=on_waiting,
115
117
  on_skipped=on_skipped,
@@ -39,6 +39,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
39
39
  """
40
40
 
41
41
  __xcom: Mapping[str, Mapping[str, str]] = {}
42
+ __running_tasks: List[AnyTask] = []
42
43
 
43
44
  def __init__(
44
45
  self,
@@ -53,6 +54,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
53
54
  retry: int = 2,
54
55
  retry_interval: Union[float, int] = 1,
55
56
  upstreams: Iterable[AnyTask] = [],
57
+ fallbacks: Iterable[AnyTask] = [],
56
58
  checkers: Iterable[AnyTask] = [],
57
59
  checking_interval: Union[float, int] = 0,
58
60
  run: Optional[Callable[..., Any]] = None,
@@ -87,6 +89,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
87
89
  retry=retry,
88
90
  retry_interval=retry_interval,
89
91
  upstreams=upstreams,
92
+ fallbacks=fallbacks,
90
93
  checkers=checkers,
91
94
  checking_interval=checking_interval,
92
95
  run=run,
@@ -257,7 +260,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
257
260
  except Exception as e:
258
261
  self.log_error(f"{e}")
259
262
  if raise_error:
260
- raise
263
+ raise e
261
264
  finally:
262
265
  if show_done_info:
263
266
  self._show_env_prefix()
@@ -303,7 +306,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
303
306
  self.log_debug("Waiting execution to be started")
304
307
  while not self.__is_execution_started:
305
308
  # Don't start checking before the execution itself has been started
306
- await asyncio.sleep(0.1)
309
+ await asyncio.sleep(0.05)
307
310
  check_coroutines: Iterable[asyncio.Task] = []
308
311
  for checker_task in self._get_checkers():
309
312
  checker_task._set_execution_id(self.get_execution_id())
@@ -334,15 +337,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
334
337
  await self.on_triggered()
335
338
  self.__is_execution_triggered = True
336
339
  await self.on_waiting()
337
- # get upstream checker
338
- upstream_check_processes: Iterable[asyncio.Task] = []
339
- self._lock_upstreams()
340
- for upstream_task in self._get_upstreams():
341
- upstream_check_processes.append(
342
- asyncio.create_task(upstream_task._loop_check())
343
- )
344
- # wait all upstream checkers to complete
345
- await asyncio.gather(*upstream_check_processes)
340
+ await self.__check_upstreams()
346
341
  # mark execution as started, so that checkers can start checking
347
342
  self.__is_execution_started = True
348
343
  local_kwargs = dict(kwargs)
@@ -353,27 +348,70 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
353
348
  return None
354
349
  # start running task
355
350
  result: Any = None
351
+ is_failed: bool = False
356
352
  while self._should_attempt():
357
353
  try:
358
354
  self.log_debug(f"Started with args: {args} and kwargs: {local_kwargs}")
359
355
  await self.on_started()
356
+ self.__running_tasks.append(self)
360
357
  result = await run_async(self.run, *args, **local_kwargs)
358
+ self.__running_tasks.remove(self)
361
359
  break
362
360
  except Exception as e:
363
- is_last_attempt = self._is_last_attempt()
364
- await self.on_failed(is_last_attempt, e)
365
- if is_last_attempt:
366
- raise e
367
361
  attempt = self._get_attempt()
368
362
  self.log_error(f"Encounter error on attempt {attempt}")
363
+ if self._is_last_attempt():
364
+ is_failed = True
365
+ raise e
366
+ self.__running_tasks.remove(self)
367
+ await self.on_failed(is_last_attempt=False, exception=e)
369
368
  self._increase_attempt()
370
369
  await asyncio.sleep(self._retry_interval)
371
370
  await self.on_retry()
371
+ finally:
372
+ if is_failed:
373
+ running_tasks = self.__running_tasks
374
+ self.__running_tasks = []
375
+ await self.__trigger_failure(running_tasks)
376
+ await self.__trigger_fallbacks(running_tasks, kwargs)
372
377
  self.set_xcom(self.get_name(), f"{result}")
373
378
  self.log_debug(f"XCom: {self.__xcom}")
374
379
  await self._mark_done()
375
380
  return result
376
381
 
382
+ async def __check_upstreams(self):
383
+ coroutines: Iterable[asyncio.Task] = []
384
+ self._lock_upstreams()
385
+ for upstream_task in self._get_upstreams():
386
+ coroutines.append(asyncio.create_task(upstream_task._loop_check()))
387
+ # wait all upstream checkers to complete
388
+ await asyncio.gather(*coroutines)
389
+
390
+ async def __trigger_failure(self, tasks: List[AnyTask]):
391
+ coroutines = [
392
+ task.on_failed(is_last_attempt=True, exception=Exception("canceled"))
393
+ for task in tasks
394
+ ]
395
+ await asyncio.gather(*coroutines)
396
+
397
+ async def __trigger_fallbacks(
398
+ self, tasks: List[AnyTask], kwargs: Mapping[str, Any]
399
+ ):
400
+ coroutines: Iterable[asyncio.Task] = []
401
+ for fallback in self.__get_all_fallbacks(tasks):
402
+ fallback._set_execution_id(self.get_execution_id())
403
+ coroutines.append(asyncio.create_task(fallback._run_all(**kwargs)))
404
+ await asyncio.gather(*coroutines)
405
+
406
+ def __get_all_fallbacks(self, tasks: List[AnyTask]) -> List[AnyTask]:
407
+ all_fallbacks: List[AnyTask] = []
408
+ for task in tasks:
409
+ task._lock_fallbacks()
410
+ for fallback in task._get_fallbacks():
411
+ if fallback not in all_fallbacks:
412
+ all_fallbacks.append(fallback)
413
+ return all_fallbacks
414
+
377
415
  async def _check_should_execute(self, *args: Any, **kwargs: Any) -> bool:
378
416
  if callable(self._should_execute):
379
417
  return await run_async(self._should_execute, *args, **kwargs)
@@ -56,6 +56,7 @@ class BaseTaskModel(CommonTaskModel, PidModel, TimeTracker):
56
56
  retry: int = 2,
57
57
  retry_interval: Union[int, float] = 1,
58
58
  upstreams: Iterable[AnyTask] = [],
59
+ fallbacks: Iterable[AnyTask] = [],
59
60
  checkers: Iterable[AnyTask] = [],
60
61
  checking_interval: Union[int, float] = 0,
61
62
  run: Optional[Callable[..., Any]] = None,
@@ -85,6 +86,7 @@ class BaseTaskModel(CommonTaskModel, PidModel, TimeTracker):
85
86
  retry=retry,
86
87
  retry_interval=retry_interval,
87
88
  upstreams=upstreams,
89
+ fallbacks=fallbacks,
88
90
  checkers=checkers,
89
91
  checking_interval=checking_interval,
90
92
  run=run,
@@ -47,6 +47,7 @@ class CommonTaskModel:
47
47
  retry: int = 2,
48
48
  retry_interval: Union[float, int] = 1,
49
49
  upstreams: Iterable[AnyTask] = [],
50
+ fallbacks: Iterable[AnyTask] = [],
50
51
  checkers: Iterable[AnyTask] = [],
51
52
  checking_interval: Union[float, int] = 0,
52
53
  run: Optional[Callable[..., Any]] = None,
@@ -73,6 +74,7 @@ class CommonTaskModel:
73
74
  self._retry = retry
74
75
  self._retry_interval = retry_interval
75
76
  self._upstreams = upstreams
77
+ self._fallbacks = fallbacks
76
78
  self._checkers = [checker.copy() for checker in checkers]
77
79
  self._checking_interval = checking_interval
78
80
  self._run_function: Optional[Callable[..., Any]] = run
@@ -90,16 +92,21 @@ class CommonTaskModel:
90
92
  self.__allow_add_env_files = True
91
93
  self.__allow_add_inputs = True
92
94
  self.__allow_add_upstreams: bool = True
95
+ self.__allow_add_fallbacks: bool = True
93
96
  self.__allow_add_checkers: bool = True
94
97
  self.__has_already_inject_env_files: bool = False
95
98
  self.__has_already_inject_envs: bool = False
96
99
  self.__has_already_inject_inputs: bool = False
97
100
  self.__has_already_inject_upstreams: bool = False
101
+ self.__has_already_inject_fallbacks: bool = False
98
102
  self.__all_inputs: Optional[List[AnyInput]] = None
99
103
 
100
104
  def _lock_upstreams(self):
101
105
  self.__allow_add_upstreams = False
102
106
 
107
+ def _lock_fallbacks(self):
108
+ self.__allow_add_fallbacks = False
109
+
103
110
  def _set_execution_id(self, execution_id: str):
104
111
  if self.__execution_id == "":
105
112
  self.__execution_id = execution_id
@@ -276,6 +283,25 @@ class CommonTaskModel:
276
283
  self.__has_already_inject_upstreams = True
277
284
  return list(self._upstreams)
278
285
 
286
+ def insert_fallback(self, *fallbacks: AnyTask):
287
+ if not self.__allow_add_fallbacks:
288
+ raise Exception(f"Cannot insert fallbacks to `{self.get_name()}`")
289
+ self._fallbacks = list(fallbacks) + list(self._fallbacks)
290
+
291
+ def add_fallback(self, *fallbacks: AnyTask):
292
+ if not self.__allow_add_fallbacks:
293
+ raise Exception(f"Cannot add fallbacks to `{self.get_name()}`")
294
+ self._fallbacks = list(self._fallbacks) + list(fallbacks)
295
+
296
+ def inject_fallbacks(self):
297
+ pass
298
+
299
+ def _get_fallbacks(self) -> List[AnyTask]:
300
+ if not self.__has_already_inject_fallbacks:
301
+ self.inject_fallbacks()
302
+ self.__has_already_inject_fallbacks = True
303
+ return list(self._fallbacks)
304
+
279
305
  def get_icon(self) -> str:
280
306
  return self._icon
281
307
 
zrb/task/checker.py CHANGED
@@ -32,6 +32,7 @@ class Checker(BaseTask):
32
32
  color: Optional[str] = None,
33
33
  description: str = "",
34
34
  upstreams: Iterable[AnyTask] = [],
35
+ fallbacks: Iterable[AnyTask] = [],
35
36
  on_triggered: Optional[OnTriggered] = None,
36
37
  on_waiting: Optional[OnWaiting] = None,
37
38
  on_skipped: Optional[OnSkipped] = None,
@@ -55,6 +56,7 @@ class Checker(BaseTask):
55
56
  color=color,
56
57
  description=description,
57
58
  upstreams=upstreams,
59
+ fallbacks=fallbacks,
58
60
  on_triggered=on_triggered,
59
61
  on_waiting=on_waiting,
60
62
  on_skipped=on_skipped,
zrb/task/cmd_task.py CHANGED
@@ -113,6 +113,7 @@ class CmdTask(BaseTask):
113
113
  cmd_path: CmdVal = "",
114
114
  cwd: Optional[Union[str, pathlib.Path]] = None,
115
115
  upstreams: Iterable[AnyTask] = [],
116
+ fallbacks: Iterable[AnyTask] = [],
116
117
  on_triggered: Optional[OnTriggered] = None,
117
118
  on_waiting: Optional[OnWaiting] = None,
118
119
  on_skipped: Optional[OnSkipped] = None,
@@ -141,6 +142,7 @@ class CmdTask(BaseTask):
141
142
  color=color,
142
143
  description=description,
143
144
  upstreams=upstreams,
145
+ fallbacks=fallbacks,
144
146
  on_triggered=on_triggered,
145
147
  on_waiting=on_waiting,
146
148
  on_skipped=on_skipped,
@@ -1,6 +1,7 @@
1
1
  import os
2
2
  import pathlib
3
3
 
4
+ from zrb.config.config import container_backend
4
5
  from zrb.helper.accessories.name import get_random_name
5
6
  from zrb.helper.docker_compose.fetch_external_env import fetch_compose_file_env_map
6
7
  from zrb.helper.docker_compose.file import read_compose_file, write_compose_file
@@ -36,27 +37,30 @@ from zrb.task_env.env_file import EnvFile
36
37
  from zrb.task_group.group import Group
37
38
  from zrb.task_input.any_input import AnyInput
38
39
 
39
- CURRENT_DIR = os.path.dirname(__file__)
40
- SHELL_SCRIPT_DIR = os.path.join(CURRENT_DIR, "..", "shell-scripts")
41
- TDockerComposeTask = TypeVar("TDockerComposeTask", bound="DockerComposeTask")
42
40
 
43
- ensure_docker_is_installed = CmdTask(
44
- name="ensure-docker-is-installed",
45
- cmd_path=[
46
- os.path.join(SHELL_SCRIPT_DIR, "_common-util.sh"),
47
- os.path.join(SHELL_SCRIPT_DIR, "ensure-docker-is-installed.sh"),
48
- ],
49
- preexec_fn=None,
50
- )
41
+ def _get_ensure_zrb_network_task(backend: str):
42
+ CURRENT_DIR = os.path.dirname(__file__)
43
+ SHELL_SCRIPT_DIR = os.path.join(CURRENT_DIR, "..", "shell-scripts")
44
+ ensure_container_backend = CmdTask(
45
+ name="ensure-container_backend",
46
+ cmd_path=[
47
+ os.path.join(SHELL_SCRIPT_DIR, "_common-util.sh"),
48
+ os.path.join(SHELL_SCRIPT_DIR, f"ensure-{backend}-is-installed.sh"),
49
+ ],
50
+ preexec_fn=None,
51
+ )
52
+ return CmdTask(
53
+ name="ensure-zrb-network",
54
+ cmd=[
55
+ f"{backend} network inspect zrb >/dev/null 2>&1 || \\",
56
+ f"{backend} network create -d bridge zrb",
57
+ ],
58
+ upstreams=[ensure_container_backend],
59
+ )
51
60
 
52
- ensure_zrb_network_exists = CmdTask(
53
- name="ensure-zrb-network-exists",
54
- cmd=[
55
- "docker network inspect zrb >/dev/null 2>&1 || \\",
56
- "docker network create -d bridge zrb",
57
- ],
58
- upstreams=[ensure_docker_is_installed],
59
- )
61
+
62
+ TDockerComposeTask = TypeVar("TDockerComposeTask", bound="DockerComposeTask")
63
+ ensure_zrb_network_task = _get_ensure_zrb_network_task(container_backend)
60
64
 
61
65
 
62
66
  @typechecked
@@ -96,6 +100,7 @@ class DockerComposeTask(CmdTask):
96
100
  setup_cmd_path: CmdVal = "",
97
101
  cwd: Optional[Union[str, pathlib.Path]] = None,
98
102
  upstreams: Iterable[AnyTask] = [],
103
+ fallbacks: Iterable[AnyTask] = [],
99
104
  on_triggered: Optional[OnTriggered] = None,
100
105
  on_waiting: Optional[OnWaiting] = None,
101
106
  on_skipped: Optional[OnSkipped] = None,
@@ -126,7 +131,8 @@ class DockerComposeTask(CmdTask):
126
131
  description=description,
127
132
  executable=executable,
128
133
  cwd=cwd,
129
- upstreams=[ensure_zrb_network_exists] + upstreams,
134
+ upstreams=[ensure_zrb_network_task] + upstreams,
135
+ fallbacks=fallbacks,
130
136
  on_triggered=on_triggered,
131
137
  on_waiting=on_waiting,
132
138
  on_skipped=on_skipped,
@@ -350,7 +356,7 @@ class DockerComposeTask(CmdTask):
350
356
  cmd_str = "\n".join(
351
357
  [
352
358
  setup_cmd_str,
353
- f"docker compose {options} {self._compose_cmd} {flags} {args}",
359
+ f"{container_backend} compose {options} {self._compose_cmd} {flags} {args}", # noqa
354
360
  ]
355
361
  )
356
362
  self.log_info(f"Command: {cmd_str}")
zrb/task/flow_task.py CHANGED
@@ -32,6 +32,7 @@ class FlowTask(BaseTask):
32
32
  color: Optional[str] = None,
33
33
  description: str = "",
34
34
  upstreams: Iterable[AnyTask] = [],
35
+ fallbacks: Iterable[AnyTask] = [],
35
36
  on_triggered: Optional[OnTriggered] = None,
36
37
  on_waiting: Optional[OnWaiting] = None,
37
38
  on_skipped: Optional[OnSkipped] = None,
@@ -72,6 +73,7 @@ class FlowTask(BaseTask):
72
73
  color=color,
73
74
  description=description,
74
75
  upstreams=final_upstreams,
76
+ fallbacks=fallbacks,
75
77
  on_triggered=on_triggered,
76
78
  on_waiting=on_waiting,
77
79
  on_skipped=on_skipped,
zrb/task/http_checker.py CHANGED
@@ -75,6 +75,7 @@ class HTTPChecker(Checker):
75
75
  url: str = "/",
76
76
  is_https: Union[bool, str] = False,
77
77
  upstreams: Iterable[AnyTask] = [],
78
+ fallbacks: Iterable[AnyTask] = [],
78
79
  on_triggered: Optional[OnTriggered] = None,
79
80
  on_waiting: Optional[OnWaiting] = None,
80
81
  on_skipped: Optional[OnSkipped] = None,
@@ -98,6 +99,7 @@ class HTTPChecker(Checker):
98
99
  color=color,
99
100
  description=description,
100
101
  upstreams=upstreams,
102
+ fallbacks=fallbacks,
101
103
  on_triggered=on_triggered,
102
104
  on_waiting=on_waiting,
103
105
  on_skipped=on_skipped,
zrb/task/notifier.py CHANGED
@@ -46,6 +46,7 @@ class Notifier(BaseTask):
46
46
  show_toast: bool = True,
47
47
  show_stdout: bool = True,
48
48
  upstreams: Iterable[AnyTask] = [],
49
+ fallbacks: Iterable[AnyTask] = [],
49
50
  on_triggered: Optional[OnTriggered] = None,
50
51
  on_waiting: Optional[OnWaiting] = None,
51
52
  on_skipped: Optional[OnSkipped] = None,
@@ -69,6 +70,7 @@ class Notifier(BaseTask):
69
70
  color=color,
70
71
  description=description,
71
72
  upstreams=upstreams,
73
+ fallbacks=fallbacks,
72
74
  on_triggered=on_triggered,
73
75
  on_waiting=on_waiting,
74
76
  on_skipped=on_skipped,
zrb/task/path_checker.py CHANGED
@@ -42,6 +42,7 @@ class PathChecker(Checker):
42
42
  color: Optional[str] = None,
43
43
  description: str = "",
44
44
  upstreams: Iterable[AnyTask] = [],
45
+ fallbacks: Iterable[AnyTask] = [],
45
46
  on_triggered: Optional[OnTriggered] = None,
46
47
  on_waiting: Optional[OnWaiting] = None,
47
48
  on_skipped: Optional[OnSkipped] = None,
@@ -67,6 +68,7 @@ class PathChecker(Checker):
67
68
  color=color,
68
69
  description=description,
69
70
  upstreams=upstreams,
71
+ fallbacks=fallbacks,
70
72
  on_triggered=on_triggered,
71
73
  on_waiting=on_waiting,
72
74
  on_skipped=on_skipped,
zrb/task/path_watcher.py CHANGED
@@ -56,6 +56,7 @@ class PathWatcher(Checker):
56
56
  color: Optional[str] = None,
57
57
  description: str = "",
58
58
  upstreams: Iterable[AnyTask] = [],
59
+ fallbacks: Iterable[AnyTask] = [],
59
60
  on_triggered: Optional[OnTriggered] = None,
60
61
  on_waiting: Optional[OnWaiting] = None,
61
62
  on_skipped: Optional[OnSkipped] = None,
@@ -83,6 +84,7 @@ class PathWatcher(Checker):
83
84
  color=color,
84
85
  description=description,
85
86
  upstreams=upstreams,
87
+ fallbacks=fallbacks,
86
88
  on_triggered=on_triggered,
87
89
  on_waiting=on_waiting,
88
90
  on_skipped=on_skipped,
zrb/task/port_checker.py CHANGED
@@ -54,6 +54,7 @@ class PortChecker(Checker):
54
54
  port: Union[int, JinjaTemplate] = 80,
55
55
  timeout: Union[int, JinjaTemplate] = 5,
56
56
  upstreams: Iterable[AnyTask] = [],
57
+ fallbacks: Iterable[AnyTask] = [],
57
58
  on_triggered: Optional[OnTriggered] = None,
58
59
  on_waiting: Optional[OnWaiting] = None,
59
60
  on_skipped: Optional[OnSkipped] = None,
@@ -77,6 +78,7 @@ class PortChecker(Checker):
77
78
  color=color,
78
79
  description=description,
79
80
  upstreams=upstreams,
81
+ fallbacks=fallbacks,
80
82
  on_triggered=on_triggered,
81
83
  on_waiting=on_waiting,
82
84
  on_skipped=on_skipped,
@@ -63,6 +63,7 @@ class RecurringTask(BaseTask):
63
63
  color: Optional[str] = None,
64
64
  description: str = "",
65
65
  upstreams: Iterable[AnyTask] = [],
66
+ fallbacks: Iterable[AnyTask] = [],
66
67
  on_triggered: Optional[OnTriggered] = None,
67
68
  on_waiting: Optional[OnWaiting] = None,
68
69
  on_skipped: Optional[OnSkipped] = None,
@@ -92,6 +93,7 @@ class RecurringTask(BaseTask):
92
93
  color=color,
93
94
  description=description,
94
95
  upstreams=upstreams,
96
+ fallbacks=fallbacks,
95
97
  on_triggered=on_triggered,
96
98
  on_waiting=on_waiting,
97
99
  on_skipped=on_skipped,
@@ -53,6 +53,7 @@ class RemoteCmdTask(BaseRemoteCmdTask):
53
53
  cmd_path: CmdVal = "",
54
54
  cwd: Optional[Union[str, pathlib.Path]] = None,
55
55
  upstreams: Iterable[AnyTask] = [],
56
+ fallbacks: Iterable[AnyTask] = [],
56
57
  on_triggered: Optional[OnTriggered] = None,
57
58
  on_waiting: Optional[OnWaiting] = None,
58
59
  on_skipped: Optional[OnSkipped] = None,
@@ -94,6 +95,7 @@ class RemoteCmdTask(BaseRemoteCmdTask):
94
95
  post_cmd=post_cmd,
95
96
  cwd=cwd,
96
97
  upstreams=[ensure_ssh_is_installed] + upstreams,
98
+ fallbacks=fallbacks,
97
99
  on_triggered=on_triggered,
98
100
  on_waiting=on_waiting,
99
101
  on_skipped=on_skipped,
@@ -57,6 +57,7 @@ class ResourceMaker(BaseTask):
57
57
  color: Optional[str] = None,
58
58
  description: str = "",
59
59
  upstreams: Iterable[AnyTask] = [],
60
+ fallbacks: Iterable[AnyTask] = [],
60
61
  on_triggered: Optional[OnTriggered] = None,
61
62
  on_waiting: Optional[OnWaiting] = None,
62
63
  on_skipped: Optional[OnSkipped] = None,
@@ -78,6 +79,7 @@ class ResourceMaker(BaseTask):
78
79
  color=color,
79
80
  description=description,
80
81
  upstreams=upstreams,
82
+ fallbacks=fallbacks,
81
83
  on_triggered=on_triggered,
82
84
  on_waiting=on_waiting,
83
85
  on_skipped=on_skipped,
zrb/task/rsync_task.py CHANGED
@@ -56,6 +56,7 @@ class RsyncTask(BaseRemoteCmdTask):
56
56
  executable: Optional[str] = None,
57
57
  cwd: Optional[Union[str, pathlib.Path]] = None,
58
58
  upstreams: Iterable[AnyTask] = [],
59
+ fallbacks: Iterable[AnyTask] = [],
59
60
  on_triggered: Optional[OnTriggered] = None,
60
61
  on_waiting: Optional[OnWaiting] = None,
61
62
  on_skipped: Optional[OnSkipped] = None,
@@ -91,6 +92,7 @@ class RsyncTask(BaseRemoteCmdTask):
91
92
  cmd=cmd,
92
93
  cwd=cwd,
93
94
  upstreams=[ensure_rsync_is_installed] + upstreams,
95
+ fallbacks=fallbacks,
94
96
  on_triggered=on_triggered,
95
97
  on_waiting=on_waiting,
96
98
  on_skipped=on_skipped,
zrb/task/time_watcher.py CHANGED
@@ -51,6 +51,7 @@ class TimeWatcher(Checker):
51
51
  color: Optional[str] = None,
52
52
  description: str = "",
53
53
  upstreams: Iterable[AnyTask] = [],
54
+ fallbacks: Iterable[AnyTask] = [],
54
55
  on_triggered: Optional[OnTriggered] = None,
55
56
  on_waiting: Optional[OnWaiting] = None,
56
57
  on_skipped: Optional[OnSkipped] = None,
@@ -74,6 +75,7 @@ class TimeWatcher(Checker):
74
75
  color=color,
75
76
  description=description,
76
77
  upstreams=upstreams,
78
+ fallbacks=fallbacks,
77
79
  on_triggered=on_triggered,
78
80
  on_waiting=on_waiting,
79
81
  on_skipped=on_skipped,
zrb/task/wiki_task.py ADDED
@@ -0,0 +1,119 @@
1
+ import os
2
+
3
+ from zrb.action.runner import Runner
4
+ from zrb.helper.python_task import show_lines
5
+ from zrb.helper.typecheck import typechecked
6
+ from zrb.helper.typing import Any, Callable, Iterable, List, Mapping, Optional, Union
7
+ from zrb.task.any_task import AnyTask
8
+ from zrb.task.any_task_event_handler import (
9
+ OnFailed,
10
+ OnReady,
11
+ OnRetry,
12
+ OnSkipped,
13
+ OnStarted,
14
+ OnTriggered,
15
+ OnWaiting,
16
+ )
17
+ from zrb.task.task import Task
18
+ from zrb.task_env.env import Env
19
+ from zrb.task_env.env_file import EnvFile
20
+ from zrb.task_group.group import Group
21
+ from zrb.task_input.any_input import AnyInput
22
+
23
+
24
+ @typechecked
25
+ def create_wiki_tasks(
26
+ directory: str,
27
+ group: Optional[Group] = None,
28
+ inputs: Iterable[AnyInput] = [],
29
+ envs: Iterable[Env] = [],
30
+ env_files: Iterable[EnvFile] = [],
31
+ icon: Optional[str] = None,
32
+ color: Optional[str] = None,
33
+ upstreams: Iterable[AnyTask] = [],
34
+ fallbacks: Iterable[AnyTask] = [],
35
+ on_triggered: Optional[OnTriggered] = None,
36
+ on_waiting: Optional[OnWaiting] = None,
37
+ on_skipped: Optional[OnSkipped] = None,
38
+ on_started: Optional[OnStarted] = None,
39
+ on_ready: Optional[OnReady] = None,
40
+ on_retry: Optional[OnRetry] = None,
41
+ on_failed: Optional[OnFailed] = None,
42
+ should_execute: Union[bool, str, Callable[..., bool]] = True,
43
+ runner: Optional[Runner] = None,
44
+ ):
45
+ abs_directory = os.path.abspath(directory)
46
+ directory_structure = _get_directory_structure(abs_directory)
47
+ tasks: List[AnyTask] = []
48
+ for file_name in directory_structure["files"]:
49
+ if not file_name.endswith(".md"):
50
+ continue
51
+ task_name = file_name[:-3]
52
+ task = Task(
53
+ name=task_name,
54
+ group=group,
55
+ inputs=inputs,
56
+ envs=envs,
57
+ env_files=env_files,
58
+ icon=icon,
59
+ color=color,
60
+ upstreams=upstreams,
61
+ fallbacks=fallbacks,
62
+ on_triggered=on_triggered,
63
+ on_waiting=on_waiting,
64
+ on_skipped=on_skipped,
65
+ on_started=on_started,
66
+ on_ready=on_ready,
67
+ on_retry=on_retry,
68
+ on_failed=on_failed,
69
+ should_execute=should_execute,
70
+ run=_create_function(directory=directory, file_name=file_name),
71
+ )
72
+ if runner is not None:
73
+ runner.register(task)
74
+ tasks.append(task)
75
+ for dir_name in directory_structure["dirs"]:
76
+ sub_group = Group(name=dir_name, parent=group)
77
+ sub_tasks = create_wiki_tasks(
78
+ directory=os.path.join(abs_directory, dir_name),
79
+ group=sub_group,
80
+ inputs=inputs,
81
+ envs=envs,
82
+ env_files=env_files,
83
+ icon=icon,
84
+ color=color,
85
+ upstreams=upstreams,
86
+ fallbacks=fallbacks,
87
+ on_triggered=on_triggered,
88
+ on_waiting=on_waiting,
89
+ on_skipped=on_skipped,
90
+ on_started=on_started,
91
+ on_ready=on_ready,
92
+ on_retry=on_retry,
93
+ on_failed=on_failed,
94
+ should_execute=should_execute,
95
+ runner=runner,
96
+ )
97
+ tasks = tasks + sub_tasks
98
+ return tasks
99
+
100
+
101
+ def _create_function(directory: str, file_name: str) -> Callable[..., Any]:
102
+ def fn(*args: Any, **kwargs: Any):
103
+ with open(os.path.join(directory, file_name)) as f:
104
+ content = f.read()
105
+ lines = content.split("\n")
106
+ show_lines(kwargs["_task"], *lines)
107
+
108
+ return fn
109
+
110
+
111
+ def _get_directory_structure(path) -> Mapping[str, List[str]]:
112
+ contents = {"files": [], "dirs": []}
113
+ for item in os.listdir(path):
114
+ full_path = os.path.join(path, item)
115
+ if os.path.isdir(full_path):
116
+ contents["dirs"].append(item)
117
+ elif os.path.isfile(full_path):
118
+ contents["files"].append(item)
119
+ return contents
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: zrb
3
- Version: 0.9.3
3
+ Version: 0.10.0
4
4
  Summary: A Framework to Enhance Your Workflow
5
5
  Home-page: https://github.com/state-alchemists/zrb
6
6
  License: AGPL-3.0-or-later
@@ -1,4 +1,4 @@
1
- zrb/__init__.py,sha256=rAdL6lnrlKAcFBrqC2otYsF-UsOyeH9pOtcQDukemDI,2440
1
+ zrb/__init__.py,sha256=a6q4Q6WsU-IEACDBmoE3mYhtTXPKr8dj3QqOMTLLsfI,2514
2
2
  zrb/__main__.py,sha256=cNxFamU9qYt50y33wh1ekEMpRJ8_A3pPXW4wLywQaqY,314
3
3
  zrb/action/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
4
  zrb/action/runner.py,sha256=Tphwb60lKTnW3UCSo8urn23W4qzJ4TlkY9Xwy4Sl2a8,4839
@@ -111,7 +111,7 @@ zrb/builtin/generator/docker_compose_task/template/src/kebab-zrb-task-name/docke
111
111
  zrb/builtin/generator/docker_compose_task/template/src/kebab-zrb-task-name/docker-compose.yml,sha256=NlCmer0mm-NyoF-yDRSlucgpxPrYtc6hVzAVvs8Obpg,762
112
112
  zrb/builtin/generator/docker_compose_task/template/src/kebab-zrb-task-name/image/Dockerfile,sha256=p1lq7ckHynkTakKop6pk6qcZI5en1pag5Jj71pL-lJ8,312
113
113
  zrb/builtin/generator/docker_compose_task/template/src/kebab-zrb-task-name/image/main.py,sha256=9oXlXs0J3d2fhm9flhVGA-H_XxCDsOj_dFRhyhWEjvc,511
114
- zrb/builtin/generator/docker_compose_task/template/src/kebab-zrb-task-name/image/pyproject.toml,sha256=j-B3WOCItCFNPYCkxoQXyAIZg6adx_4aVPn4hgYiFpM,525
114
+ zrb/builtin/generator/docker_compose_task/template/src/kebab-zrb-task-name/image/pyproject.toml,sha256=lCuHzvgZ541o8vm-9I_hnSIL4YP_LWd4PA9jS6GRB9Y,525
115
115
  zrb/builtin/generator/fastapp/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
116
116
  zrb/builtin/generator/fastapp/add.py,sha256=oNmwFxcHrzLQI_dqprTVyOc1ssC5uzqio_D530tikDk,7637
117
117
  zrb/builtin/generator/fastapp/template/_automate/snake_zrb_app_name/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -794,7 +794,7 @@ zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/docs/modular-monol
794
794
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/docs/modular-monolith/images/fastapp.png,sha256=0etGKABnezz-2igIVXrPfCeVGu1ZNCfCfEVRKqYiSek,40600
795
795
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/loadtest/.gitignore,sha256=pV8ocs2GHxcYONxSStiofsLNjBiao0VxgcWQ36WWKyc,17
796
796
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/loadtest/locustfile.py,sha256=Xi73PCgvtJd7lUbvN3k8fanYffct3JVTKWrGLsFjsn8,870
797
- zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/loadtest/pyproject.toml,sha256=g8E1uRwpqRANF4szjeLo-07u1d-3ltHH9lVEGt6GaJ8,495
797
+ zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/loadtest/pyproject.toml,sha256=09Alg5DVE3yddSPyZs6apJoPcrngJXTRACc7-j4vf9E,494
798
798
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/loadtest/template.env,sha256=KVDIKgYQ-PdOTm5nho96HIgResVkn7MQy7dJWuPF65U,107
799
799
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/monitoring/clickhouse/clickhouse-cluster.xml,sha256=02gTyN8aPK3QWnYLfJHSv3SG_AgZ7lDJ5kxwRMx_uII,2870
800
800
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/monitoring/clickhouse/clickhouse-config.xml,sha256=sx3tdbrynKx9BKyRA-eFq8MUsRcD9WD3FZS-QsfpSQM,55854
@@ -1008,7 +1008,7 @@ zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/module/log/reg
1008
1008
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/module/log/rpc.py,sha256=Q1ClGIxzRij8oHrWKDtkb0fC_BeqCjKBi1xP962MGEc,445
1009
1009
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/module/log/schema/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1010
1010
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/module/log/schema/activity.py,sha256=1Wqitx-6-UjXeFhscrbIystLm-XY2FqbUkxwbJ3sgxA,338
1011
- zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/pyproject.toml,sha256=bnyLqnOtwFvLUFsvZgyBv7gD8hR9rxlx0QoSIG4X5d8,1000
1011
+ zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/pyproject.toml,sha256=7w5FxHFCW_LqFooddSoS1L-3NFMRWfnXN47AyL8lFTg,1000
1012
1012
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/schema/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1013
1013
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/schema/frontend_config.py,sha256=l_tDK3RkTrXBKQZxMAEmiSC_rlJb956wVMp53k-4SZE,163
1014
1014
  zrb/builtin/generator/fastapp/template/src/kebab-zrb-app-name/src/start.sh,sha256=ssQUi5Ad8VCYR8bNCgjn49YaHtkajiDnzuY2hpdlkwU,1950
@@ -1077,11 +1077,11 @@ zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/cmd/
1077
1077
  zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/cmd/build.sh,sha256=BdrlubJq1b9kjtB06IIBxy615NUCh98x-eD3e9JFeAY,86
1078
1078
  zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/cmd/install-symlink.sh,sha256=DntlTyRlfRyxier2byya2dUqW33T2g61yhZLKELVri8,37
1079
1079
  zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/cmd/prepare-venv.sh,sha256=rXg-BvwoWK2xgbZvl01xHko6TZkSkb-yc_LiW8iF2n4,38
1080
- zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/cmd/publish.sh,sha256=UjIEE_ta-wfmz3CfTfy8xrpSsZ4Ck10OyabPGTmUiZc,80
1081
- zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/local.py,sha256=HN6baO5SbNENvxpeOrxpjSQSisZ_WTTPI0k2zcB5TC4,3131
1080
+ zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/cmd/publish.sh,sha256=eR83QHGe96VQN4ULgFF2HYI1687WXhOmZ53CN7reM9U,29
1081
+ zrb/builtin/generator/pip_package/template/_automate/snake_zrb_package_name/local.py,sha256=2MJ4kAvF__XcR8DxwVR-o_m86afPdhx3Tc_nBfoNsAQ,2844
1082
1082
  zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/.gitignore,sha256=0EufjWT4Uway6zeCoEbXUIHxyE0GuJD-l58Bbp8kVyo,6
1083
1083
  zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/README.md,sha256=hk0zeAogO6xDhpXOyqNQmWJW70tszYbqupoD94A0bF8,1995
1084
- zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/pyproject.toml,sha256=f-1tLKqM1CQC--CxZjKQnj04XeJCSx5a6APQ9zUMpjA,764
1084
+ zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/pyproject.toml,sha256=DYYx99Z8UAB45VpBRxc2i0JBXwHlVXLFUMirIKiKUk4,764
1085
1085
  zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/src/snake_zrb_package_name/__init__.py,sha256=nFL5b7hvWxJ48FAtlq-kdS5HYpTaFahCuCVzxx8LvG0,38
1086
1086
  zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/src/snake_zrb_package_name/__main__.py,sha256=nFL5b7hvWxJ48FAtlq-kdS5HYpTaFahCuCVzxx8LvG0,38
1087
1087
  zrb/builtin/generator/pip_package/template/src/kebab-zrb-package-name/src/snake_zrb_package_name/util.py,sha256=A7e4ILr3Vyhb4bONNlh6NoaF_-5hLZ4YwhWrSZ40jaI,60
@@ -1095,14 +1095,14 @@ zrb/builtin/generator/plugin/template/_cmd/activate-venv.sh,sha256=DWgQyDPqIhvTK
1095
1095
  zrb/builtin/generator/plugin/template/_cmd/build.sh,sha256=BdrlubJq1b9kjtB06IIBxy615NUCh98x-eD3e9JFeAY,86
1096
1096
  zrb/builtin/generator/plugin/template/_cmd/install-symlink.sh,sha256=DntlTyRlfRyxier2byya2dUqW33T2g61yhZLKELVri8,37
1097
1097
  zrb/builtin/generator/plugin/template/_cmd/prepare-venv.sh,sha256=rXg-BvwoWK2xgbZvl01xHko6TZkSkb-yc_LiW8iF2n4,38
1098
- zrb/builtin/generator/plugin/template/_cmd/publish.sh,sha256=kiF-8ngC9g-2OqDHH3Px5VLuP0q58JVh-EIPMYSLvr4,64
1098
+ zrb/builtin/generator/plugin/template/_cmd/publish.sh,sha256=eR83QHGe96VQN4ULgFF2HYI1687WXhOmZ53CN7reM9U,29
1099
1099
  zrb/builtin/generator/plugin/template/project.sh,sha256=yVjqMckvg2AFxDDMg6xbUjCF_t4xDt8HSLQsfe6m6lY,1938
1100
- zrb/builtin/generator/plugin/template/pyproject.toml,sha256=vEovnqYgMWPkT8Ayh2AcZnJXDFN44xK6TyqGfEYYCj0,763
1100
+ zrb/builtin/generator/plugin/template/pyproject.toml,sha256=s45zeBuZ_6PDtqYu3BxsVgysnF7-Pqcj3-FCRceKRds,763
1101
1101
  zrb/builtin/generator/plugin/template/src/snake_zrb_package_name/__init__.py,sha256=5Twm0lVcddWW1tnRKDkKSkwMeuTxZgZ-GyPcr2MeyZk,130
1102
1102
  zrb/builtin/generator/plugin/template/src/snake_zrb_package_name/__main__.py,sha256=xniLN9eAYflMDjM9LOPlt7FATS1P6aZBkUTGa9cfv6w,121
1103
1103
  zrb/builtin/generator/plugin/template/src/snake_zrb_package_name/task/example_task.py,sha256=HainQwB35U6keQjN4DDm_0CKdLfLSaXDzWoVkWRAOAg,325
1104
1104
  zrb/builtin/generator/plugin/template/template.env,sha256=91EyYfFAatX6OB46KoH6c6Sc54yqN-lXSm5NlPuvh3Q,118
1105
- zrb/builtin/generator/plugin/template/zrb_init.py,sha256=dneMFEC6d4jWB8-j15EigUo2FKtW3oDbpjVRQ38Cmzk,2459
1105
+ zrb/builtin/generator/plugin/template/zrb_init.py,sha256=5JOhOPMPXsIgOhnqAmW9zJU9Rwc8uinns8y6ZdHdcL0,2213
1106
1106
  zrb/builtin/generator/project/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1107
1107
  zrb/builtin/generator/project/create.py,sha256=Z3h1u3ZKxlzsMOhLNxLBkUewtcArnTOGg8dO3j-6mP4,3303
1108
1108
  zrb/builtin/generator/project/template/.flake8,sha256=uBzLhwCiogbbtgxD9dBTGxSm_8VQ1UHpVkn2CroGl3c,56
@@ -1113,7 +1113,7 @@ zrb/builtin/generator/project/template/.python-version,sha256=rGeoqWHOE1NzOu73di
1113
1113
  zrb/builtin/generator/project/template/README.md,sha256=jNnkBuWhfab1HlcOqi0NKaM1O1NtTjchFrvOtR4KQPg,2026
1114
1114
  zrb/builtin/generator/project/template/_automate/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1115
1115
  zrb/builtin/generator/project/template/project.sh,sha256=yVjqMckvg2AFxDDMg6xbUjCF_t4xDt8HSLQsfe6m6lY,1938
1116
- zrb/builtin/generator/project/template/pyproject.toml,sha256=xlAUFSQR4N9z8dfxgUCsbQYdsb1Xn_tFhUW9L9yH-To,520
1116
+ zrb/builtin/generator/project/template/pyproject.toml,sha256=RcFR64JMegOsGuO0xlvCrqkeW6yEaNmBpEQtW7nyS3g,520
1117
1117
  zrb/builtin/generator/project/template/src/.gitkeep,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1118
1118
  zrb/builtin/generator/project/template/template.env,sha256=y7EQynzEPauiYe0Qqx2xQqg-x0FCn6tkalWfg8BpzOE,64
1119
1119
  zrb/builtin/generator/project/template/zrb_init.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -1157,7 +1157,7 @@ zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/.doc
1157
1157
  zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/.gitignore,sha256=-HAk8HPeDhUKv-zCBPehLdOdolHVNfjOi_QcdmHosus,23
1158
1158
  zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/Dockerfile,sha256=xTuQw_l427RQAt3zTmYN4YcA7M5szz753a88jVEdKfg,311
1159
1159
  zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/main.py,sha256=9oXlXs0J3d2fhm9flhVGA-H_XxCDsOj_dFRhyhWEjvc,511
1160
- zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/pyproject.toml,sha256=oQMu5-uqgGtcLpWwMcygI-S48uA-WQ5klEC29DPbuOk,568
1160
+ zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/pyproject.toml,sha256=UPXIM0ukot6YkkEVPmG2by0aPN0Mgf8s_TbURxSADJg,568
1161
1161
  zrb/builtin/generator/simple_python_app/template/src/kebab-zrb-app-name/src/template.env,sha256=vtoZ0LV8OKAU1EUWBiB8PIKbf1FaNfm-49j7aXvKsgs,87
1162
1162
  zrb/builtin/git.py,sha256=Djz83w8_DiF1lZkWSl5HRgWlj7SArOpyQW5rQTjVUf0,3016
1163
1163
  zrb/builtin/group.py,sha256=LotriKtrebUzHgA4_0XzO4WPSG6Dkwb-E8_HsHPQlo8,1168
@@ -1173,7 +1173,7 @@ zrb/builtin/update.py,sha256=4CY6qqpRChaxKL0d6ckDQmziLlQTX4Q5QmEgmCJVx1s,397
1173
1173
  zrb/builtin/version.py,sha256=3VibJO-_AOC0Kx4thuKT2HKM0Jhe92liFFsOYrjTdeY,478
1174
1174
  zrb/builtin/watch_changes.py,sha256=sylF-qCSsivffjh0nd5-M4aobRpQu3S58S00X370fzQ,1191
1175
1175
  zrb/config/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1176
- zrb/config/config.py,sha256=mqLM8TjyHsJ9Da5rFkC4IePTBtLyao-DNjM_JPuPRK4,1170
1176
+ zrb/config/config.py,sha256=h3Sx75fTi_mRntW1zkuDXSTzTdUd4HJhrQAzoaSgqsU,1266
1177
1177
  zrb/helper/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1178
1178
  zrb/helper/accessories/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1179
1179
  zrb/helper/accessories/color.py,sha256=nYoL77v-9dJATLuSyu7ySq-orIcr4hXB5CqMoxaG7qQ,805
@@ -1224,40 +1224,42 @@ zrb/helper/util.py,sha256=qaJY-r-z9O1DTg6etptQsxnUO5u165Rv0RraP0VUTiA,3545
1224
1224
  zrb/runner.py,sha256=MPCNPMCyiYNZeubSxd1eM2Zr6PCIKF-9pkG385AXElw,118
1225
1225
  zrb/shell-scripts/_common-util.sh,sha256=8zvSAbDp8z4JWxMT6s6bSnNBCfCB88gLLpK5LOhyPBg,229
1226
1226
  zrb/shell-scripts/ensure-docker-is-installed.sh,sha256=8CL5gYs428LPWcF43X-1O1i2YyWAOGzXTKZttiS9J1Q,2999
1227
+ zrb/shell-scripts/ensure-podman-is-installed.sh,sha256=RvLLQIBN5cfLEsFkTpomgl_PxJZ6z0Wl0VGGtjIA5JM,1529
1227
1228
  zrb/shell-scripts/ensure-rsync-is-installed.sh,sha256=ffr8avoCUSoDQkEBWmeelgn-EtF9reQTaM0wfW6B0hc,1146
1228
1229
  zrb/shell-scripts/ensure-ssh-is-installed.sh,sha256=w5pCzsbEa3bnxT07q6gX0nWn-7HXsMiwBRrg7dMD57w,2414
1229
1230
  zrb/shell-scripts/notify.ps1,sha256=6_xPoIwuxARpYljcjVV-iRJS3gJqGfx-B6kj719cJ9o,843
1230
1231
  zrb/shell-scripts/rsync-util.sh,sha256=QzdhSBvUNMxB4U2B4m0Dxg9czGckRjB7Vk4A1ObG0-k,353
1231
1232
  zrb/shell-scripts/ssh-util.sh,sha256=9lXDzw6oO8HuA4vdbfps_uQMMwKyNYX9fZkZgpK52g8,401
1232
1233
  zrb/task/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1233
- zrb/task/any_task.py,sha256=VtEXfPTdi5sVYIPT5pupOrj3kjx-yhyHTyNUnn1h06U,36254
1234
+ zrb/task/any_task.py,sha256=hxL55NcbsXhMy4xa1z7pdhV5qE41QC5s63BrN81s0MQ,39020
1234
1235
  zrb/task/any_task_event_handler.py,sha256=vpO9t0fck8-oFu1KYptfcg2hXKRsk6V5je4Dg-Bl21o,359
1235
- zrb/task/base_remote_cmd_task.py,sha256=_DPrUp1uzHPhM4KvduAMh6HgRX6hG5yRL7-2CWoAZjo,9220
1236
+ zrb/task/base_remote_cmd_task.py,sha256=nwEuiSF4dh3hKNfBH0ABWotx59wU-on4E6jzW2Wl67U,9296
1236
1237
  zrb/task/base_task/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1237
- zrb/task/base_task/base_task.py,sha256=YD8weEGKdlQlH5isBAHWtekVYlNh40QA-qd8McKYH3c,17502
1238
+ zrb/task/base_task/base_task.py,sha256=tN1f6ZWPk0YdkmP9PJFRCuwkoY1n1RuftZLXjUzKLtM,19079
1238
1239
  zrb/task/base_task/component/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
1239
- zrb/task/base_task/component/base_task_model.py,sha256=EqfkXHjLkW7Fq_VPG3e9D3W_HCC7mgHvBHPs0Bzcdlo,10300
1240
- zrb/task/base_task/component/common_task_model.py,sha256=-zRTWQNqddH2CZyfvmW3gc7XKxmLSU6BsR_9j2TAgdc,11275
1240
+ zrb/task/base_task/component/base_task_model.py,sha256=YlEuvYSzlrK83Kds07bu2drKSw3rKyl7qIR1qwIPNZk,10376
1241
+ zrb/task/base_task/component/common_task_model.py,sha256=JoAAf8EvuPx31fCK_TBxX_TBeHZrZyFDjLeK8ts0w3A,12285
1241
1242
  zrb/task/base_task/component/pid_model.py,sha256=RjJIqOpavucDssnd3q3gT4q8QnP8I9SUdlv1b9pR7kU,292
1242
1243
  zrb/task/base_task/component/renderer.py,sha256=9wP2IW811Ta81IoPWmeQ7yVc7eG-uaSnOVbEyeaOIuk,4439
1243
1244
  zrb/task/base_task/component/trackers.py,sha256=gM9eOukMh6kvNJnRsHscQ_JN--Haa2YA4bIufqh8upE,1950
1244
- zrb/task/checker.py,sha256=T3q7_YXwpa1pG-EFh5sptLpJanWECqOwdc1POBkHnHg,3117
1245
- zrb/task/cmd_task.py,sha256=Di6CPSJS7RJGDIx1J-oEnijVJpjslXoP5q9K6SZ3GHA,13890
1245
+ zrb/task/checker.py,sha256=c_7vNq4Li_OdB9OXE6_VDAFazZwUKC9E7aesuksGH_I,3193
1246
+ zrb/task/cmd_task.py,sha256=wrSB-6jhPwd0dHVqGgonQjRu8qfXw7w8WH85p7yOOf4,13966
1246
1247
  zrb/task/decorator.py,sha256=7qEkdPoKzOIYQQnCXnjQMw0okG5rC24m7cmNxCou9r8,2887
1247
- zrb/task/docker_compose_task.py,sha256=pOVp9t9NXPb6nHnfTSnAkX5xOkiQLnuCMZvflbt1oa4,14017
1248
- zrb/task/flow_task.py,sha256=VsoGtxolNIdz-lHs0HSUYguVxU8c_R6CaTlsWQ_UjXU,4639
1249
- zrb/task/http_checker.py,sha256=IZgAJk3t3rDCpo-TxQumB7Llhqd_JedMVEu1bx_rGr8,5172
1250
- zrb/task/notifier.py,sha256=PgTekYIkQCnjshUL9p697a7wirgJVpkSs2tErHkFyXs,5986
1248
+ zrb/task/docker_compose_task.py,sha256=RYWYZFxHizbFcbkFGm5mQqKRwAm1WeXapffoJ5tEO-c,14333
1249
+ zrb/task/flow_task.py,sha256=uhwwT1Xpwcr4V9LPfJq4kyD3QC-4U9ijTAYLMBV2NIU,4715
1250
+ zrb/task/http_checker.py,sha256=QF43EuqY8FhLr7u-zVlITnjKgq6ozTy42f8kiqlBYAY,5248
1251
+ zrb/task/notifier.py,sha256=DNzRyG1goF-p6bSXWOkiJ1JO5FtXwVFaXaB63hj6GwM,6062
1251
1252
  zrb/task/parallel.py,sha256=HD8jTNkM-korep1vjllE4ZKS50-_P5a8rktq1QHHVd0,1042
1252
- zrb/task/path_checker.py,sha256=qRWGgtf4SXpyFUiHyAmpktiUmK_VvOQqUJmJvatvGfM,4153
1253
- zrb/task/path_watcher.py,sha256=QhGXO39A1avMRUNVni-lbapmtaImFC_zxqNHMXQo0gg,6268
1254
- zrb/task/port_checker.py,sha256=2-077O1DBa9RidxnijuAx3GKsyc6oy2mmSb0XniGuZk,4072
1255
- zrb/task/recurring_task.py,sha256=PezKAfMHtpe-CKJqZuUufcA1VGADTEnxaLP__9u95bE,7133
1256
- zrb/task/remote_cmd_task.py,sha256=9ObPxcIFaY7kFQw2Gg34ifyeGxfA3c_T_y1KO5aoZrI,3709
1257
- zrb/task/resource_maker.py,sha256=9lZ288jGHuBzz1jrFU_Enw_Mj2j8CS0hxzb5XSCVwnI,6576
1258
- zrb/task/rsync_task.py,sha256=EBzeZyO-L-lUgI9ARBiLFOrgjfnEtwseZ0CXKrJHOH8,3949
1253
+ zrb/task/path_checker.py,sha256=m_M_bTVGt-dpSQxGODXcZCTXCtB7S5NTm6nNC4OOlek,4229
1254
+ zrb/task/path_watcher.py,sha256=BHtKq2lEyl6eOraJz40oSWp8AWPcyisZSaodwdiG3Io,6344
1255
+ zrb/task/port_checker.py,sha256=lOt4DG7eVe9cvQ23nLgdPHSYH2hZpw7EuKgNDkvUMFw,4148
1256
+ zrb/task/recurring_task.py,sha256=UQ90VMG6oCgKL1akkSmDPHpTj2WQ6yhs-aldoGgTOwU,7209
1257
+ zrb/task/remote_cmd_task.py,sha256=pzSqwkKsEy8pGPyiZOY1X1t5m-8bObdWBo73Fjcb508,3785
1258
+ zrb/task/resource_maker.py,sha256=QrzYlhWCAMu2_WmMr4RImbP53ppNHzeob6I5cHxX2xU,6652
1259
+ zrb/task/rsync_task.py,sha256=tYLbu7q54Fs4z3LizIb_i9IMmaGGx48JFr5S8Lgr9hg,4025
1259
1260
  zrb/task/task.py,sha256=38w8diC22nU5bzN2X9mfJ8PKxxMl1Q_Lrlu5uIBRuc4,182
1260
- zrb/task/time_watcher.py,sha256=UlrwzxwzHxzdKmW6F5wEuhrCzFVk-JC89pdLKLjYOaA,3908
1261
+ zrb/task/time_watcher.py,sha256=M-GZPZIYmeBiTDeU9mgecpMJ7UMoZ1Zsj9c4OwTVa7o,3984
1262
+ zrb/task/wiki_task.py,sha256=dM4ANgGtiw0O5DK-S1WUM8VxLOG2wgxK5n6OtvN9r4M,3855
1261
1263
  zrb/task_env/constant.py,sha256=pWmniGJQV-74aNR7J0PYldFbL6YxZT27Nxs1jdwhH_Q,44
1262
1264
  zrb/task_env/env.py,sha256=y16WTzZGUJB596a2Qb_X1dhV0oYxU4JwlWf_rrHKMWo,4766
1263
1265
  zrb/task_env/env_file.py,sha256=BWG9ei41GrTKuTAOudneVBM-3ay88cnlM_11zWKMePE,2932
@@ -1274,8 +1276,8 @@ zrb/task_input/int_input.py,sha256=NVXAToqgdmWVwDqnr3XGuvq_QMNvUiIdD-pW5L4uebk,4
1274
1276
  zrb/task_input/password_input.py,sha256=5sS3XP7WtGow7r7Fid8J9SX0iNCidO6Bg7q40UpZDM0,4029
1275
1277
  zrb/task_input/str_input.py,sha256=D2WBeB-CdmAuOSzT7jTXvie7X3EK_m_Oq8_SVwmNpWA,4042
1276
1278
  zrb/task_input/task_input.py,sha256=L-U5dX-I2U5ci7GU226Q8pXcQe5SpGuOl5viFwlfiM0,2022
1277
- zrb-0.9.3.dist-info/LICENSE,sha256=WfnGCl8G60EYOPAEkuc8C9m9pdXWDe08NsKj3TBbxsM,728
1278
- zrb-0.9.3.dist-info/METADATA,sha256=nUsNR8qh2tGtY7Q_FRvRBPgqMLVTMajMEI5zzdxkzOA,16500
1279
- zrb-0.9.3.dist-info/WHEEL,sha256=FMvqSimYX_P7y0a7UY-_Mc83r5zkBZsCYPm7Lr0Bsq4,88
1280
- zrb-0.9.3.dist-info/entry_points.txt,sha256=xTgXc1kBKYhJHEujdaSPHUcJT3-hbyP1mLgwkv-5sSk,40
1281
- zrb-0.9.3.dist-info/RECORD,,
1279
+ zrb-0.10.0.dist-info/LICENSE,sha256=WfnGCl8G60EYOPAEkuc8C9m9pdXWDe08NsKj3TBbxsM,728
1280
+ zrb-0.10.0.dist-info/METADATA,sha256=ZdXksnBCBCCYXhM_SbvSWapwbHVSSTiHyCVeeaZ3r5U,16501
1281
+ zrb-0.10.0.dist-info/WHEEL,sha256=FMvqSimYX_P7y0a7UY-_Mc83r5zkBZsCYPm7Lr0Bsq4,88
1282
+ zrb-0.10.0.dist-info/entry_points.txt,sha256=xTgXc1kBKYhJHEujdaSPHUcJT3-hbyP1mLgwkv-5sSk,40
1283
+ zrb-0.10.0.dist-info/RECORD,,
File without changes
File without changes