VWED_server/docs/script_registration_examples.md

775 lines
22 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# VWED脚本注册声明示例文档
## 概述
本文档详细说明了在VWED在线脚本中如何注册和声明各种类型的内置函数包括API接口、自定义函数、事件监听器和定时任务。
---
## 1. API接口注册示例
### 1.1 基本GET接口
```python
#!/usr/bin/env python
# -*- coding: utf-8 -*-
def boot():
"""脚本启动函数"""
# 注册GET接口 - 传参数和定义执行逻辑分开
VWED.api.register_route(
path="/hello",
method="GET",
handler=hello_handler,
description="问候接口"
)
def hello_handler(request_data):
"""处理问候请求"""
name = request_data["query_params"].get("name", "World")
return {"message": f"Hello, {name}!"}
```
**请求示例**: `GET /api/dynamic/hello?name=张三`
**响应示例**:
```json
{
"message": "Hello, 张三!"
}
```
### 1.2 带参数定义的POST接口
```python
def boot():
# 注册POST接口简化参数定义 - 传参数和定义执行逻辑分开
VWED.api.register_route(
path="/calculate",
method="POST",
handler=calculate_handler,
description="数学计算接口",
params={"a": 0, "b": 0, "operation": "add"} # 简化的参数定义:键值对形式的默认值
)
def calculate_handler(a: int, b: int, operation: str):
"""数学计算处理器 - 直接接收参数"""
# 执行计算
if operation == "add":
result = a + b
elif operation == "subtract":
result = a - b
elif operation == "multiply":
result = a * b
elif operation == "divide":
result = a / b if b != 0 else None
else:
result = None
# 记录日志
VWED.log.sync_info(f"计算执行: {a} {operation} {b} = {result}")
return {
"result": result,
"operation": operation,
"operand_a": a,
"operand_b": b,
"timestamp": VWED.util.now()
}
```
**请求示例**:
```bash
POST /api/dynamic/calculate
Content-Type: application/json
{
"a": 10,
"b": 5,
"operation": "multiply"
}
```
### 1.3 数据处理接口
```python
def boot():
# 注册数据处理接口 - 传参数和定义执行逻辑分开
VWED.api.register_route(
path="/process-data",
method="POST",
handler=process_data_handler,
description="数据处理接口",
params={"data_list": [], "process_type": "filter"} # 简化的参数定义
)
def process_data_handler(data_list: list, process_type: str):
"""处理批量数据 - 直接接收参数"""
if process_type == "filter":
# 过滤正数
result = [x for x in data_list if isinstance(x, (int, float)) and x > 0]
elif process_type == "sort":
# 排序
result = sorted(data_list)
elif process_type == "sum":
# 求和
result = sum(x for x in data_list if isinstance(x, (int, float)))
else:
result = data_list
VWED.log.sync_info(f"数据处理完成: {process_type}, 输入{len(data_list)}项,输出{len(result) if isinstance(result, list) else 1}项")
return {
"original_data": data_list,
"processed_data": result,
"process_type": process_type,
"input_count": len(data_list),
"output_count": len(result) if isinstance(result, list) else 1
}
```
---
## 2. 自定义函数注册示例
### 2.1 简单计算函数
```python
def boot():
# 注册简单函数 - 传参数和定义执行逻辑分开
VWED.function.register(
name="simple_add",
handler=simple_add,
description="简单加法函数",
params={"a": 0, "b": 0} # 简化的参数定义
)
def simple_add(a: int, b: int):
"""供VWED任务调用的加法函数 - 直接接收参数"""
result = a + b
VWED.log.sync_info(f"执行加法: {a} + {b} = {result}")
return {"result": result}
```
**VWED任务中的调用方式**:
```json
{
"block_type": "script",
"execution_mode": "function_call",
"function_name": "simple_add",
"function_args": {
"a": 10,
"b": 20
}
}
```
### 2.2 带多个参数的函数
```python
def boot():
# 注册多参数函数 - 简化的参数定义
VWED.function.register(
name="data_statistics",
handler=data_statistics,
description="数据统计函数",
params={"numbers": [1, 2, 3], "operation": "sum", "round_digits": 2} # 简化的参数定义
)
def data_statistics(numbers: list, operation: str, round_digits: int):
"""数据统计函数 - 直接接收参数"""
if not numbers:
return {"error": "数字数组不能为空"}
# 执行计算
if operation == "sum":
result = sum(numbers)
elif operation == "avg":
result = sum(numbers) / len(numbers)
elif operation == "max":
result = max(numbers)
elif operation == "min":
result = min(numbers)
elif operation == "median":
sorted_numbers = sorted(numbers)
n = len(sorted_numbers)
if n % 2 == 0:
result = (sorted_numbers[n//2-1] + sorted_numbers[n//2]) / 2
else:
result = sorted_numbers[n//2]
else:
return {"error": f"不支持的运算类型: {operation}"}
# 四舍五入
if isinstance(result, float):
result = round(result, round_digits)
VWED.log.sync_info(f"数据统计: {operation}({numbers}) = {result}")
return {
"result": result,
"operation": operation,
"input_count": len(numbers),
"input_numbers": numbers
}
```
### 2.3 异步函数示例
```python
def boot():
# 注册异步函数 - 简化的参数定义
VWED.function.register(
name="async_data_fetch",
handler=async_data_fetch,
description="异步数据获取函数",
params={"source": "database", "delay": 1} # 简化的参数定义
)
async def async_data_fetch(source: str, delay: int):
"""异步获取和处理数据 - 直接接收参数"""
await VWED.log.info(f"开始异步数据获取: {source}")
# 模拟异步操作
await VWED.util.async_sleep(delay)
# 模拟数据获取
mock_data = {
"database": [{"id": 1, "name": "数据1"}, {"id": 2, "name": "数据2"}],
"api": [{"status": "success", "data": "API数据"}],
"file": [{"content": "文件内容", "size": 1024}]
}
data = mock_data.get(source, [])
await VWED.log.info(f"异步数据获取完成: {source}, 获取到{len(data)}条记录")
return {
"source": source,
"data": data,
"count": len(data),
"fetch_time": delay,
"completed_at": VWED.util.now()
}
```
### 2.4 数据验证函数
```python
def boot():
# 注册数据验证函数 - 简化的参数定义
VWED.function.register(
name="validate_user_data",
handler=validate_user_data,
description="用户数据验证函数",
params={"user_data": {"name": "", "age": 0, "email": ""}, "strict_mode": False} # 简化的参数定义
)
def validate_user_data(user_data: dict, strict_mode: bool):
"""验证用户数据 - 直接接收参数"""
errors = []
warnings = []
# 必填字段检查
if not user_data.get("name"):
errors.append("姓名是必填字段")
# 年龄验证
age = user_data.get("age")
if age is not None:
if not isinstance(age, int) or age < 0:
errors.append("年龄必须是非负整数")
elif age > 150:
warnings.append("年龄超过150岁请确认")
# 邮箱验证
email = user_data.get("email")
if email:
if "@" not in email or "." not in email:
if strict_mode:
errors.append("邮箱格式不正确")
else:
warnings.append("邮箱格式可能不正确")
# 记录验证结果
is_valid = len(errors) == 0
VWED.log.sync_info(f"用户数据验证: {'通过' if is_valid else '失败'}, 错误{len(errors)}个,警告{len(warnings)}个")
return {
"is_valid": is_valid,
"errors": errors,
"warnings": warnings,
"validated_fields": list(user_data.keys()),
"strict_mode": strict_mode
}
```
---
## 3. 事件监听器注册示例
### 3.1 基本事件监听器
```python
def boot():
# 注册基本事件监听器 - 传参数和定义执行逻辑分开
VWED.event.listen(
event_name="user_login",
handler=on_user_login
)
def on_user_login(event_data):
"""用户登录事件处理"""
user_id = event_data.get("user_id", "unknown")
login_time = event_data.get("login_time", VWED.util.now())
VWED.log.sync_info(f"用户登录: {user_id} at {login_time}")
# 更新登录统计
login_count = VWED.data.get("login_count", 0)
VWED.data.set("login_count", login_count + 1)
# 记录最近登录用户
recent_logins = VWED.data.get("recent_logins", [])
recent_logins.append({"user_id": user_id, "time": login_time})
# 只保留最近10条记录
if len(recent_logins) > 10:
recent_logins = recent_logins[-10:]
VWED.data.set("recent_logins", recent_logins)
```
### 3.2 高优先级事件监听器
```python
def boot():
# 注册高优先级事件监听器
@VWED.event.listen("system_error", priority=0) # 优先级0最高
def on_system_error(event_data):
"""系统错误事件处理(高优先级)"""
error_type = event_data.get("error_type", "unknown")
error_message = event_data.get("error_message", "")
VWED.log.sync_error(f"系统错误: {error_type} - {error_message}")
# 错误统计
error_count = VWED.data.get("error_count", 0)
VWED.data.set("error_count", error_count + 1)
# 如果是严重错误,触发告警
if error_type in ["database_down", "memory_overflow", "security_breach"]:
# 触发告警事件
asyncio.create_task(VWED.event.emit("critical_alert", {
"level": "critical",
"source": "system_monitor",
"error_type": error_type,
"message": error_message,
"timestamp": VWED.util.now()
}))
```
### 3.3 任务完成事件监听器
```python
def boot():
# 监听VWED任务完成事件
@VWED.event.listen("task_completed", priority=1)
def on_task_completed(event_data):
"""任务完成事件处理"""
task_id = event_data.get("task_id", "unknown")
task_status = event_data.get("status", "unknown")
execution_time = event_data.get("execution_time_ms", 0)
VWED.log.sync_info(f"任务完成: {task_id}, 状态: {task_status}, 耗时: {execution_time}ms")
# 更新任务统计
completed_tasks = VWED.data.get("completed_tasks", [])
completed_tasks.append({
"task_id": task_id,
"status": task_status,
"execution_time_ms": execution_time,
"completed_at": VWED.util.now()
})
# 只保留最近100条记录
if len(completed_tasks) > 100:
completed_tasks = completed_tasks[-100:]
VWED.data.set("completed_tasks", completed_tasks)
# 如果任务执行时间过长,记录预警
if execution_time > 30000: # 超过30秒
VWED.log.sync_warning(f"任务执行时间过长: {task_id} ({execution_time}ms)")
```
---
## 4. 定时任务注册示例
### 4.1 周期性定时任务
```python
def boot():
# 注册周期性定时任务 - 每分钟执行一次 - 传参数和定义执行逻辑分开
VWED.timer.interval(
interval=60, # 60秒间隔
handler=system_monitor
)
def system_monitor():
"""系统监控定时任务"""
# 获取系统统计信息
stats = {
"login_count": VWED.data.get("login_count", 0),
"error_count": VWED.data.get("error_count", 0),
"completed_tasks": len(VWED.data.get("completed_tasks", [])),
"check_time": VWED.util.now()
}
VWED.log.sync_info(f"系统监控: 登录{stats['login_count']}次, 错误{stats['error_count']}个, 完成任务{stats['completed_tasks']}个")
# 保存监控记录
monitor_history = VWED.data.get("monitor_history", [])
monitor_history.append(stats)
# 只保留最近24小时的记录
if len(monitor_history) > 1440: # 24*60分钟
monitor_history = monitor_history[-1440:]
VWED.data.set("monitor_history", monitor_history)
```
### 4.2 一次性延迟任务
```python
def boot():
# 注册一次性延迟任务 - 10秒后执行
@VWED.timer.once(delay=10)
def initialization_task():
"""初始化任务(延迟执行)"""
VWED.log.sync_info("执行初始化任务")
# 初始化数据结构
if not VWED.data.has("initialized"):
VWED.data.set("login_count", 0)
VWED.data.set("error_count", 0)
VWED.data.set("completed_tasks", [])
VWED.data.set("monitor_history", [])
VWED.data.set("initialized", True)
VWED.data.set("init_time", VWED.util.now())
VWED.log.sync_info("系统数据初始化完成")
```
### 4.3 数据清理定时任务
```python
def boot():
# 注册数据清理任务 - 每小时执行一次
@VWED.timer.interval(3600) # 3600秒 = 1小时
def data_cleanup():
"""数据清理定时任务"""
VWED.log.sync_info("开始执行数据清理")
cleanup_count = 0
# 清理过期的监控记录
monitor_history = VWED.data.get("monitor_history", [])
original_count = len(monitor_history)
# 只保留最近12小时的记录
monitor_history = monitor_history[-720:] # 12*60分钟
VWED.data.set("monitor_history", monitor_history)
cleanup_count += original_count - len(monitor_history)
# 清理过期的任务记录
completed_tasks = VWED.data.get("completed_tasks", [])
original_count = len(completed_tasks)
# 只保留最近50条记录
completed_tasks = completed_tasks[-50:]
VWED.data.set("completed_tasks", completed_tasks)
cleanup_count += original_count - len(completed_tasks)
# 清理过期的登录记录
recent_logins = VWED.data.get("recent_logins", [])
original_count = len(recent_logins)
# 只保留最近20条记录
recent_logins = recent_logins[-20:]
VWED.data.set("recent_logins", recent_logins)
cleanup_count += original_count - len(recent_logins)
VWED.log.sync_info(f"数据清理完成,清理了{cleanup_count}条过期记录")
# 记录清理统计
cleanup_stats = VWED.data.get("cleanup_stats", [])
cleanup_stats.append({
"cleanup_time": VWED.util.now(),
"cleaned_records": cleanup_count
})
# 只保留最近10次清理记录
if len(cleanup_stats) > 10:
cleanup_stats = cleanup_stats[-10:]
VWED.data.set("cleanup_stats", cleanup_stats)
```
---
## 5. 完整的脚本示例
以下是一个包含所有类型注册的完整脚本示例:
```python
def boot():
"""脚本启动函数 - 注册所有服务"""
VWED.log.sync_info("=== 开始注册脚本服务 ===")
# 注册API接口
register_api_services()
# 注册自定义函数
register_custom_functions()
# 注册事件监听器
register_event_listeners()
# 注册定时任务
register_timer_tasks()
VWED.log.sync_info("=== 脚本服务注册完成 ===")
def register_api_services():
"""注册API服务"""
VWED.log.sync_info("注册API接口...")
# 传参数和定义执行逻辑分开
VWED.api.register_route(
path="/status",
method="GET",
handler=get_system_status,
description="系统状态查询接口"
)
VWED.api.register_route(
path="/trigger-event",
method="POST",
handler=trigger_event,
description="手动触发事件接口"
)
def get_system_status(request_data):
return {
"status": "running",
"timestamp": VWED.util.now(),
"script_id": VWED.get_script_id(),
"stats": {
"login_count": VWED.data.get("login_count", 0),
"error_count": VWED.data.get("error_count", 0),
"task_count": len(VWED.data.get("completed_tasks", []))
}
}
def trigger_event(request_data):
event_name = request_data["body"].get("event_name")
event_data = request_data["body"].get("event_data", {})
if event_name:
# 异步触发事件
asyncio.create_task(VWED.event.emit(event_name, event_data))
return {"success": True, "event_triggered": event_name}
else:
return {"success": False, "error": "event_name is required"}
def register_custom_functions():
"""注册自定义函数"""
VWED.log.sync_info("注册自定义函数...")
# 传参数和定义执行逻辑分开
VWED.function.register(
name="get_statistics",
handler=get_statistics,
description="获取系统统计信息"
)
VWED.function.register(
name="reset_counters",
handler=reset_counters,
description="重置计数器"
)
def get_statistics(args):
return {
"login_count": VWED.data.get("login_count", 0),
"error_count": VWED.data.get("error_count", 0),
"completed_tasks": len(VWED.data.get("completed_tasks", [])),
"monitor_records": len(VWED.data.get("monitor_history", [])),
"initialized": VWED.data.get("initialized", False),
"init_time": VWED.data.get("init_time", None)
}
def reset_counters(args):
VWED.data.set("login_count", 0)
VWED.data.set("error_count", 0)
VWED.data.set("completed_tasks", [])
VWED.log.sync_info("计数器已重置")
return {"success": True, "reset_time": VWED.util.now()}
def register_event_listeners():
"""注册事件监听器"""
VWED.log.sync_info("注册事件监听器...")
# 传参数和定义执行逻辑分开
VWED.event.listen(
event_name="user_action",
handler=on_user_action
)
def on_user_action(event_data):
action = event_data.get("action", "unknown")
user_id = event_data.get("user_id", "unknown")
VWED.log.sync_info(f"用户操作: {user_id} 执行了 {action}")
# 记录用户操作
user_actions = VWED.data.get("user_actions", [])
user_actions.append({
"user_id": user_id,
"action": action,
"timestamp": VWED.util.now()
})
# 只保留最近50条记录
if len(user_actions) > 50:
user_actions = user_actions[-50:]
VWED.data.set("user_actions", user_actions)
def register_timer_tasks():
"""注册定时任务"""
VWED.log.sync_info("注册定时任务...")
# 传参数和定义执行逻辑分开
VWED.timer.interval(
interval=30, # 每30秒
handler=heartbeat
)
VWED.timer.once(
delay=5, # 5秒后执行一次
handler=delayed_initialization
)
def heartbeat():
heartbeat_count = VWED.data.get("heartbeat_count", 0)
VWED.data.set("heartbeat_count", heartbeat_count + 1)
if heartbeat_count % 10 == 0: # 每300秒5分钟记录一次
VWED.log.sync_info(f"系统心跳 #{heartbeat_count}")
def delayed_initialization():
VWED.log.sync_info("延迟初始化任务执行")
VWED.data.set("delayed_init_completed", True)
# 工具函数示例
def format_timestamp(timestamp_str):
"""格式化时间戳"""
try:
from datetime import datetime
dt = datetime.fromisoformat(timestamp_str.replace('Z', '+00:00'))
return dt.strftime("%Y-%m-%d %H:%M:%S")
except:
return timestamp_str
def calculate_average(numbers):
"""计算平均值"""
if not numbers:
return 0
return sum(numbers) / len(numbers)
```
---
## 6. 注册验证和调试技巧
### 6.1 验证注册状态
在脚本中可以添加验证代码来检查注册状态:
```python
def boot():
# ... 注册代码 ...
# 验证注册状态
verify_registrations()
def verify_registrations():
"""验证注册状态"""
# 可以通过API查询注册状态
# GET /api/script/registry/status
VWED.log.sync_info("验证注册状态...")
# 这里可以添加自定义验证逻辑
expected_functions = ["get_statistics", "reset_counters"]
expected_apis = ["/status", "/trigger-event"]
VWED.log.sync_info(f"预期注册函数: {expected_functions}")
VWED.log.sync_info(f"预期注册API: {expected_apis}")
```
### 6.2 调试技巧
```python
def boot():
try:
# 注册代码
register_all_services()
VWED.log.sync_info("✓ 所有服务注册成功")
except Exception as e:
VWED.log.sync_error(f"✗ 服务注册失败: {str(e)}")
# 可以根据需要添加详细的错误处理
def register_all_services():
"""集中注册所有服务"""
service_count = 0
# 注册API带计数
api_services = register_api_services()
service_count += api_services
# 注册函数(带计数)
function_services = register_custom_functions()
service_count += function_services
# 注册事件监听器(带计数)
event_services = register_event_listeners()
service_count += event_services
# 注册定时任务(带计数)
timer_services = register_timer_tasks()
service_count += timer_services
VWED.log.sync_info(f"总共注册了 {service_count} 个服务")
return service_count
```
---
## 总结
本文档提供了VWED脚本中各种注册声明的完整示例包括
1. **API接口注册** - 支持GET/POST/PUT/DELETE等HTTP方法
2. **自定义函数注册** - 供VWED任务系统调用的函数
3. **事件监听器注册** - 响应系统和自定义事件
4. **定时任务注册** - 周期性和一次性任务
每种类型都提供了从简单到复杂的多个示例帮助开发者快速掌握VWED脚本的注册机制。
关键要点:
- 所有注册都必须在 `boot()` 函数中进行
- 使用装饰器语法进行注册声明
- 支持详细的参数定义和文档描述
- 提供完整的错误处理和日志记录
- 支持异步和同步两种执行模式