ErisPulse 1.1.13__py3-none-any.whl → 1.1.14.dev1__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.
ErisPulse/__init__.py CHANGED
@@ -1,3 +1,40 @@
1
+ """
2
+ # SDK 核心初始化
3
+
4
+ 提供SDK全局对象构建和初始化功能。
5
+
6
+ ## 主要功能
7
+ - 构建全局sdk对象
8
+ - 预注册核心错误类型
9
+ - 提供SDK初始化入口
10
+ - 集成各核心模块
11
+
12
+ ## API 文档
13
+ ### 核心对象:
14
+ - sdk: 全局SDK命名空间对象
15
+ - sdk.init(): SDK初始化入口函数
16
+
17
+ ### 预注册错误类型:
18
+ - CaughtExternalError: 外部捕获异常
19
+ - InitError: 初始化错误
20
+ - MissingDependencyError: 缺少依赖错误
21
+ - InvalidDependencyError: 无效依赖错误
22
+ - CycleDependencyError: 循环依赖错误
23
+ - ModuleLoadError: 模块加载错误
24
+
25
+ ### 示例用法:
26
+
27
+ ```
28
+ from ErisPulse import sdk
29
+
30
+ # 初始化SDK
31
+ sdk.init()
32
+
33
+ # 访问各模块功能
34
+ sdk.logger.info("SDK已初始化")
35
+ ```
36
+
37
+ """
1
38
 
2
39
  import types
3
40
  sdk = types.SimpleNamespace()
@@ -35,7 +72,8 @@ def init() -> None:
35
72
  logger.info("[Init] SDK 正在初始化...")
36
73
  if env.create_env_file_if_not_exists():
37
74
  logger.info("[Init] 项目首次初始化,建议先配置环境变量")
38
- sys.exit(0)
75
+ if input("是否立即退出?(y/n): ").strip().lower() == "y":
76
+ sys.exit(0)
39
77
  env.load_env_file()
40
78
 
41
79
  sdkModulePath = os.path.join(os.path.dirname(__file__), "modules")
@@ -185,4 +223,4 @@ def init() -> None:
185
223
  raiserr.InitError(f"sdk初始化失败: {e}", exit=True)
186
224
 
187
225
 
188
- sdk.init = init
226
+ sdk.init = init
ErisPulse/__main__.py CHANGED
@@ -1,3 +1,48 @@
1
+ """
2
+ # CLI 入口
3
+
4
+ 提供命令行界面(CLI)用于模块管理、源管理和开发调试。
5
+
6
+ ## 主要功能
7
+ - 模块管理: 安装/卸载/启用/禁用
8
+ - 源管理: 添加/删除/更新源
9
+ - 热重载: 开发时自动重启
10
+ - 彩色终端输出
11
+
12
+ ## 主要命令
13
+ ### 模块管理:
14
+ install: 安装模块
15
+ uninstall: 卸载模块
16
+ enable: 启用模块
17
+ disable: 禁用模块
18
+ list: 列出模块
19
+ update: 更新模块列表
20
+ upgrade: 升级模块
21
+
22
+ ### 源管理:
23
+ origin add: 添加源
24
+ origin del: 删除源
25
+ origin list: 列出源
26
+
27
+ ### 开发调试:
28
+ run: 运行脚本
29
+ --reload: 启用热重载
30
+
31
+ ### 示例用法:
32
+
33
+ ```
34
+ # 安装模块
35
+ epsdk install MyModule
36
+
37
+ # 启用热重载
38
+ epsdk run main.py --reload
39
+
40
+ # 管理源
41
+ epsdk origin add https://example.com/map.json
42
+ ```
43
+
44
+ """
45
+
1
46
  import argparse
2
47
  import os
3
48
  import sys
@@ -1119,7 +1164,6 @@ def main():
1119
1164
  else:
1120
1165
  origin_parser.print_help()
1121
1166
  else:
1122
- # 如果没有提供命令,显示帮助信息
1123
1167
  parser.print_help()
1124
1168
 
1125
1169
  if __name__ == "__main__":
ErisPulse/adapter.py CHANGED
@@ -1,3 +1,50 @@
1
+ """
2
+ # 适配器系统
3
+
4
+ 提供平台适配器基类、消息发送DSL和适配器管理功能。
5
+
6
+ ## 主要功能
7
+ - BaseAdapter: 适配器基类
8
+ - SendDSL: 链式消息发送接口
9
+ - AdapterManager: 适配器管理
10
+ - 适配器注册和生命周期管理
11
+
12
+ ## API 文档
13
+ ### 适配器基类 (BaseAdapter):
14
+ - call_api(): 必须实现的API调用方法
15
+ - start(): 启动适配器
16
+ - shutdown(): 关闭适配器
17
+ - on(): 事件监听装饰器
18
+ - emit(): 触发事件
19
+
20
+ ### 消息发送DSL (SendDSL):
21
+ - To(): 设置消息目标
22
+ - Text(): 发送文本消息
23
+ - 可扩展其他消息类型
24
+
25
+ ### 适配器管理 (AdapterManager):
26
+ - register(): 注册适配器
27
+ - startup(): 启动适配器
28
+ - shutdown(): 关闭所有适配器
29
+ - get(): 获取适配器实例
30
+
31
+ ### 示例用法:
32
+
33
+ ```
34
+ from ErisPulse import sdk
35
+
36
+ # 注册适配器
37
+ sdk.adapter.register("MyPlatform", MyAdapter)
38
+
39
+ # 发送消息
40
+ sdk.adapter.MyPlatform.Send.To("user", "123").Text("Hello")
41
+
42
+ # 启动适配器
43
+ await sdk.adapter.startup()
44
+ ```
45
+
46
+ """
47
+
1
48
  import functools
2
49
  import asyncio
3
50
  from typing import Callable, Any, Dict, List, Type, Optional, Set
ErisPulse/db.py CHANGED
@@ -1,12 +1,75 @@
1
+ """
2
+ # 环境配置
3
+
4
+ 提供键值存储、事务支持、快照和恢复功能,用于管理框架配置数据。
5
+
6
+ ## API 文档
7
+ ### 基本操作:
8
+ - get(key, default=None) -> any: 获取配置项
9
+ - set(key, value) -> bool: 设置配置项
10
+ - delete(key) -> bool: 删除配置项
11
+ - get_all_keys() -> list[str]: 获取所有键名
12
+
13
+ ### 批量操作:
14
+ - get_multi(keys) -> dict: 批量获取键值
15
+ - set_multi(items) -> bool: 批量设置键值
16
+ - delete_multi(keys) -> bool: 批量删除键值
17
+
18
+ ### 事务管理:
19
+ - transaction() -> contextmanager: 创建事务上下文
20
+
21
+ ### 快照管理:
22
+ - snapshot(name=None) -> str: 创建数据库快照
23
+ - restore(snapshot_name) -> bool: 从快照恢复
24
+ - list_snapshots() -> list: 列出所有快照
25
+ - delete_snapshot(name) -> bool: 删除指定快照
26
+ - set_snapshot_interval(seconds): 设置自动快照间隔
27
+
28
+ ### 其他功能:
29
+ - clear(): 清空所有配置
30
+ - load_env_file(): 从env.py加载配置(SDK自动)
31
+
32
+ ### 示例用法:
33
+
34
+ ```
35
+ from ErisPulse import sdk
36
+
37
+ env = sdk.env
38
+
39
+ # 基本操作
40
+ env.set('config_key', 'value')
41
+ value = env.get('config_key')
42
+ value_another = env.config_key # 通过属性访问
43
+ env.config_key = 'value' # 通过属性赋值
44
+
45
+ # 事务使用
46
+ with env.transaction():
47
+ env.set('key1', 'value1')
48
+ env.set('key2', 'value2')
49
+
50
+ # 快照管理
51
+ snapshot_path = env.snapshot()
52
+ env.restore('snapshot_name')
53
+ ```
54
+
55
+ """
56
+
1
57
  import os
2
58
  import json
3
59
  import sqlite3
4
60
  import importlib.util
61
+ import shutil
62
+ import time
63
+ import threading
5
64
  from pathlib import Path
65
+ from datetime import datetime
66
+ from functools import lru_cache
67
+ from .raiserr import raiserr
6
68
 
7
69
  class EnvManager:
8
70
  _instance = None
9
71
  db_path = os.path.join(os.path.dirname(__file__), "config.db")
72
+ SNAPSHOT_DIR = os.path.join(os.path.dirname(__file__), "snapshots")
10
73
 
11
74
  def __new__(cls, *args, **kwargs):
12
75
  if not cls._instance:
@@ -15,12 +78,21 @@ class EnvManager:
15
78
 
16
79
  def __init__(self):
17
80
  if not hasattr(self, "_initialized"):
81
+ # 确保关键属性在初始化时都有默认值
82
+ self._last_snapshot_time = time.time()
83
+ self._snapshot_interval = 3600
18
84
  self._init_db()
19
85
  self._initialized = True
20
86
 
21
87
  def _init_db(self):
22
88
  os.makedirs(os.path.dirname(self.db_path), exist_ok=True)
89
+ os.makedirs(self.SNAPSHOT_DIR, exist_ok=True)
23
90
  conn = sqlite3.connect(self.db_path)
91
+
92
+ # 启用WAL模式提高并发性能
93
+ conn.execute("PRAGMA journal_mode=WAL")
94
+ conn.execute("PRAGMA synchronous=NORMAL")
95
+
24
96
  cursor = conn.cursor()
25
97
  cursor.execute("""
26
98
  CREATE TABLE IF NOT EXISTS config (
@@ -30,6 +102,10 @@ class EnvManager:
30
102
  """)
31
103
  conn.commit()
32
104
  conn.close()
105
+
106
+ # 初始化自动快照调度器
107
+ self._last_snapshot_time = time.time() # 初始化为当前时间
108
+ self._snapshot_interval = 3600 # 默认每小时自动快照
33
109
 
34
110
  def get(self, key, default=None):
35
111
  try:
@@ -59,18 +135,128 @@ class EnvManager:
59
135
 
60
136
  def set(self, key, value):
61
137
  serialized_value = json.dumps(value) if isinstance(value, (dict, list)) else str(value)
62
- conn = sqlite3.connect(self.db_path)
63
- cursor = conn.cursor()
64
- cursor.execute("INSERT OR REPLACE INTO config (key, value) VALUES (?, ?)", (key, serialized_value))
65
- conn.commit()
66
- conn.close()
138
+ with self.transaction():
139
+ conn = sqlite3.connect(self.db_path)
140
+ cursor = conn.cursor()
141
+ cursor.execute("INSERT OR REPLACE INTO config (key, value) VALUES (?, ?)", (key, serialized_value))
142
+ conn.commit()
143
+ conn.close()
144
+
145
+ self._check_auto_snapshot()
146
+ return True
147
+
148
+ def set_multi(self, items):
149
+ with self.transaction():
150
+ conn = sqlite3.connect(self.db_path)
151
+ cursor = conn.cursor()
152
+ for key, value in items.items():
153
+ serialized_value = json.dumps(value) if isinstance(value, (dict, list)) else str(value)
154
+ cursor.execute("INSERT OR REPLACE INTO config (key, value) VALUES (?, ?)",
155
+ (key, serialized_value))
156
+ conn.commit()
157
+ conn.close()
158
+
159
+ self._check_auto_snapshot()
160
+ return True
67
161
 
68
162
  def delete(self, key):
163
+ with self.transaction():
164
+ conn = sqlite3.connect(self.db_path)
165
+ cursor = conn.cursor()
166
+ cursor.execute("DELETE FROM config WHERE key = ?", (key,))
167
+ conn.commit()
168
+ conn.close()
169
+
170
+ self._check_auto_snapshot()
171
+ return True
172
+
173
+ def delete_multi(self, keys):
174
+ with self.transaction():
175
+ conn = sqlite3.connect(self.db_path)
176
+ cursor = conn.cursor()
177
+ cursor.executemany("DELETE FROM config WHERE key = ?", [(k,) for k in keys])
178
+ conn.commit()
179
+ conn.close()
180
+
181
+ self._check_auto_snapshot()
182
+ return True
183
+
184
+ def get_multi(self, keys):
69
185
  conn = sqlite3.connect(self.db_path)
70
186
  cursor = conn.cursor()
71
- cursor.execute("DELETE FROM config WHERE key = ?", (key,))
72
- conn.commit()
187
+ placeholders = ','.join(['?'] * len(keys))
188
+ cursor.execute(f"SELECT key, value FROM config WHERE key IN ({placeholders})", keys)
189
+ results = {row[0]: json.loads(row[1]) if row[1].startswith(('{', '[')) else row[1]
190
+ for row in cursor.fetchall()}
73
191
  conn.close()
192
+ return results
193
+
194
+ def transaction(self):
195
+ return self._Transaction(self)
196
+
197
+ class _Transaction:
198
+ def __init__(self, env_manager):
199
+ self.env_manager = env_manager
200
+ self.conn = None
201
+ self.cursor = None
202
+
203
+ def __enter__(self):
204
+ self.conn = sqlite3.connect(self.env_manager.db_path)
205
+ self.cursor = self.conn.cursor()
206
+ self.cursor.execute("BEGIN TRANSACTION")
207
+ return self
208
+
209
+ def __exit__(self, exc_type, exc_val, exc_tb):
210
+ if exc_type is None:
211
+ self.conn.commit()
212
+ else:
213
+ self.conn.rollback()
214
+ from .logger import logger
215
+ logger.error(f"事务执行失败: {exc_val}")
216
+ self.conn.close()
217
+
218
+ def _check_auto_snapshot(self):
219
+ from .logger import logger
220
+
221
+ if not hasattr(self, '_last_snapshot_time') or self._last_snapshot_time is None:
222
+ self._last_snapshot_time = time.time()
223
+
224
+ if not hasattr(self, '_snapshot_interval') or self._snapshot_interval is None:
225
+ self._snapshot_interval = 3600
226
+
227
+ current_time = time.time()
228
+
229
+ try:
230
+ time_diff = current_time - self._last_snapshot_time
231
+ if not isinstance(time_diff, (int, float)):
232
+ raiserr.register(
233
+ "ErisPulseEnvTimeDiffTypeError",
234
+ doc = "时间差应为数值类型",
235
+ )
236
+ raiserr.ErisPulseEnvTimeDiffTypeError(
237
+ f"时间差应为数值类型,实际为: {type(time_diff)}"
238
+ )
239
+
240
+ if not isinstance(self._snapshot_interval, (int, float)):
241
+ raiserr.register(
242
+ "ErisPulseEnvSnapshotIntervalTypeError",
243
+ doc = "快照间隔应为数值类型",
244
+ )
245
+ raiserr.ErisPulseEnvSnapshotIntervalTypeError(
246
+ f"快照间隔应为数值类型,实际为: {type(self._snapshot_interval)}"
247
+ )
248
+
249
+ if time_diff > self._snapshot_interval:
250
+ self._last_snapshot_time = current_time
251
+ self.snapshot(f"auto_{datetime.now().strftime('%Y%m%d_%H%M%S')}")
252
+
253
+ except Exception as e:
254
+ logger.error(f"自动快照检查失败: {e}")
255
+ self._last_snapshot_time = current_time
256
+ self._snapshot_interval = 3600
257
+
258
+ def set_snapshot_interval(self, seconds):
259
+ self._snapshot_interval = seconds
74
260
 
75
261
  def clear(self):
76
262
  conn = sqlite3.connect(self.db_path)
@@ -127,4 +313,99 @@ from ErisPulse import sdk
127
313
  from .logger import logger
128
314
  logger.error(f"配置项 {key} 不存在")
129
315
 
130
- env = EnvManager()
316
+ def __setattr__(self, key, value):
317
+ try:
318
+ self.set(key, value)
319
+ except Exception as e:
320
+ from .logger import logger
321
+ logger.error(f"设置配置项 {key} 失败: {e}")
322
+
323
+ def snapshot(self, name=None):
324
+ if not name:
325
+ name = datetime.now().strftime("%Y%m%d_%H%M%S")
326
+ snapshot_path = os.path.join(self.SNAPSHOT_DIR, f"{name}.db")
327
+
328
+ try:
329
+ # 快照目录
330
+ os.makedirs(self.SNAPSHOT_DIR, exist_ok=True)
331
+
332
+ # 安全关闭连接
333
+ if hasattr(self, "_conn") and self._conn is not None:
334
+ try:
335
+ self._conn.close()
336
+ except Exception as e:
337
+ from .logger import logger
338
+ logger.warning(f"关闭数据库连接时出错: {e}")
339
+
340
+ # 创建快照
341
+ shutil.copy2(self.db_path, snapshot_path)
342
+ from .logger import logger
343
+ logger.info(f"数据库快照已创建: {snapshot_path}")
344
+ return snapshot_path
345
+ except Exception as e:
346
+ from .logger import logger
347
+ logger.error(f"创建快照失败: {e}")
348
+ raise
349
+
350
+ def restore(self, snapshot_name):
351
+ snapshot_path = os.path.join(self.SNAPSHOT_DIR, f"{snapshot_name}.db") \
352
+ if not snapshot_name.endswith('.db') else snapshot_name
353
+
354
+ if not os.path.exists(snapshot_path):
355
+ from .logger import logger
356
+ logger.error(f"快照文件不存在: {snapshot_path}")
357
+ return False
358
+
359
+ try:
360
+ # 安全关闭连接
361
+ if hasattr(self, "_conn") and self._conn is not None:
362
+ try:
363
+ self._conn.close()
364
+ except Exception as e:
365
+ from .logger import logger
366
+ logger.warning(f"关闭数据库连接时出错: {e}")
367
+
368
+ # 执行恢复操作
369
+ shutil.copy2(snapshot_path, self.db_path)
370
+ self._init_db() # 恢复后重新初始化数据库连接
371
+ from .logger import logger
372
+ logger.info(f"数据库已从快照恢复: {snapshot_path}")
373
+ return True
374
+ except Exception as e:
375
+ from .logger import logger
376
+ logger.error(f"恢复快照失败: {e}")
377
+ return False
378
+
379
+ def list_snapshots(self):
380
+ snapshots = []
381
+ for f in os.listdir(self.SNAPSHOT_DIR):
382
+ if f.endswith('.db'):
383
+ path = os.path.join(self.SNAPSHOT_DIR, f)
384
+ stat = os.stat(path)
385
+ snapshots.append((
386
+ f[:-3], # 去掉.db后缀
387
+ datetime.fromtimestamp(stat.st_ctime),
388
+ stat.st_size
389
+ ))
390
+ return sorted(snapshots, key=lambda x: x[1], reverse=True)
391
+
392
+ def delete_snapshot(self, snapshot_name):
393
+ snapshot_path = os.path.join(self.SNAPSHOT_DIR, f"{snapshot_name}.db") \
394
+ if not snapshot_name.endswith('.db') else snapshot_name
395
+
396
+ if not os.path.exists(snapshot_path):
397
+ from .logger import logger
398
+ logger.error(f"快照文件不存在: {snapshot_path}")
399
+ return False
400
+
401
+ try:
402
+ os.remove(snapshot_path)
403
+ from .logger import logger
404
+ logger.info(f"快照已删除: {snapshot_path}")
405
+ return True
406
+ except Exception as e:
407
+ from .logger import logger
408
+ logger.error(f"删除快照失败: {e}")
409
+ return False
410
+
411
+ env = EnvManager()
ErisPulse/logger.py CHANGED
@@ -1,3 +1,49 @@
1
+ """
2
+ # 日志系统
3
+
4
+ 提供模块化、多级别的日志记录功能,支持内存存储和文件输出。
5
+
6
+ ## API 文档
7
+ ### 基本操作:
8
+ - debug(msg, *args, **kwargs): 调试信息
9
+ - info(msg, *args, **kwargs): 运行信息
10
+ - warning(msg, *args, **kwargs): 警告信息
11
+ - error(msg, *args, **kwargs): 错误信息
12
+ - critical(msg, *args, **kwargs): 致命错误并终止程序
13
+
14
+ ### 日志控制:
15
+ - set_level(level): 设置全局日志级别
16
+ - set_module_level(module_name, level): 设置模块日志级别
17
+
18
+ ### 日志存储:
19
+ - save_logs(path): 保存内存中的日志到文件
20
+ - set_output_file(path): 设置日志输出文件
21
+
22
+ ### 示例用法:
23
+
24
+ ```
25
+ from ErisPulse import sdk
26
+
27
+ # 基本日志记录
28
+ sdk.logger.debug("调试信息")
29
+ sdk.logger.info("运行状态")
30
+
31
+ # 模块级日志控制
32
+ sdk.logger.set_module_level("MyModule", "DEBUG")
33
+
34
+ # 异常捕获
35
+ @sdk.logger.catch
36
+ def risky_function():
37
+ raise Exception("出错了")
38
+ ```
39
+
40
+ ## 准备弃用
41
+
42
+ catch(func_or_level=None, level="error"): 异常捕获装饰器
43
+ - 原因: 异常捕获功能已集成到 raiserr 模块中,建议使用 raiserr 进行异常处理。
44
+
45
+ """
46
+
1
47
  import logging
2
48
  import inspect
3
49
  import datetime
@@ -152,4 +198,4 @@ class Logger:
152
198
  raiserr.register("CriticalError", doc="发生致命错误")
153
199
  raiserr.CriticalError(f"程序发生致命错误:{msg}", exit=True)
154
200
 
155
- logger = Logger()
201
+ logger = Logger()
ErisPulse/mods.py CHANGED
@@ -1,3 +1,41 @@
1
+ """
2
+ # 模块管理系统
3
+
4
+ 提供模块的注册、状态管理和依赖解析功能。
5
+
6
+ ## API 文档
7
+ ### 模块状态:
8
+ - set_module_status(module_name, status): 设置模块启用状态
9
+ - get_module_status(module_name): 获取模块状态
10
+
11
+ ### 模块信息:
12
+ - set_module(module_name, module_info): 设置模块信息
13
+ - get_module(module_name): 获取模块信息
14
+ - get_all_modules(): 获取所有模块信息
15
+ - remove_module(module_name): 删除模块
16
+
17
+ ### 前缀管理:
18
+ - update_prefixes(module_prefix, status_prefix): 更新存储前缀
19
+ - module_prefix: 模块存储前缀属性
20
+ - status_prefix: 状态存储前缀属性
21
+
22
+ ### 示例用法:
23
+
24
+ ```
25
+ from ErisPulse import sdk
26
+
27
+ # 设置模块状态
28
+ sdk.mods.set_module_status("MyModule", True)
29
+
30
+ # 获取模块信息
31
+ module_info = sdk.mods.get_module("MyModule")
32
+
33
+ # 批量操作
34
+ sdk.mods.set_all_modules({"Module1": {...}, "Module2": {...}})
35
+ ```
36
+
37
+ """
38
+
1
39
  import json
2
40
  from typing import Dict, Optional
3
41
 
ErisPulse/raiserr.py CHANGED
@@ -1,3 +1,38 @@
1
+ """
2
+ # 错误管理系统
3
+
4
+ 提供错误类型注册、抛出和管理功能,集成全局异常处理。
5
+
6
+ ## API 文档
7
+ ### 错误注册:
8
+ - register(name, doc="", base=Exception): 注册新的错误类型
9
+ - info(name: str = None): 获取错误类型信息
10
+
11
+ ### 错误抛出:
12
+ - __getattr__(name): 动态获取错误抛出函数
13
+ - ErrorType(msg, exit=False): 抛出注册的错误类型
14
+
15
+ ### 全局处理:
16
+ - global_exception_handler: 全局同步异常处理器
17
+ - async_exception_handler: 全局异步异常处理器
18
+
19
+ ### 示例用法:
20
+
21
+ ```
22
+ from ErisPulse import sdk
23
+
24
+ # 注册自定义错误
25
+ sdk.raiserr.register("MyError", doc="自定义错误描述")
26
+
27
+ # 抛出错误
28
+ sdk.raiserr.MyError("发生了错误", exit=False)
29
+
30
+ # 获取错误信息
31
+ error_info = sdk.raiserr.info("MyError")
32
+ ```
33
+
34
+ """
35
+
1
36
  import sys
2
37
  import traceback
3
38
  import asyncio
@@ -71,4 +106,4 @@ def async_exception_handler(loop, context):
71
106
  )
72
107
  else:
73
108
  logger.warning(f"异步任务警告: {message}")
74
- asyncio.get_event_loop().set_exception_handler(async_exception_handler)
109
+ asyncio.get_event_loop().set_exception_handler(async_exception_handler)
ErisPulse/util.py CHANGED
@@ -1,3 +1,47 @@
1
+ """
2
+ # 工具函数集合
3
+
4
+ 提供各种实用工具函数和装饰器,简化开发流程。
5
+
6
+ ## API 文档
7
+ ### 拓扑排序:
8
+ - topological_sort(elements, dependencies, error): 拓扑排序依赖关系
9
+ - show_topology(): 可视化模块依赖关系
10
+
11
+ ### 装饰器:
12
+ - @cache: 缓存函数结果
13
+ - @run_in_executor: 将同步函数转为异步
14
+ - @retry(max_attempts=3, delay=1): 失败自动重试
15
+
16
+ ### 异步执行:
17
+ - ExecAsync(async_func, *args, **kwargs): 异步执行函数
18
+
19
+ ### 示例用法:
20
+
21
+ ```
22
+ from ErisPulse import sdk
23
+
24
+ # 拓扑排序
25
+ sorted_modules = sdk.util.topological_sort(modules, dependencies, error)
26
+
27
+ # 缓存装饰器
28
+ @sdk.util.cache
29
+ def expensive_operation(param):
30
+ return heavy_computation(param)
31
+
32
+ # 异步执行
33
+ @sdk.util.run_in_executor
34
+ def sync_task():
35
+ pass
36
+
37
+ # 重试机制
38
+ @sdk.util.retry(max_attempts=3, delay=1)
39
+ def unreliable_operation():
40
+ pass
41
+ ```
42
+
43
+ """
44
+
1
45
  import time
2
46
  import asyncio
3
47
  import functools
@@ -96,4 +140,4 @@ def retry(max_attempts=3, delay=1):
96
140
  raise
97
141
  time.sleep(delay)
98
142
  return wrapper
99
- return decorator
143
+ return decorator
@@ -0,0 +1,165 @@
1
+ Metadata-Version: 2.4
2
+ Name: ErisPulse
3
+ Version: 1.1.14.dev1
4
+ Summary: ErisPulse 是一个模块化、可扩展的异步 Python SDK 框架,主要用于构建高效、可维护的机器人应用程序。
5
+ Author-email: "艾莉丝·格雷拉特(WSu2059)" <wsu2059@qq.com>, runoneall <runoobsteve@gmail.com>
6
+ License: MIT License
7
+
8
+ Copyright (c) 2025 ErisPulse
9
+
10
+ Permission is hereby granted, free of charge, to any person obtaining a copy
11
+ of this software and associated documentation files (the "Software"), to deal
12
+ in the Software without restriction, including without limitation the rights
13
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14
+ copies of the Software, and to permit persons to whom the Software is
15
+ furnished to do so, subject to the following conditions:
16
+
17
+ The above copyright notice and this permission notice shall be included in all
18
+ copies or substantial portions of the Software.
19
+
20
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
21
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
23
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
24
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
26
+ SOFTWARE.
27
+ License-File: LICENSE
28
+ Classifier: Development Status :: 5 - Production/Stable
29
+ Classifier: Intended Audience :: Developers
30
+ Classifier: License :: OSI Approved :: MIT License
31
+ Classifier: Operating System :: OS Independent
32
+ Classifier: Programming Language :: Python :: 3
33
+ Classifier: Programming Language :: Python :: 3 :: Only
34
+ Classifier: Programming Language :: Python :: 3.9
35
+ Classifier: Programming Language :: Python :: 3.10
36
+ Classifier: Programming Language :: Python :: 3.11
37
+ Classifier: Programming Language :: Python :: 3.12
38
+ Classifier: Topic :: Software Development :: Libraries :: Python Modules
39
+ Requires-Python: >=3.9
40
+ Requires-Dist: aiohttp
41
+ Requires-Dist: watchdog
42
+ Description-Content-Type: text/markdown
43
+
44
+ ![](./.github/assets/erispulse_logo.png)
45
+ **ErisPulse** 是基于 [Framer](https://github.com/FramerOrg/Framer) 构建的异步机器人开发框架。
46
+
47
+ [![FramerOrg](https://img.shields.io/badge/合作伙伴-FramerOrg-blue?style=flat-square)](https://github.com/FramerOrg)
48
+ [![License](https://img.shields.io/github/license/ErisPulse/ErisPulse?style=flat-square)](https://github.com/ErisPulse/ErisPulse/blob/main/LICENSE)
49
+
50
+ [![Python Versions](https://img.shields.io/pypi/pyversions/ErisPulse?style=flat-square)](https://pypi.org/project/ErisPulse/)
51
+
52
+ > 文档站:
53
+
54
+ [![Docs-Main](https://img.shields.io/badge/docs-main_site-blue?style=flat-square)](https://www.erisdev.com/docs.html)
55
+ [![Docs-CF Pages](https://img.shields.io/badge/docs-cloudflare-blue?style=flat-square)](https://erispulse.pages.dev/docs.html)
56
+ [![Docs-GitHub](https://img.shields.io/badge/docs-github-blue?style=flat-square)](https://erispulse.github.io/docs.html)
57
+ [![Docs-Netlify](https://img.shields.io/badge/docs-netlify-blue?style=flat-square)](https://erispulse.netlify.app/docs.htm)
58
+
59
+ - [GitHub 社区讨论](https://github.com/ErisPulse/ErisPulse/discussions)
60
+
61
+ ### 框架选型指南
62
+ | 需求 | 推荐框架 | 理由 |
63
+ |-------------------|----------------|-----------------------------|
64
+ | 轻量化/底层模块化 | [Framer](https://github.com/FramerOrg/Framer) | 高度解耦的模块化设计 |
65
+ | 全功能机器人开发 | ErisPulse | 开箱即用的完整解决方案 |
66
+
67
+ ## ✨ 核心特性
68
+ - ⚡ 完全异步架构设计(async/await)
69
+ - 🧩 模块化插件系统
70
+ - 🔁 支持python热重载
71
+ - 🛑 统一的错误管理
72
+ - 🛠️ 灵活的配置管理
73
+
74
+ ## 📦 安装
75
+
76
+ ```bash
77
+ pip install ErisPulse --upgrade
78
+ ```
79
+
80
+ ---
81
+
82
+ ## 开发者快速入门
83
+
84
+ ErisPulse SDK 支持使用 [`uv`](https://github.com/astral-sh/uv) 进行完整的开发环境管理。你可以**无需手动安装 Python**,直接通过 `uv` 下载 Python、创建虚拟环境并开始开发。
85
+
86
+ ### 安装 `uv`
87
+
88
+ #### macOS / Linux:
89
+ ```bash
90
+ curl -LsSf https://astral.sh/uv/install.sh | sh
91
+ ```
92
+
93
+ #### Windows (PowerShell):
94
+ ```powershell
95
+ powershell -ExecutionPolicy ByPass -c "irm https://astral.sh/uv/install.ps1 | iex"
96
+ ```
97
+
98
+ 验证是否安装成功:
99
+ ```bash
100
+ uv --version
101
+ ```
102
+
103
+ ### 克隆项目并进入目录
104
+
105
+ ```bash
106
+ git clone https://github.com/ErisPulse/ErisPulse.git
107
+ cd ErisPulse
108
+ ```
109
+
110
+ ### 使用 `uv` 自动下载 Python 并创建虚拟环境
111
+
112
+ ```bash
113
+ uv python install 3.12 # 自动下载并安装 Python 3.12
114
+ uv venv # 创建默认 .venv 虚拟环境
115
+ source .venv/bin/activate
116
+ # Windows: .venv\Scripts\activate
117
+ ```
118
+
119
+ > ✅ 如果你切换分支或需要不同 Python 版本,只需替换 `3.12` 为其他版本即可。
120
+
121
+ ### 安装依赖并开始开发
122
+
123
+ ```bash
124
+ uv pip install -e .
125
+ ```
126
+
127
+ 这将以“开发模式”安装 SDK,所有本地修改都会立即生效。
128
+
129
+ ### 验证安装
130
+
131
+ 运行以下命令确认 SDK 正常加载:
132
+
133
+ ```bash
134
+ python -c "from ErisPulse import sdk; sdk.init()"
135
+ ```
136
+
137
+ ### 运行测试
138
+
139
+ 我们提供了一个交互式测试脚本,可以帮助您快速验证SDK功能:
140
+
141
+ ```bash
142
+ uv run devs/test.py
143
+ ```
144
+
145
+ 测试脚本提供以下功能:
146
+ - 日志功能测试
147
+ - 环境配置测试
148
+ - 错误管理测试
149
+ - 工具函数测试
150
+ - 适配器功能测试
151
+ - 版本信息查看
152
+
153
+ ### 开始开发
154
+
155
+ 你可以通过 CLI 工具进行模块调试、热重载开发等操作:
156
+
157
+ ```bash
158
+ epsdk run your_script.py --reload
159
+ ```
160
+
161
+ ---
162
+
163
+ ## 🤝 贡献
164
+
165
+ 欢迎任何形式的贡献!无论是报告 bug、提出新功能请求,还是直接提交代码,都非常感谢。
@@ -0,0 +1,13 @@
1
+ ErisPulse/__init__.py,sha256=k-X8WV9sIrYeYDNb8qZyBZ8s8yNL2bKWhZdkPbzRWII,8936
2
+ ErisPulse/__main__.py,sha256=aZK7FdvFTgsKgHPYpaeKpA_l2JFhEy9TNy3vndkONFk,50001
3
+ ErisPulse/adapter.py,sha256=g5npw-RAmGKXY3gTO8oNA63DRJ3Z9xVrl9BWuus-EQs,9837
4
+ ErisPulse/db.py,sha256=rXxpTug5NMZQTJ_07lJTe-PWdoePNPAkYoQDfazFapY,14411
5
+ ErisPulse/logger.py,sha256=832gGOiRUfXhYjz9JZ3DfVzB6ttqIimyLU0xk5k7lZ0,7319
6
+ ErisPulse/mods.py,sha256=lBCWM0VfsCJehnMgpswKYuHitg30JERg0H4WN6kqgbA,4509
7
+ ErisPulse/raiserr.py,sha256=2dJA3g6aje4yxhr1JPeZsrxudblKAOq6T_LMHeRjQ24,3438
8
+ ErisPulse/util.py,sha256=tmmZA4Ef5ElB01KZg2fTZLrkZOJbORjnkAd8sXj7xqw,4335
9
+ erispulse-1.1.14.dev1.dist-info/METADATA,sha256=I03H-qlpVtNAxuX_H60HgnTaMqLrKGpPfe5zIq9EhfE,5882
10
+ erispulse-1.1.14.dev1.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
11
+ erispulse-1.1.14.dev1.dist-info/entry_points.txt,sha256=AjKvOdYR7QGXVpEJhjUYUwV2JluE4lm9vNbknC3hjOM,155
12
+ erispulse-1.1.14.dev1.dist-info/licenses/LICENSE,sha256=plj4EYVfKAzc0ZWoC5T2vsQ86u0yLpu17NdAPeIcgVo,1066
13
+ erispulse-1.1.14.dev1.dist-info/RECORD,,
@@ -1,5 +1,4 @@
1
1
  Wheel-Version: 1.0
2
- Generator: setuptools (80.9.0)
2
+ Generator: hatchling 1.27.0
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
5
-
@@ -1,79 +0,0 @@
1
- Metadata-Version: 2.4
2
- Name: ErisPulse
3
- Version: 1.1.13
4
- Summary: ErisPulse 是一个模块化、可扩展的异步 Python SDK 框架,主要用于构建高效、可维护的机器人应用程序。
5
- Author-email: "艾莉丝·格雷拉特(WSu2059)" <wsu2059@qq.com>, runoneall <runoobsteve@gmail.com>
6
- Classifier: Development Status :: 5 - Production/Stable
7
- Classifier: Intended Audience :: Developers
8
- Classifier: License :: OSI Approved :: MIT License
9
- Classifier: Programming Language :: Python :: 3
10
- Classifier: Programming Language :: Python :: 3.7
11
- Classifier: Programming Language :: Python :: 3.8
12
- Classifier: Programming Language :: Python :: 3.9
13
- Classifier: Programming Language :: Python :: 3.10
14
- Classifier: Programming Language :: Python :: 3.11
15
- Classifier: Programming Language :: Python :: 3.12
16
- Classifier: Programming Language :: Python :: 3 :: Only
17
- Classifier: Operating System :: OS Independent
18
- Classifier: Topic :: Software Development :: Libraries :: Python Modules
19
- Requires-Python: >=3.7
20
- Description-Content-Type: text/markdown
21
- License-File: LICENSE
22
- Requires-Dist: aiohttp
23
- Requires-Dist: watchdog
24
- Dynamic: license-file
25
-
26
- ![](./.github/assets/erispulse_logo.png)
27
- **ErisPulse** 是基于 [Framer](https://github.com/FramerOrg/Framer) 构建的异步机器人开发框架。
28
-
29
- ## 合作伙伴
30
- [![FramerOrg](https://img.shields.io/badge/合作伙伴-FramerOrg-blue?style=flat-square)](https://github.com/FramerOrg)
31
-
32
- ### 框架选型指南
33
- | 需求 | 推荐框架 | 理由 |
34
- |-------------------|----------------|-----------------------------|
35
- | 轻量化/底层模块化 | [Framer](https://github.com/FramerOrg/Framer) | 高度解耦的模块化设计 |
36
- | 全功能机器人开发 | ErisPulse | 开箱即用的完整解决方案 |
37
-
38
-
39
- ## ✨ 核心特性
40
- - ⚡ 完全异步架构设计(async/await)
41
- - 🧩 模块化插件系统
42
- - 📜 内置日志系统
43
- - 🛑 统一的错误管理
44
- - 🛠️ 灵活的配置管理
45
-
46
- ## 📦 安装
47
-
48
- ```bash
49
- pip install ErisPulse --upgrade
50
- ```
51
-
52
- **要求**:Python ≥ 3.7,pip ≥ 20.0
53
-
54
- ## 🚀 快速开始
55
-
56
- ```python
57
- import asyncio
58
- from ErisPulse import sdk, logger
59
-
60
- async def main():
61
- sdk.init()
62
- logger.info("ErisPulse 已启动")
63
- # 这里可以添加自定义逻辑
64
-
65
- if __name__ == "__main__":
66
- asyncio.run(main())
67
- ```
68
-
69
- ## 导航
70
- - [开发者指南](docs/DEVELOPMENT.md)
71
- - [底层方法与接口](docs/REFERENCE.md)
72
- - [命令行工具](docs/CLI.md)
73
- - [源配置指南](docs/ORIGIN.md)
74
- - [更新日志](docs/CHANGELOG.md)
75
- > [GitHub 社区](https://github.com/ErisPulse/ErisPulse/discussions)
76
-
77
- ## 🤝 贡献
78
-
79
- 欢迎任何形式的贡献!无论是报告 bug、提出新功能请求,还是直接提交代码,都非常感谢。
@@ -1,14 +0,0 @@
1
- ErisPulse/__init__.py,sha256=tCgjl-0rUeiHV_2rdFlQ-CVTFzbKdjdqXvUApRc6Avk,8095
2
- ErisPulse/__main__.py,sha256=WtfHeAfWi-q1KEmrkl9slYsbCm3EI9MWb34406Usch8,49245
3
- ErisPulse/adapter.py,sha256=5ntqm5Xrzdi1F6N4kWhqiRzMavSO92Fj9WZ-d3-V2VM,8798
4
- ErisPulse/db.py,sha256=DuIc19GbCQMi17BWfLjaDHnthIbdysTSRxaYVFur07w,4424
5
- ErisPulse/logger.py,sha256=sMA1mUZvwJ8wHwdyCrgIf_VRICv_uBCkx3tmd1stF3E,6094
6
- ErisPulse/mods.py,sha256=lNiZP2EcfUhYRnOQwROyVnmhsfmk8JAZhmbhxfC2-VQ,3513
7
- ErisPulse/raiserr.py,sha256=z8BigWkVrBE9dD_dJa5np2YYREwdugyWXKE4_-LEO_Q,2616
8
- ErisPulse/util.py,sha256=ux3-QRT0_JjabL6S9KChhyR1E_CSRiVYEFYV5txML1M,3406
9
- erispulse-1.1.13.dist-info/licenses/LICENSE,sha256=plj4EYVfKAzc0ZWoC5T2vsQ86u0yLpu17NdAPeIcgVo,1066
10
- erispulse-1.1.13.dist-info/METADATA,sha256=92lw9G8SIHNWMsfMYuKoK1tJJcGc0wo6cBwHxJAWmAY,2751
11
- erispulse-1.1.13.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
12
- erispulse-1.1.13.dist-info/entry_points.txt,sha256=AjKvOdYR7QGXVpEJhjUYUwV2JluE4lm9vNbknC3hjOM,155
13
- erispulse-1.1.13.dist-info/top_level.txt,sha256=Lm_qtkVvNJR8_dXh_qEDdl_12cZGpic-i4HUlVVUMZc,10
14
- erispulse-1.1.13.dist-info/RECORD,,
@@ -1 +0,0 @@
1
- ErisPulse