zrb 0.15.1__py3-none-any.whl → 0.17.2__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.
- zrb/__init__.py +5 -0
- zrb/action/runner.py +6 -1
- zrb/builtin/_helper/reccuring_action.py +0 -23
- zrb/builtin/devtool/install/helix/helix.py +1 -4
- zrb/builtin/devtool/install/helix/resource/config.toml +2 -1
- zrb/builtin/process/pid/get_by_name.py +1 -1
- zrb/builtin/schedule.py +14 -10
- zrb/builtin/watch_changes.py +15 -14
- zrb/helper/callable.py +4 -1
- zrb/task/any_task.py +7 -9
- zrb/task/base_task/base_task.py +10 -6
- zrb/task/base_task/component/trackers.py +4 -3
- zrb/task/checker.py +4 -4
- zrb/task/cmd_task.py +10 -1
- zrb/task/decorator.py +2 -2
- zrb/task/docker_compose_task.py +2 -2
- zrb/task/http_checker.py +11 -2
- zrb/task/looper.py +43 -0
- zrb/task/path_checker.py +11 -2
- zrb/task/path_watcher.py +62 -42
- zrb/task/port_checker.py +11 -2
- zrb/task/recurring_task.py +1 -0
- zrb/task/resource_maker.py +10 -1
- zrb/task/server.py +191 -0
- zrb/task/time_watcher.py +47 -19
- zrb/task/watcher.py +100 -0
- {zrb-0.15.1.dist-info → zrb-0.17.2.dist-info}/METADATA +1 -1
- {zrb-0.15.1.dist-info → zrb-0.17.2.dist-info}/RECORD +31 -28
- {zrb-0.15.1.dist-info → zrb-0.17.2.dist-info}/LICENSE +0 -0
- {zrb-0.15.1.dist-info → zrb-0.17.2.dist-info}/WHEEL +0 -0
- {zrb-0.15.1.dist-info → zrb-0.17.2.dist-info}/entry_points.txt +0 -0
zrb/__init__.py
CHANGED
@@ -32,8 +32,10 @@ from zrb.task.resource_maker import (
|
|
32
32
|
get_default_resource_skip_parsing,
|
33
33
|
)
|
34
34
|
from zrb.task.rsync_task import RsyncTask
|
35
|
+
from zrb.task.server import Controller, Server
|
35
36
|
from zrb.task.task import Task
|
36
37
|
from zrb.task.time_watcher import TimeWatcher
|
38
|
+
from zrb.task.watcher import Watcher
|
37
39
|
from zrb.task.wiki_task import create_wiki_tasks
|
38
40
|
from zrb.task_env.env import Env
|
39
41
|
from zrb.task_env.env_file import EnvFile
|
@@ -74,6 +76,9 @@ assert HTTPChecker
|
|
74
76
|
assert PortChecker
|
75
77
|
assert PathChecker
|
76
78
|
assert PathWatcher
|
79
|
+
assert Controller
|
80
|
+
assert Server
|
81
|
+
assert Watcher
|
77
82
|
assert TimeWatcher
|
78
83
|
assert ResourceMaker
|
79
84
|
assert FlowTask
|
zrb/action/runner.py
CHANGED
@@ -110,7 +110,12 @@ class Runner:
|
|
110
110
|
|
111
111
|
def __get_wrapped_task_function(self, task: AnyTask) -> Callable[..., Any]:
|
112
112
|
def wrapped_function(*args: Any, **kwargs: Any) -> Any:
|
113
|
-
function = task.to_function(
|
113
|
+
function = task.to_function(
|
114
|
+
env_prefix=self.__env_prefix,
|
115
|
+
raise_error=True,
|
116
|
+
should_clear_xcom=True,
|
117
|
+
should_stop_looper=True,
|
118
|
+
)
|
114
119
|
try:
|
115
120
|
function(*args, **kwargs)
|
116
121
|
except Exception:
|
@@ -1,6 +1,4 @@
|
|
1
|
-
from zrb.helper.typing import Any
|
2
1
|
from zrb.task.cmd_task import CmdTask
|
3
|
-
from zrb.task.decorator import python_task
|
4
2
|
from zrb.task.notifier import Notifier
|
5
3
|
from zrb.task.task import Task
|
6
4
|
from zrb.task_input.str_input import StrInput
|
@@ -8,8 +6,6 @@ from zrb.task_input.str_input import StrInput
|
|
8
6
|
|
9
7
|
def create_recurring_action(
|
10
8
|
notif_title: str,
|
11
|
-
trigger_caption: str,
|
12
|
-
trigger_xcom_key: str,
|
13
9
|
default_message: str = "👋",
|
14
10
|
) -> Task:
|
15
11
|
# define inputs
|
@@ -23,16 +19,11 @@ def create_recurring_action(
|
|
23
19
|
default="",
|
24
20
|
prompt="Command to be executed",
|
25
21
|
)
|
26
|
-
# define tasks
|
27
|
-
show_trigger_info = _create_show_trigger_info(
|
28
|
-
trigger_caption=trigger_caption, trigger_xcom_key=trigger_xcom_key
|
29
|
-
)
|
30
22
|
run_command = CmdTask(
|
31
23
|
name="run-command",
|
32
24
|
icon="⚙️",
|
33
25
|
color="blue",
|
34
26
|
inputs=[command_input],
|
35
|
-
upstreams=[show_trigger_info],
|
36
27
|
should_execute='{{ input.command != "" }}',
|
37
28
|
cmd="{{ input.command }}",
|
38
29
|
)
|
@@ -43,7 +34,6 @@ def create_recurring_action(
|
|
43
34
|
inputs=[message_input],
|
44
35
|
title=notif_title,
|
45
36
|
message="{{ input.message }}",
|
46
|
-
upstreams=[show_trigger_info],
|
47
37
|
should_execute='{{ input.message != "" }}',
|
48
38
|
)
|
49
39
|
# return aggregator task
|
@@ -53,16 +43,3 @@ def create_recurring_action(
|
|
53
43
|
upstreams=[run_command, notify],
|
54
44
|
retry=0,
|
55
45
|
)
|
56
|
-
|
57
|
-
|
58
|
-
def _create_show_trigger_info(trigger_caption: str, trigger_xcom_key: str) -> Task:
|
59
|
-
@python_task(
|
60
|
-
name="show-trigger-info",
|
61
|
-
icon="🔍",
|
62
|
-
color="magenta",
|
63
|
-
)
|
64
|
-
def show_trigger_info(*args: Any, **kwargs: Any):
|
65
|
-
task: Task = kwargs.get("_task")
|
66
|
-
task.print_out(f"{trigger_caption}: {task.get_xcom(trigger_xcom_key)}")
|
67
|
-
|
68
|
-
return show_trigger_info
|
@@ -29,7 +29,6 @@ install_helix = FlowTask(
|
|
29
29
|
run=write_config(
|
30
30
|
template_file=os.path.join(
|
31
31
|
_CURRENT_DIR,
|
32
|
-
"helix",
|
33
32
|
"resource",
|
34
33
|
"themes",
|
35
34
|
"gruvbox_transparent.toml", # noqa
|
@@ -41,9 +40,7 @@ install_helix = FlowTask(
|
|
41
40
|
Task(
|
42
41
|
name="configure-helix",
|
43
42
|
run=write_config(
|
44
|
-
template_file=os.path.join(
|
45
|
-
_CURRENT_DIR, "helix", "resource", "config.toml"
|
46
|
-
),
|
43
|
+
template_file=os.path.join(_CURRENT_DIR, "resource", "config.toml"),
|
47
44
|
config_file="~/.config/helix/config.toml",
|
48
45
|
remove_old_config=True,
|
49
46
|
),
|
@@ -3,6 +3,7 @@ theme = "gruvbox_transparent"
|
|
3
3
|
[editor]
|
4
4
|
line-number = "relative"
|
5
5
|
mouse = true
|
6
|
+
bufferline = "always"
|
6
7
|
|
7
8
|
[editor.cursor-shape]
|
8
9
|
insert = "bar"
|
@@ -16,4 +17,4 @@ enable = true
|
|
16
17
|
hidden = false
|
17
18
|
git-ignore = false
|
18
19
|
git-global = false
|
19
|
-
git-exclude = false
|
20
|
+
git-exclude = false
|
zrb/builtin/schedule.py
CHANGED
@@ -1,10 +1,10 @@
|
|
1
1
|
from zrb.builtin._helper.reccuring_action import create_recurring_action
|
2
2
|
from zrb.runner import runner
|
3
|
-
from zrb.task.
|
3
|
+
from zrb.task.server import Controller, Server
|
4
4
|
from zrb.task.time_watcher import TimeWatcher
|
5
5
|
from zrb.task_input.str_input import StrInput
|
6
6
|
|
7
|
-
schedule =
|
7
|
+
schedule = Server(
|
8
8
|
name="schedule",
|
9
9
|
icon="📅",
|
10
10
|
color="yellow",
|
@@ -17,15 +17,19 @@ schedule = RecurringTask(
|
|
17
17
|
description="Schedule cron pattern to show the message",
|
18
18
|
),
|
19
19
|
],
|
20
|
-
|
21
|
-
|
22
|
-
name="
|
20
|
+
controllers=[
|
21
|
+
Controller(
|
22
|
+
name="periodic",
|
23
|
+
trigger=TimeWatcher(
|
24
|
+
name="watch-time",
|
25
|
+
color="cyan",
|
26
|
+
icon="⏰",
|
27
|
+
schedule="{{input.schedule}}",
|
28
|
+
),
|
29
|
+
action=create_recurring_action(
|
30
|
+
notif_title="Schedule",
|
31
|
+
),
|
23
32
|
)
|
24
33
|
],
|
25
|
-
task=create_recurring_action(
|
26
|
-
notif_title="Schedule",
|
27
|
-
trigger_caption="Schedule",
|
28
|
-
trigger_xcom_key="watch-time.scheduled-time",
|
29
|
-
),
|
30
34
|
)
|
31
35
|
runner.register(schedule)
|
zrb/builtin/watch_changes.py
CHANGED
@@ -1,10 +1,10 @@
|
|
1
1
|
from zrb.builtin._helper.reccuring_action import create_recurring_action
|
2
2
|
from zrb.runner import runner
|
3
3
|
from zrb.task.path_watcher import PathWatcher
|
4
|
-
from zrb.task.
|
4
|
+
from zrb.task.server import Controller, Server
|
5
5
|
from zrb.task_input.str_input import StrInput
|
6
6
|
|
7
|
-
watch_changes =
|
7
|
+
watch_changes = Server(
|
8
8
|
name="watch-changes",
|
9
9
|
icon="🕵️",
|
10
10
|
color="yellow",
|
@@ -23,19 +23,20 @@ watch_changes = RecurringTask(
|
|
23
23
|
description="Ignored file pattern",
|
24
24
|
),
|
25
25
|
],
|
26
|
-
|
27
|
-
|
28
|
-
name="watch
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
26
|
+
controllers=[
|
27
|
+
Controller(
|
28
|
+
name="watch",
|
29
|
+
trigger=PathWatcher(
|
30
|
+
name="watch-path",
|
31
|
+
color="cyan",
|
32
|
+
icon="👀",
|
33
|
+
path="{{input.pattern}}",
|
34
|
+
ignored_path="{{input.ignored_pattern}}",
|
35
|
+
),
|
36
|
+
action=create_recurring_action(
|
37
|
+
notif_title="Watch",
|
38
|
+
),
|
33
39
|
)
|
34
40
|
],
|
35
|
-
task=create_recurring_action(
|
36
|
-
notif_title="Watch",
|
37
|
-
trigger_caption="File changes",
|
38
|
-
trigger_xcom_key="watch-path.file",
|
39
|
-
),
|
40
41
|
)
|
41
42
|
runner.register(watch_changes)
|
zrb/helper/callable.py
CHANGED
@@ -1,3 +1,4 @@
|
|
1
|
+
import asyncio
|
1
2
|
import inspect
|
2
3
|
from typing import Any, Callable
|
3
4
|
|
@@ -10,4 +11,6 @@ logger.debug(colored("Loading zrb.helper.callable", attrs=["dark"]))
|
|
10
11
|
async def run_async(fn: Callable, *args: Any, **kwargs: Any) -> Any:
|
11
12
|
if inspect.iscoroutinefunction(fn):
|
12
13
|
return await fn(*args, **kwargs)
|
13
|
-
|
14
|
+
coro = asyncio.to_thread(fn, *args, **kwargs)
|
15
|
+
task = asyncio.create_task(coro)
|
16
|
+
return await task
|
zrb/task/any_task.py
CHANGED
@@ -25,14 +25,12 @@ TAnyTask = TypeVar("TAnyTask", bound="AnyTask")
|
|
25
25
|
|
26
26
|
class AnyTask(ABC):
|
27
27
|
"""
|
28
|
-
|
28
|
+
Contract/interface for all Zrb Task.
|
29
29
|
|
30
|
-
This class acts as a template for creating new
|
31
|
-
extend this class and implement all its abstract methods. The `AnyTask` class is
|
32
|
-
considered atomic and is not broken into multiple interfaces.
|
30
|
+
This class acts as a template for creating new Zrb Task types.
|
33
31
|
|
34
|
-
|
35
|
-
|
32
|
+
To define a new Zrb Task, you should extend this class and implement all its methods.
|
33
|
+
The easiest way to do so is by extending `Task`
|
36
34
|
"""
|
37
35
|
|
38
36
|
@abstractmethod
|
@@ -74,7 +72,7 @@ class AnyTask(ABC):
|
|
74
72
|
Examples:
|
75
73
|
>>> from zrb import Task
|
76
74
|
>>> class MyTask(Task):
|
77
|
-
>>>
|
75
|
+
>>> def run(self, *args: Any, **kwargs: Any) -> int:
|
78
76
|
>>> self.print_out('Doing some calculation')
|
79
77
|
>>> return 42
|
80
78
|
"""
|
@@ -88,8 +86,7 @@ class AnyTask(ABC):
|
|
88
86
|
Any other tasks depends on the current task, will be `started` once the current task is `ready`.
|
89
87
|
|
90
88
|
This method should be implemented to define the criteria for considering the task
|
91
|
-
`ready`. The specifics of this completion depend on the task's
|
92
|
-
nature and the subclass implementation.
|
89
|
+
`ready`. The specifics of this completion depend on the task's nature and the subclass implementation.
|
93
90
|
|
94
91
|
Returns:
|
95
92
|
bool: True if the task is completed, False otherwise.
|
@@ -308,6 +305,7 @@ class AnyTask(ABC):
|
|
308
305
|
is_async: bool = False,
|
309
306
|
show_done_info: bool = True,
|
310
307
|
should_clear_xcom: bool = False,
|
308
|
+
should_stop_looper: bool = False,
|
311
309
|
) -> Callable[..., Any]:
|
312
310
|
"""
|
313
311
|
Converts the current task into a callable function.
|
zrb/task/base_task/base_task.py
CHANGED
@@ -26,6 +26,7 @@ from zrb.task.any_task_event_handler import (
|
|
26
26
|
from zrb.task.base_task.component.base_task_model import BaseTaskModel
|
27
27
|
from zrb.task.base_task.component.renderer import Renderer
|
28
28
|
from zrb.task.base_task.component.trackers import AttemptTracker, FinishTracker
|
29
|
+
from zrb.task.looper import looper
|
29
30
|
from zrb.task.parallel import AnyParallel
|
30
31
|
from zrb.task_env.env import Env, PrivateEnv
|
31
32
|
from zrb.task_env.env_file import EnvFile
|
@@ -71,10 +72,10 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
|
|
71
72
|
):
|
72
73
|
# init properties
|
73
74
|
retry_interval = retry_interval if retry_interval >= 0 else 0
|
74
|
-
checking_interval = checking_interval if checking_interval > 0 else 0.
|
75
|
+
checking_interval = checking_interval if checking_interval > 0 else 0.05
|
75
76
|
retry = retry if retry >= 0 else 0
|
76
77
|
# init parent classes
|
77
|
-
FinishTracker.__init__(self)
|
78
|
+
FinishTracker.__init__(self, checking_interval=checking_interval)
|
78
79
|
Renderer.__init__(self)
|
79
80
|
AttemptTracker.__init__(self, retry=retry)
|
80
81
|
BaseTaskModel.__init__(
|
@@ -140,7 +141,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
|
|
140
141
|
xcom_dir = self.__get_xcom_dir()
|
141
142
|
xcom_file = os.path.join(xcom_dir, key)
|
142
143
|
with open(xcom_file, "w") as f:
|
143
|
-
f.write(value)
|
144
|
+
f.write(f"{value}")
|
144
145
|
|
145
146
|
def get_xcom(self, key: str) -> str:
|
146
147
|
self.__ensure_xcom_dir_exists()
|
@@ -164,6 +165,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
|
|
164
165
|
is_async: bool = False,
|
165
166
|
show_done_info: bool = True,
|
166
167
|
should_clear_xcom: bool = False,
|
168
|
+
should_stop_looper: bool = False,
|
167
169
|
) -> Callable[..., Any]:
|
168
170
|
async def function(*args: Any, **kwargs: Any) -> Any:
|
169
171
|
self.log_info("Copy task")
|
@@ -175,6 +177,8 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
|
|
175
177
|
kwargs=kwargs,
|
176
178
|
show_done_info=show_done_info,
|
177
179
|
)
|
180
|
+
if should_stop_looper:
|
181
|
+
looper.stop()
|
178
182
|
if should_clear_xcom:
|
179
183
|
self_cp.clear_xcom()
|
180
184
|
return result
|
@@ -229,7 +233,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
|
|
229
233
|
await run_async(self._on_retry, self)
|
230
234
|
|
231
235
|
async def check(self) -> bool:
|
232
|
-
return await self._is_done
|
236
|
+
return await run_async(self._is_done)
|
233
237
|
|
234
238
|
def inject_envs(self):
|
235
239
|
super().inject_envs()
|
@@ -311,7 +315,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
|
|
311
315
|
if self.__is_check_triggered:
|
312
316
|
self.log_debug("Waiting readiness flag to be set")
|
313
317
|
while not self.__is_ready:
|
314
|
-
await asyncio.sleep(
|
318
|
+
await asyncio.sleep(self._checking_interval)
|
315
319
|
return True
|
316
320
|
self.__is_check_triggered = True
|
317
321
|
check_result = await self._check()
|
@@ -332,7 +336,7 @@ class BaseTask(FinishTracker, AttemptTracker, Renderer, BaseTaskModel, AnyTask):
|
|
332
336
|
self.log_debug("Waiting execution to be started")
|
333
337
|
while not self.__is_execution_started:
|
334
338
|
# Don't start checking before the execution itself has been started
|
335
|
-
await asyncio.sleep(0
|
339
|
+
await asyncio.sleep(self._checking_interval / 2.0)
|
336
340
|
check_coroutines: Iterable[asyncio.Task] = []
|
337
341
|
for checker_task in self._get_checkers():
|
338
342
|
checker_task._set_execution_id(self.get_execution_id())
|
@@ -2,7 +2,7 @@ import asyncio
|
|
2
2
|
import time
|
3
3
|
|
4
4
|
from zrb.helper.typecheck import typechecked
|
5
|
-
from zrb.helper.typing import Optional
|
5
|
+
from zrb.helper.typing import Optional, Union
|
6
6
|
|
7
7
|
LOG_NAME_LENGTH = 20
|
8
8
|
|
@@ -51,9 +51,10 @@ class AttemptTracker:
|
|
51
51
|
|
52
52
|
@typechecked
|
53
53
|
class FinishTracker:
|
54
|
-
def __init__(self):
|
54
|
+
def __init__(self, checking_interval: Union[float, int]):
|
55
55
|
self.__execution_queue: Optional[asyncio.Queue] = None
|
56
56
|
self.__counter = 0
|
57
|
+
self.__checking_interval = checking_interval
|
57
58
|
|
58
59
|
async def _mark_awaited(self):
|
59
60
|
if self.__execution_queue is None:
|
@@ -69,5 +70,5 @@ class FinishTracker:
|
|
69
70
|
|
70
71
|
async def _is_done(self) -> bool:
|
71
72
|
while self.__execution_queue is None:
|
72
|
-
await asyncio.sleep(0
|
73
|
+
await asyncio.sleep(self.__checking_interval / 2.0)
|
73
74
|
return await self.__execution_queue.get()
|
zrb/task/checker.py
CHANGED
@@ -44,7 +44,7 @@ class Checker(BaseTask):
|
|
44
44
|
on_ready: Optional[OnReady] = None,
|
45
45
|
on_retry: Optional[OnRetry] = None,
|
46
46
|
on_failed: Optional[OnFailed] = None,
|
47
|
-
checking_interval: Union[int, float] = 0
|
47
|
+
checking_interval: Union[int, float] = 0,
|
48
48
|
progress_interval: Union[int, float] = 30,
|
49
49
|
expected_result: bool = True,
|
50
50
|
should_execute: Union[bool, str, Callable[..., bool]] = True,
|
@@ -83,15 +83,15 @@ class Checker(BaseTask):
|
|
83
83
|
while True:
|
84
84
|
self._should_show_progress = wait_time >= self._progress_interval
|
85
85
|
inspect_result = await self.inspect(*args, **kwargs)
|
86
|
-
if inspect_result == self._expected_result:
|
86
|
+
if inspect_result is not None and inspect_result == self._expected_result:
|
87
87
|
return True
|
88
88
|
if wait_time >= self._progress_interval:
|
89
89
|
wait_time = 0
|
90
90
|
await asyncio.sleep(self._checking_interval)
|
91
91
|
wait_time += self._checking_interval
|
92
92
|
|
93
|
-
async def inspect(self, *args: Any, **kwargs: Any) -> bool:
|
94
|
-
return
|
93
|
+
async def inspect(self, *args: Any, **kwargs: Any) -> Optional[bool]:
|
94
|
+
return None
|
95
95
|
|
96
96
|
def show_progress(self, message: str):
|
97
97
|
if self._should_show_progress:
|
zrb/task/cmd_task.py
CHANGED
@@ -199,8 +199,17 @@ class CmdTask(BaseTask):
|
|
199
199
|
raise_error: bool = True,
|
200
200
|
is_async: bool = False,
|
201
201
|
show_done_info: bool = True,
|
202
|
+
should_clear_xcom: bool = False,
|
203
|
+
should_stop_looper: bool = False,
|
202
204
|
) -> Callable[..., CmdResult]:
|
203
|
-
return super().to_function(
|
205
|
+
return super().to_function(
|
206
|
+
env_prefix=env_prefix,
|
207
|
+
raise_error=raise_error,
|
208
|
+
is_async=is_async,
|
209
|
+
show_done_info=show_done_info,
|
210
|
+
should_clear_xcom=should_clear_xcom,
|
211
|
+
should_stop_looper=should_stop_looper,
|
212
|
+
)
|
204
213
|
|
205
214
|
def print_result(self, result: CmdResult):
|
206
215
|
if not self._should_print_cmd_result or result.output == "":
|
zrb/task/decorator.py
CHANGED
@@ -43,9 +43,9 @@ def python_task(
|
|
43
43
|
on_retry: Optional[OnRetry] = None,
|
44
44
|
on_failed: Optional[OnFailed] = None,
|
45
45
|
checkers: Iterable[AnyTask] = [],
|
46
|
-
checking_interval: float = 0
|
46
|
+
checking_interval: Union[float, int] = 0,
|
47
47
|
retry: int = 2,
|
48
|
-
retry_interval: float = 1,
|
48
|
+
retry_interval: Union[float, int] = 1,
|
49
49
|
should_execute: Union[bool, str, Callable[..., bool]] = True,
|
50
50
|
return_upstream_result: bool = False,
|
51
51
|
runner: Optional[Runner] = None,
|
zrb/task/docker_compose_task.py
CHANGED
@@ -115,9 +115,9 @@ class DockerComposeTask(CmdTask):
|
|
115
115
|
on_retry: Optional[OnRetry] = None,
|
116
116
|
on_failed: Optional[OnFailed] = None,
|
117
117
|
checkers: Iterable[AnyTask] = [],
|
118
|
-
checking_interval: float = 0
|
118
|
+
checking_interval: Union[float, int] = 0,
|
119
119
|
retry: int = 2,
|
120
|
-
retry_interval: float = 1,
|
120
|
+
retry_interval: Union[float, int] = 1,
|
121
121
|
max_output_line: int = 1000,
|
122
122
|
max_error_line: int = 1000,
|
123
123
|
preexec_fn: Optional[Callable[[], Any]] = os.setsid,
|
zrb/task/http_checker.py
CHANGED
@@ -87,7 +87,7 @@ class HTTPChecker(Checker):
|
|
87
87
|
on_ready: Optional[OnReady] = None,
|
88
88
|
on_retry: Optional[OnRetry] = None,
|
89
89
|
on_failed: Optional[OnFailed] = None,
|
90
|
-
checking_interval: Union[int, float] = 0
|
90
|
+
checking_interval: Union[int, float] = 0,
|
91
91
|
progress_interval: Union[int, float] = 5,
|
92
92
|
expected_result: bool = True,
|
93
93
|
should_execute: Union[bool, JinjaTemplate, Callable[..., bool]] = True,
|
@@ -133,8 +133,17 @@ class HTTPChecker(Checker):
|
|
133
133
|
raise_error: bool = True,
|
134
134
|
is_async: bool = False,
|
135
135
|
show_done_info: bool = True,
|
136
|
+
should_clear_xcom: bool = False,
|
137
|
+
should_stop_looper: bool = False,
|
136
138
|
) -> Callable[..., bool]:
|
137
|
-
return super().to_function(
|
139
|
+
return super().to_function(
|
140
|
+
env_prefix=env_prefix,
|
141
|
+
raise_error=raise_error,
|
142
|
+
is_async=is_async,
|
143
|
+
show_done_info=show_done_info,
|
144
|
+
should_clear_xcom=should_clear_xcom,
|
145
|
+
should_stop_looper=should_stop_looper,
|
146
|
+
)
|
138
147
|
|
139
148
|
async def run(self, *args: Any, **kwargs: Any) -> bool:
|
140
149
|
self._config = HttpConnectionConfig(
|
zrb/task/looper.py
ADDED
@@ -0,0 +1,43 @@
|
|
1
|
+
from zrb.helper.accessories.color import colored
|
2
|
+
from zrb.helper.callable import run_async
|
3
|
+
from zrb.helper.log import logger
|
4
|
+
from zrb.helper.typing import Callable, List, Mapping, Optional
|
5
|
+
|
6
|
+
logger.debug(colored("Loading zrb.task.looper", attrs=["dark"]))
|
7
|
+
|
8
|
+
|
9
|
+
class Looper:
|
10
|
+
def __init__(self):
|
11
|
+
self._queue: Mapping[str, List[Optional[bool]]] = {}
|
12
|
+
self._should_stop = False
|
13
|
+
|
14
|
+
async def pop(self, identifier: str) -> Optional[bool]:
|
15
|
+
if identifier not in self._queue or len(self._queue[identifier]) == 0:
|
16
|
+
return None
|
17
|
+
return self._queue[identifier].pop(0)
|
18
|
+
|
19
|
+
def stop(self):
|
20
|
+
self._should_stop = True
|
21
|
+
|
22
|
+
def is_registered(self, identifier: str) -> bool:
|
23
|
+
return identifier in self._queue
|
24
|
+
|
25
|
+
async def register(self, identifier: str, function: Callable[..., Optional[bool]]):
|
26
|
+
if identifier in self._queue:
|
27
|
+
return
|
28
|
+
self._queue[identifier] = []
|
29
|
+
while not self._should_stop:
|
30
|
+
try:
|
31
|
+
result = await run_async(function)
|
32
|
+
if result is not None:
|
33
|
+
if not result:
|
34
|
+
continue
|
35
|
+
while len(self._queue[identifier]) > 1000:
|
36
|
+
self._queue[identifier].pop(0)
|
37
|
+
self._queue[identifier].append(result)
|
38
|
+
except KeyboardInterrupt:
|
39
|
+
self.stop()
|
40
|
+
break
|
41
|
+
|
42
|
+
|
43
|
+
looper = Looper()
|
zrb/task/path_checker.py
CHANGED
@@ -56,7 +56,7 @@ class PathChecker(Checker):
|
|
56
56
|
on_failed: Optional[OnFailed] = None,
|
57
57
|
path: JinjaTemplate = "",
|
58
58
|
ignored_path: Union[JinjaTemplate, Iterable[JinjaTemplate]] = [],
|
59
|
-
checking_interval: Union[int, float] = 0
|
59
|
+
checking_interval: Union[int, float] = 0,
|
60
60
|
progress_interval: Union[int, float] = 5,
|
61
61
|
expected_result: bool = True,
|
62
62
|
should_execute: Union[bool, JinjaTemplate, Callable[..., bool]] = True,
|
@@ -99,8 +99,17 @@ class PathChecker(Checker):
|
|
99
99
|
raise_error: bool = True,
|
100
100
|
is_async: bool = False,
|
101
101
|
show_done_info: bool = True,
|
102
|
+
should_clear_xcom: bool = False,
|
103
|
+
should_stop_looper: bool = False,
|
102
104
|
) -> Callable[..., bool]:
|
103
|
-
return super().to_function(
|
105
|
+
return super().to_function(
|
106
|
+
env_prefix=env_prefix,
|
107
|
+
raise_error=raise_error,
|
108
|
+
is_async=is_async,
|
109
|
+
show_done_info=show_done_info,
|
110
|
+
should_clear_xcom=should_clear_xcom,
|
111
|
+
should_stop_looper=should_stop_looper,
|
112
|
+
)
|
104
113
|
|
105
114
|
async def run(self, *args: Any, **kwargs: Any) -> bool:
|
106
115
|
self._rendered_path = self.render_str(self._path)
|