jettask 0.2.18__py3-none-any.whl → 0.2.20__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.
- jettask/__init__.py +60 -2
- jettask/cli.py +314 -228
- jettask/config/__init__.py +9 -1
- jettask/config/config.py +245 -0
- jettask/config/env_loader.py +381 -0
- jettask/config/lua_scripts.py +158 -0
- jettask/config/nacos_config.py +132 -5
- jettask/core/__init__.py +1 -1
- jettask/core/app.py +1573 -666
- jettask/core/app_importer.py +33 -16
- jettask/core/container.py +532 -0
- jettask/core/task.py +1 -4
- jettask/core/unified_manager_base.py +2 -2
- jettask/executor/__init__.py +38 -0
- jettask/executor/core.py +625 -0
- jettask/executor/executor.py +338 -0
- jettask/executor/orchestrator.py +290 -0
- jettask/executor/process_entry.py +638 -0
- jettask/executor/task_executor.py +317 -0
- jettask/messaging/__init__.py +68 -0
- jettask/messaging/event_pool.py +2188 -0
- jettask/messaging/reader.py +519 -0
- jettask/messaging/registry.py +266 -0
- jettask/messaging/scanner.py +369 -0
- jettask/messaging/sender.py +312 -0
- jettask/persistence/__init__.py +118 -0
- jettask/persistence/backlog_monitor.py +567 -0
- jettask/{backend/data_access.py → persistence/base.py} +58 -57
- jettask/persistence/consumer.py +315 -0
- jettask/{core → persistence}/db_manager.py +23 -22
- jettask/persistence/maintenance.py +81 -0
- jettask/persistence/message_consumer.py +259 -0
- jettask/{backend/namespace_data_access.py → persistence/namespace.py} +66 -98
- jettask/persistence/offline_recovery.py +196 -0
- jettask/persistence/queue_discovery.py +215 -0
- jettask/persistence/task_persistence.py +218 -0
- jettask/persistence/task_updater.py +583 -0
- jettask/scheduler/__init__.py +2 -2
- jettask/scheduler/loader.py +6 -5
- jettask/scheduler/run_scheduler.py +1 -1
- jettask/scheduler/scheduler.py +7 -7
- jettask/scheduler/{unified_scheduler_manager.py → scheduler_coordinator.py} +18 -13
- jettask/task/__init__.py +16 -0
- jettask/{router.py → task/router.py} +26 -8
- jettask/task/task_center/__init__.py +9 -0
- jettask/task/task_executor.py +318 -0
- jettask/task/task_registry.py +291 -0
- jettask/test_connection_monitor.py +73 -0
- jettask/utils/__init__.py +31 -1
- jettask/{monitor/run_backlog_collector.py → utils/backlog_collector.py} +1 -1
- jettask/utils/db_connector.py +1629 -0
- jettask/{db_init.py → utils/db_init.py} +1 -1
- jettask/utils/rate_limit/__init__.py +30 -0
- jettask/utils/rate_limit/concurrency_limiter.py +665 -0
- jettask/utils/rate_limit/config.py +145 -0
- jettask/utils/rate_limit/limiter.py +41 -0
- jettask/utils/rate_limit/manager.py +269 -0
- jettask/utils/rate_limit/qps_limiter.py +154 -0
- jettask/utils/rate_limit/task_limiter.py +384 -0
- jettask/utils/serializer.py +3 -0
- jettask/{monitor/stream_backlog_monitor.py → utils/stream_backlog.py} +14 -6
- jettask/utils/time_sync.py +173 -0
- jettask/webui/__init__.py +27 -0
- jettask/{api/v1 → webui/api}/alerts.py +1 -1
- jettask/{api/v1 → webui/api}/analytics.py +2 -2
- jettask/{api/v1 → webui/api}/namespaces.py +1 -1
- jettask/{api/v1 → webui/api}/overview.py +1 -1
- jettask/{api/v1 → webui/api}/queues.py +3 -3
- jettask/{api/v1 → webui/api}/scheduled.py +1 -1
- jettask/{api/v1 → webui/api}/settings.py +1 -1
- jettask/{api.py → webui/app.py} +253 -145
- jettask/webui/namespace_manager/__init__.py +10 -0
- jettask/{multi_namespace_consumer.py → webui/namespace_manager/multi.py} +69 -22
- jettask/{unified_consumer_manager.py → webui/namespace_manager/unified.py} +1 -1
- jettask/{run.py → webui/run.py} +2 -2
- jettask/{services → webui/services}/__init__.py +1 -3
- jettask/{services → webui/services}/overview_service.py +34 -16
- jettask/{services → webui/services}/queue_service.py +1 -1
- jettask/{backend → webui/services}/queue_stats_v2.py +1 -1
- jettask/{services → webui/services}/settings_service.py +1 -1
- jettask/worker/__init__.py +53 -0
- jettask/worker/lifecycle.py +1507 -0
- jettask/worker/manager.py +583 -0
- jettask/{core/offline_worker_recovery.py → worker/recovery.py} +268 -175
- {jettask-0.2.18.dist-info → jettask-0.2.20.dist-info}/METADATA +2 -71
- jettask-0.2.20.dist-info/RECORD +145 -0
- jettask/__main__.py +0 -140
- jettask/api/__init__.py +0 -103
- jettask/backend/__init__.py +0 -1
- jettask/backend/api/__init__.py +0 -3
- jettask/backend/api/v1/__init__.py +0 -17
- jettask/backend/api/v1/monitoring.py +0 -431
- jettask/backend/api/v1/namespaces.py +0 -504
- jettask/backend/api/v1/queues.py +0 -342
- jettask/backend/api/v1/tasks.py +0 -367
- jettask/backend/core/__init__.py +0 -3
- jettask/backend/core/cache.py +0 -221
- jettask/backend/core/database.py +0 -200
- jettask/backend/core/exceptions.py +0 -102
- jettask/backend/dependencies.py +0 -261
- jettask/backend/init_meta_db.py +0 -158
- jettask/backend/main.py +0 -1426
- jettask/backend/main_unified.py +0 -78
- jettask/backend/main_v2.py +0 -394
- jettask/backend/models/__init__.py +0 -3
- jettask/backend/models/requests.py +0 -236
- jettask/backend/models/responses.py +0 -230
- jettask/backend/namespace_api_old.py +0 -267
- jettask/backend/services/__init__.py +0 -3
- jettask/backend/start.py +0 -42
- jettask/backend/unified_api_router.py +0 -1541
- jettask/cleanup_deprecated_tables.sql +0 -16
- jettask/core/consumer_manager.py +0 -1695
- jettask/core/delay_scanner.py +0 -256
- jettask/core/event_pool.py +0 -1700
- jettask/core/heartbeat_process.py +0 -222
- jettask/core/task_batch.py +0 -153
- jettask/core/worker_scanner.py +0 -271
- jettask/executors/__init__.py +0 -5
- jettask/executors/asyncio.py +0 -876
- jettask/executors/base.py +0 -30
- jettask/executors/common.py +0 -148
- jettask/executors/multi_asyncio.py +0 -309
- jettask/gradio_app.py +0 -570
- jettask/integrated_gradio_app.py +0 -1088
- jettask/main.py +0 -0
- jettask/monitoring/__init__.py +0 -3
- jettask/pg_consumer.py +0 -1896
- jettask/run_monitor.py +0 -22
- jettask/run_webui.py +0 -148
- jettask/scheduler/multi_namespace_scheduler.py +0 -294
- jettask/scheduler/unified_manager.py +0 -450
- jettask/task_center_client.py +0 -150
- jettask/utils/serializer_optimized.py +0 -33
- jettask/webui_exceptions.py +0 -67
- jettask-0.2.18.dist-info/RECORD +0 -150
- /jettask/{constants.py → config/constants.py} +0 -0
- /jettask/{backend/config.py → config/task_center.py} +0 -0
- /jettask/{pg_consumer → messaging/pg_consumer}/pg_consumer_v2.py +0 -0
- /jettask/{pg_consumer → messaging/pg_consumer}/sql/add_execution_time_field.sql +0 -0
- /jettask/{pg_consumer → messaging/pg_consumer}/sql/create_new_tables.sql +0 -0
- /jettask/{pg_consumer → messaging/pg_consumer}/sql/create_tables_v3.sql +0 -0
- /jettask/{pg_consumer → messaging/pg_consumer}/sql/migrate_to_new_structure.sql +0 -0
- /jettask/{pg_consumer → messaging/pg_consumer}/sql/modify_time_fields.sql +0 -0
- /jettask/{pg_consumer → messaging/pg_consumer}/sql_utils.py +0 -0
- /jettask/{models.py → persistence/models.py} +0 -0
- /jettask/scheduler/{manager.py → task_crud.py} +0 -0
- /jettask/{schema.sql → schemas/schema.sql} +0 -0
- /jettask/{task_center.py → task/task_center/client.py} +0 -0
- /jettask/{monitoring → utils}/file_watcher.py +0 -0
- /jettask/{services/redis_monitor_service.py → utils/redis_monitor.py} +0 -0
- /jettask/{api/v1 → webui/api}/__init__.py +0 -0
- /jettask/{webui_config.py → webui/config.py} +0 -0
- /jettask/{webui_models → webui/models}/__init__.py +0 -0
- /jettask/{webui_models → webui/models}/namespace.py +0 -0
- /jettask/{services → webui/services}/alert_service.py +0 -0
- /jettask/{services → webui/services}/analytics_service.py +0 -0
- /jettask/{services → webui/services}/scheduled_task_service.py +0 -0
- /jettask/{services → webui/services}/task_service.py +0 -0
- /jettask/{webui_sql → webui/sql}/batch_upsert_functions.sql +0 -0
- /jettask/{webui_sql → webui/sql}/verify_database.sql +0 -0
- {jettask-0.2.18.dist-info → jettask-0.2.20.dist-info}/WHEEL +0 -0
- {jettask-0.2.18.dist-info → jettask-0.2.20.dist-info}/entry_points.txt +0 -0
- {jettask-0.2.18.dist-info → jettask-0.2.20.dist-info}/licenses/LICENSE +0 -0
- {jettask-0.2.18.dist-info → jettask-0.2.20.dist-info}/top_level.txt +0 -0
@@ -17,9 +17,9 @@ from datetime import datetime
|
|
17
17
|
# 添加项目路径
|
18
18
|
sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))))
|
19
19
|
|
20
|
-
from jettask.
|
21
|
-
from jettask.
|
22
|
-
|
20
|
+
from jettask.persistence import PostgreSQLConsumer
|
21
|
+
from jettask.webui.config import PostgreSQLConfig, RedisConfig
|
22
|
+
# ConsumerStrategy 已移除,现在只使用 HEARTBEAT 策略
|
23
23
|
from sqlalchemy.ext.asyncio import create_async_engine, AsyncSession
|
24
24
|
from sqlalchemy.orm import sessionmaker
|
25
25
|
from sqlalchemy import text
|
@@ -46,6 +46,7 @@ class NamespaceConsumerProcess:
|
|
46
46
|
"""
|
47
47
|
self.namespace_info = namespace_info
|
48
48
|
self.process: Optional[mp.Process] = None
|
49
|
+
self.shutdown_event = mp.Event() # 用于优雅退出的事件
|
49
50
|
|
50
51
|
def start(self):
|
51
52
|
"""启动进程"""
|
@@ -65,12 +66,20 @@ class NamespaceConsumerProcess:
|
|
65
66
|
"""停止进程"""
|
66
67
|
if self.process and self.process.is_alive():
|
67
68
|
logger.info(f"停止命名空间 {self.namespace_info['name']} 的消费进程")
|
68
|
-
|
69
|
-
self.
|
69
|
+
# 先发送优雅退出信号
|
70
|
+
self.shutdown_event.set()
|
71
|
+
# 等待进程正常退出(7秒:5秒清理超时 + 2秒缓冲)
|
72
|
+
self.process.join(timeout=7)
|
70
73
|
if self.process.is_alive():
|
71
|
-
logger.warning(f"
|
74
|
+
logger.warning(f"等待优雅退出超时(7秒),发送 SIGTERM 信号")
|
75
|
+
self.process.terminate()
|
76
|
+
self.process.join(timeout=3)
|
77
|
+
if self.process.is_alive():
|
78
|
+
logger.warning(f"SIGTERM 超时(3秒),强制 SIGKILL")
|
72
79
|
self.process.kill()
|
73
|
-
self.process.join()
|
80
|
+
self.process.join(timeout=2)
|
81
|
+
if self.process.is_alive():
|
82
|
+
logger.error(f"SIGKILL 后进程仍然存活,可能存在严重问题")
|
74
83
|
|
75
84
|
def is_alive(self) -> bool:
|
76
85
|
"""检查进程是否存活"""
|
@@ -81,25 +90,42 @@ class NamespaceConsumerProcess:
|
|
81
90
|
# 设置信号处理
|
82
91
|
signal.signal(signal.SIGTERM, self._signal_handler)
|
83
92
|
signal.signal(signal.SIGINT, self._signal_handler)
|
84
|
-
|
93
|
+
|
85
94
|
# 创建新的事件循环
|
86
95
|
loop = asyncio.new_event_loop()
|
87
96
|
asyncio.set_event_loop(loop)
|
88
|
-
|
97
|
+
|
98
|
+
consumer = None
|
89
99
|
try:
|
90
|
-
|
100
|
+
# 传递 consumer 引用以便在信号处理中使用
|
101
|
+
consumer = loop.run_until_complete(self._async_run())
|
91
102
|
except KeyboardInterrupt:
|
92
103
|
logger.info(f"命名空间 {self.namespace_info['name']} 的消费进程收到中断信号")
|
93
104
|
except Exception as e:
|
94
105
|
logger.error(f"命名空间 {self.namespace_info['name']} 的消费进程异常退出: {e}", exc_info=True)
|
95
106
|
finally:
|
107
|
+
# 确保执行清理(带超时)
|
108
|
+
if consumer:
|
109
|
+
try:
|
110
|
+
logger.info(f"执行命名空间 {self.namespace_info['name']} 的消费者清理")
|
111
|
+
# 创建一个带超时的任务
|
112
|
+
async def cleanup_with_timeout():
|
113
|
+
try:
|
114
|
+
await asyncio.wait_for(consumer.stop(), timeout=5.0)
|
115
|
+
except asyncio.TimeoutError:
|
116
|
+
logger.warning(f"外层清理超时(5秒),强制退出")
|
117
|
+
|
118
|
+
loop.run_until_complete(cleanup_with_timeout())
|
119
|
+
except Exception as e:
|
120
|
+
logger.error(f"清理消费者时出错: {e}")
|
96
121
|
loop.close()
|
97
122
|
|
98
123
|
async def _async_run(self):
|
99
124
|
"""异步运行消费者"""
|
100
125
|
namespace_name = self.namespace_info.get('name', 'unknown')
|
101
126
|
logger.info(f"开始初始化命名空间 {namespace_name} 的消费者")
|
102
|
-
|
127
|
+
|
128
|
+
consumer = None
|
103
129
|
try:
|
104
130
|
# 创建配置
|
105
131
|
pg_config_data = self.namespace_info.get('pg_config', {})
|
@@ -131,7 +157,8 @@ class NamespaceConsumerProcess:
|
|
131
157
|
filtered_config = {k: v for k, v in redis_config_data.items() if k in valid_fields}
|
132
158
|
redis_config = RedisConfig(**filtered_config)
|
133
159
|
|
134
|
-
|
160
|
+
print(f'{pg_config=}')
|
161
|
+
print(f'{redis_config=}')
|
135
162
|
# 创建消费者实例
|
136
163
|
consumer = PostgreSQLConsumer(
|
137
164
|
pg_config=pg_config,
|
@@ -139,7 +166,7 @@ class NamespaceConsumerProcess:
|
|
139
166
|
prefix=self.namespace_info.get('redis_prefix', 'jettask'),
|
140
167
|
namespace_id=self.namespace_info.get('id'),
|
141
168
|
namespace_name=self.namespace_info.get('name'),
|
142
|
-
consumer_strategy
|
169
|
+
# consumer_strategy 参数已移除,现在只使用 HEARTBEAT 策略
|
143
170
|
)
|
144
171
|
|
145
172
|
logger.info(f"命名空间 {namespace_name} 的消费者实例创建成功,准备启动")
|
@@ -147,25 +174,45 @@ class NamespaceConsumerProcess:
|
|
147
174
|
# 启动消费者
|
148
175
|
await consumer.start()
|
149
176
|
logger.info(f"命名空间 {namespace_name} 的消费者已启动,进入运行状态")
|
150
|
-
|
177
|
+
|
151
178
|
# 保持运行直到收到停止信号
|
152
179
|
try:
|
153
|
-
while
|
154
|
-
await asyncio.sleep(
|
155
|
-
# 可以在这里添加健康检查逻辑
|
180
|
+
while not self.shutdown_event.is_set():
|
181
|
+
await asyncio.sleep(1) # 每秒检查一次退出信号
|
156
182
|
except asyncio.CancelledError:
|
157
183
|
logger.info(f"命名空间 {namespace_name} 的消费者收到取消信号")
|
158
|
-
|
159
|
-
|
160
|
-
|
184
|
+
finally:
|
185
|
+
# 确保清理(带超时)
|
186
|
+
logger.info(f"命名空间 {namespace_name} 开始执行优雅退出")
|
187
|
+
try:
|
188
|
+
# 设置 5 秒超时,避免因网络问题导致清理卡住
|
189
|
+
await asyncio.wait_for(consumer.stop(), timeout=5.0)
|
190
|
+
logger.info(f"命名空间 {namespace_name} 清理完成")
|
191
|
+
except asyncio.TimeoutError:
|
192
|
+
logger.warning(f"命名空间 {namespace_name} 清理超时(5秒),强制退出")
|
193
|
+
except Exception as e:
|
194
|
+
logger.error(f"命名空间 {namespace_name} 清理失败: {e}")
|
195
|
+
|
161
196
|
except Exception as e:
|
162
197
|
logger.error(f"命名空间 {namespace_name} 的消费者启动失败: {e}", exc_info=True)
|
198
|
+
# 确保清理(带超时)
|
199
|
+
if consumer:
|
200
|
+
try:
|
201
|
+
await asyncio.wait_for(consumer.stop(), timeout=5.0)
|
202
|
+
except asyncio.TimeoutError:
|
203
|
+
logger.warning(f"清理失败的消费者超时,跳过")
|
204
|
+
except Exception as cleanup_error:
|
205
|
+
logger.error(f"清理失败的消费者时出错: {cleanup_error}")
|
163
206
|
raise
|
207
|
+
finally:
|
208
|
+
# 返回 consumer 实例以便在外层 finally 中使用
|
209
|
+
return consumer
|
164
210
|
|
165
211
|
def _signal_handler(self, signum, frame):
|
166
|
-
"""信号处理器"""
|
212
|
+
"""信号处理器 - 触发优雅退出"""
|
167
213
|
logger.info(f"命名空间 {self.namespace_info['name']} 的消费进程收到信号 {signum}")
|
168
|
-
|
214
|
+
# 设置退出事件,让主循环优雅退出
|
215
|
+
self.shutdown_event.set()
|
169
216
|
|
170
217
|
|
171
218
|
class MultiNamespaceConsumerManager:
|
@@ -7,7 +7,7 @@ import logging
|
|
7
7
|
import multiprocessing
|
8
8
|
from typing import Dict, Optional, Set
|
9
9
|
from jettask.core.unified_manager_base import UnifiedManagerBase
|
10
|
-
from .
|
10
|
+
from .multi import NamespaceConsumerProcess
|
11
11
|
|
12
12
|
logger = logging.getLogger(__name__)
|
13
13
|
|
jettask/{run.py → webui/run.py}
RENAMED
@@ -11,7 +11,7 @@ import sys
|
|
11
11
|
import os
|
12
12
|
sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))))
|
13
13
|
|
14
|
-
from jettask.
|
14
|
+
from jettask.webui.app import app, monitor
|
15
15
|
import uvicorn
|
16
16
|
|
17
17
|
def main():
|
@@ -35,7 +35,7 @@ def main():
|
|
35
35
|
|
36
36
|
# 运行服务器
|
37
37
|
uvicorn.run(
|
38
|
-
"jettask.webui.
|
38
|
+
"jettask.webui.app:app",
|
39
39
|
host=args.host,
|
40
40
|
port=args.port,
|
41
41
|
log_level="info",
|
@@ -10,15 +10,13 @@ from .alert_service import AlertService
|
|
10
10
|
from .analytics_service import AnalyticsService
|
11
11
|
from .settings_service import SettingsService
|
12
12
|
from .task_service import TaskService
|
13
|
-
from .redis_monitor_service import RedisMonitorService
|
14
13
|
|
15
14
|
__all__ = [
|
16
15
|
'OverviewService',
|
17
|
-
'QueueService',
|
16
|
+
'QueueService',
|
18
17
|
'ScheduledTaskService',
|
19
18
|
'AlertService',
|
20
19
|
'AnalyticsService',
|
21
20
|
'SettingsService',
|
22
21
|
'TaskService',
|
23
|
-
'RedisMonitorService'
|
24
22
|
]
|
@@ -11,7 +11,7 @@ from sqlalchemy import text
|
|
11
11
|
from sqlalchemy.ext.asyncio import AsyncSession
|
12
12
|
|
13
13
|
from jettask.schemas import TimeRangeQuery
|
14
|
-
from jettask.
|
14
|
+
from jettask.persistence.db_manager import get_db_manager
|
15
15
|
|
16
16
|
logger = logging.getLogger(__name__)
|
17
17
|
|
@@ -84,26 +84,44 @@ class OverviewService:
|
|
84
84
|
'workers': 0
|
85
85
|
}
|
86
86
|
|
87
|
+
# 使用注册管理器进行统计,避免 scan
|
88
|
+
from jettask.messaging.registry import QueueRegistry
|
89
|
+
from jettask.task.task_registry import TaskRegistry
|
90
|
+
from jettask.worker.manager import WorkerState as WorkerRegistry
|
91
|
+
|
92
|
+
queue_registry = QueueRegistry(
|
93
|
+
redis_client=None,
|
94
|
+
async_redis_client=redis_client,
|
95
|
+
redis_prefix=namespace
|
96
|
+
)
|
97
|
+
|
98
|
+
task_registry = TaskRegistry(
|
99
|
+
redis_client=None,
|
100
|
+
async_redis_client=redis_client,
|
101
|
+
redis_prefix=namespace
|
102
|
+
)
|
103
|
+
|
104
|
+
worker_registry = WorkerRegistry(
|
105
|
+
redis_client=None,
|
106
|
+
async_redis_client=redis_client,
|
107
|
+
redis_prefix=namespace
|
108
|
+
)
|
109
|
+
|
87
110
|
# 统计队列数量
|
88
|
-
|
89
|
-
|
90
|
-
stats['queues'] += 1
|
91
|
-
|
111
|
+
stats['queues'] = await queue_registry.get_queue_count()
|
112
|
+
|
92
113
|
# 统计任务数量
|
93
|
-
|
94
|
-
|
95
|
-
stats['tasks'] += 1
|
96
|
-
|
114
|
+
stats['tasks'] = await task_registry.get_task_count_from_redis()
|
115
|
+
|
97
116
|
# 统计延迟任务数量
|
98
|
-
|
99
|
-
|
100
|
-
|
117
|
+
delayed_queues = await queue_registry.get_all_delayed_queues()
|
118
|
+
for queue in delayed_queues:
|
119
|
+
delayed_key = f"{namespace}:DELAYED_QUEUE:{queue}"
|
120
|
+
count = await redis_client.zcard(delayed_key)
|
101
121
|
stats['delayed_tasks'] += count
|
102
|
-
|
122
|
+
|
103
123
|
# 统计工作进程数量
|
104
|
-
|
105
|
-
async for _ in redis_client.scan_iter(match=worker_pattern):
|
106
|
-
stats['workers'] += 1
|
124
|
+
stats['workers'] = await worker_registry.get_worker_count()
|
107
125
|
|
108
126
|
return stats
|
109
127
|
|
@@ -9,7 +9,7 @@ from collections import defaultdict
|
|
9
9
|
import redis.asyncio as redis
|
10
10
|
from sqlalchemy import text
|
11
11
|
from sqlalchemy.ext.asyncio import AsyncSession
|
12
|
-
from jettask.constants import is_internal_consumer
|
12
|
+
from jettask.config.constants import is_internal_consumer
|
13
13
|
|
14
14
|
logger = logging.getLogger(__name__)
|
15
15
|
|
@@ -9,7 +9,7 @@ from datetime import datetime
|
|
9
9
|
from sqlalchemy import text
|
10
10
|
from urllib.parse import urlparse
|
11
11
|
|
12
|
-
from jettask.
|
12
|
+
from jettask.persistence.db_manager import get_db_manager
|
13
13
|
from jettask.schemas import (
|
14
14
|
ConfigMode,
|
15
15
|
NamespaceCreate,
|
@@ -0,0 +1,53 @@
|
|
1
|
+
"""
|
2
|
+
Worker 管理模块
|
3
|
+
|
4
|
+
提供 Worker 的创建、生命周期管理、状态监控等功能。
|
5
|
+
|
6
|
+
推荐使用新接口:
|
7
|
+
from jettask.worker import WorkerManager
|
8
|
+
|
9
|
+
manager = WorkerManager(redis, async_redis, 'jettask')
|
10
|
+
worker_id = await manager.start_worker('MyApp', ['queue1'])
|
11
|
+
"""
|
12
|
+
|
13
|
+
# 主要接口
|
14
|
+
from .manager import (
|
15
|
+
WorkerManager,
|
16
|
+
WorkerState, # Worker 状态管理(之前叫 WorkerRegistry)
|
17
|
+
ConsumerManager,
|
18
|
+
WorkerNaming,
|
19
|
+
)
|
20
|
+
|
21
|
+
# 生命周期和状态管理
|
22
|
+
from .lifecycle import (
|
23
|
+
WorkerLifecycle,
|
24
|
+
WorkerStateManager,
|
25
|
+
HeartbeatThreadManager,
|
26
|
+
WorkerScanner,
|
27
|
+
HeartbeatConsumerStrategy, # 兼容性
|
28
|
+
)
|
29
|
+
|
30
|
+
# 恢复
|
31
|
+
from .recovery import OfflineWorkerRecovery
|
32
|
+
|
33
|
+
# 兼容性别名:WorkerRegistry -> WorkerState
|
34
|
+
WorkerRegistry = WorkerState
|
35
|
+
|
36
|
+
__all__ = [
|
37
|
+
# 主要接口
|
38
|
+
'WorkerManager',
|
39
|
+
'WorkerState', # 新名称(推荐使用)
|
40
|
+
'WorkerRegistry', # 兼容性别名
|
41
|
+
'ConsumerManager',
|
42
|
+
'WorkerNaming',
|
43
|
+
|
44
|
+
# 生命周期和状态管理
|
45
|
+
'WorkerLifecycle',
|
46
|
+
'WorkerStateManager',
|
47
|
+
'HeartbeatThreadManager',
|
48
|
+
'WorkerScanner',
|
49
|
+
'HeartbeatConsumerStrategy', # 兼容性
|
50
|
+
|
51
|
+
# 恢复
|
52
|
+
'OfflineWorkerRecovery',
|
53
|
+
]
|