Files
java-template/docs/simple_alert_optimization.md
T
BrunoGaoandClaude 3248bb0a2a feat: 完成消息系统V2优化 - 基于user_id的高性能索引重构
## 主要更改

### 1. 数据库表结构增强
- **t_device_message_v2**: 新增7个关键字段
  - priority_level: 优先级数值(1-5)
  - channels: 分发渠道JSON
  - require_ack: 是否需要确认
  - metadata: 扩展元数据JSON
  - target_count: 目标用户总数
  - version: 乐观锁版本号

- **t_device_message_detail_v2**: 新增8个关键字段
  - distribution_id: 分发唯一ID
  - device_sn: 设备序列号
  - user_id: 用户ID(核心查询字段)
  - response_duration: 响应耗时
  - delivery_details: 分发详情JSON
  - client_info: 客户端信息JSON
  - location_info: 位置信息JSON
  - last_retry_time: 最后重试时间

### 2. 索引优化重构 (基于user_id)
- 删除原有device_sn相关索引
- 新建5个user_id高性能复合索引:
  - idx_customer_user_time: 客户+用户+时间
  - idx_customer_user_status: 客户+用户+状态
  - idx_customer_user_type: 客户+用户+类型
  - idx_user_org_priority: 用户+组织+优先级
  - idx_user_status_time: 用户+状态+时间

- detail表新建4个user_id相关索引:
  - uk_message_user_target: 唯一约束
  - idx_customer_user_status: 客户+用户+状态
  - idx_user_channel_time: 用户+渠道+时间
  - idx_user_delivery_status: 用户+分发状态

### 3. 数据迁移和初始化
- 自动生成distribution_id
- 根据urgency设置priority_level
- 初始化默认channels配置
- 保持现有数据完整性

### 4. 性能提升预期
- 用户消息查询: 预计10-20倍性能提升
- 确认状态查询: 支持快速人员清单检索
- 存储空间: JSON字段替代冗余VARCHAR
- 查询覆盖: 所有user_id查询都能命中索引

### 5. 文档和脚本
- 完整的V2优化SQL脚本
- 消息机制设计文档
- 数据库备份(22MB)
- 性能验证查询

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <[email protected]>
2025-09-15 07:56:03 +08:00

254 lines
8.9 KiB
Markdown

# 简洁告警系统优化方案
## 📋 基于现有代码的简单改进
基于对 ljwx-bigscreen 现有 `generate_alerts` 函数的分析,提供最简洁有效的优化方案。
## 🔍 现状分析
### 当前 generate_alerts 函数问题:
1. **规则查询无过滤** - 每次都加载所有告警规则,未按数据类型过滤
2. **重复设备信息查询** - 每条规则都可能重复查询相同设备信息
3. **缺乏通知渠道处理** - 触发告警后没有自动通知机制
### 现有优势:
- 已有 Redis 缓存机制
- 已有规则预编译逻辑
- 数据库查询已优化
## 🚀 三个简单优化
### 1. 规则按数据类型过滤 (最简单改进)
**问题**: 当前所有规则都被加载,浪费处理时间
**解决**: 在 `generate_alerts` 函数中按 physical_sign 过滤规则
```python
def generate_alerts(data, health_data_id):
# 现有代码...获取所有规则
# 🚀 新增: 从数据中提取当前的 physical_sign 类型
current_physical_signs = set()
for key in data.keys():
if key in ['heartRate', 'bloodOxygen', 'temperature', 'pressureHigh', 'pressureLow',
'stress', 'step', 'calorie', 'distance', 'sleep']:
# 将前端字段映射到数据库字段
sign_mapping = {
'heartRate': 'heart_rate',
'bloodOxygen': 'blood_oxygen',
'pressureHigh': 'bloodPressure',
'pressureLow': 'bloodPressure',
'step': 'steps'
}
current_physical_signs.add(sign_mapping.get(key, key))
# 🚀 过滤规则: 只处理当前数据相关的规则
filtered_rules = {}
for rule_id, rule in alert_rules_dict.items():
physical_sign = rule.get('physical_sign')
if physical_sign in current_physical_signs:
filtered_rules[rule_id] = rule
print(f"📋 规则过滤: {len(alert_rules_dict)} -> {len(filtered_rules)} 条")
# 后续处理使用 filtered_rules 替代 alert_rules_dict
alert_rules_dict = filtered_rules
# 现有代码继续...
```
### 2. 设备信息缓存 (性能提升)
**问题**: `get_device_user_org_info` 在每个规则匹配时都可能被调用
**解决**: 在函数开头一次性获取并缓存
```python
def generate_alerts(data, health_data_id):
# 现有代码...
# 🚀 新增: 提前获取设备信息并缓存
device_sn = data.get('deviceSn')
device_info_cache = None
if device_sn:
try:
device_info_cache = get_device_user_org_info(device_sn)
print(f"📱 设备信息已缓存: {device_sn}")
except Exception as e:
print(f"⚠️ 获取设备信息失败: {e}")
# 遍历规则时使用缓存的设备信息
for rule_id, rule in filtered_rules.items():
# 现有规则匹配逻辑...
# 当需要设备信息时,使用缓存
if device_info_cache:
user_id = device_info_cache.get('user_id')
org_id = device_info_cache.get('org_id')
user_name = device_info_cache.get('user_name', 'Unknown')
# 使用缓存的信息而不是重复查询
```
### 3. 简单通知渠道处理
**问题**: 告警生成后没有自动通知机制
**解决**: 在现有告警保存后添加简单的通知处理
```python
def send_simple_notification(alert_info, device_info):
"""简单的通知发送函数"""
try:
user_name = device_info.get('user_name', 'Unknown')
org_name = device_info.get('org_name', 'Unknown')
# 构建通知消息
message = f"【健康告警】{user_name}({org_name}) - {alert_info.get('alert_type', '')}: {alert_info.get('alert_desc', '')}"
# 如果有微信配置,发送微信通知
if hasattr(current_app, 'config') and current_app.config.get('WECHAT_ENABLED'):
openid = device_info.get('openid') # 需要在设备信息中包含openid
if openid:
send_wechat_alert(
alert_type=alert_info.get('alert_type'),
user_openid=openid,
user_name=user_name,
severity_level=alert_info.get('severity_level', 'medium')
)
print(f"📱 微信通知已发送: {user_name}")
# 记录通知日志
print(f"🔔 告警通知: {message}")
except Exception as e:
print(f"⚠️ 通知发送失败: {e}")
def generate_alerts(data, health_data_id):
# 现有代码...处理规则匹配
# 在保存告警后添加通知
if alert_triggered: # 当有告警触发时
# 现有保存逻辑...
# 🚀 新增: 发送通知
try:
send_simple_notification(alert_info, device_info_cache)
except Exception as notify_error:
print(f"通知发送异常: {notify_error}")
```
## 📝 完整集成代码
将以上三个改进集成到现有 `generate_alerts` 函数:
```python
def generate_alerts(data, health_data_id):
start_time = time.time()
try:
print(f"🔍 generate_alerts started with data keys: {list(data.keys()) if data else 'None'}")
# 现有代码: 获取告警规则...
customer_id = data.get('customer_id') or data.get('customerId')
alert_rules_dict = {}
cache_hit = False
# [保留现有的规则获取逻辑]
# ...
# 🚀 优化1: 规则按数据类型过滤
current_physical_signs = set()
sign_mapping = {
'heartRate': 'heart_rate', 'bloodOxygen': 'blood_oxygen',
'pressureHigh': 'bloodPressure', 'pressureLow': 'bloodPressure',
'step': 'steps', 'calorie': 'calories', 'distance': 'distance',
'temperature': 'temperature', 'stress': 'stress', 'sleep': 'sleep'
}
for key in data.keys():
if key in sign_mapping:
current_physical_signs.add(sign_mapping[key])
# 过滤规则
filtered_rules = {rid: rule for rid, rule in alert_rules_dict.items()
if rule.get('physical_sign') in current_physical_signs}
print(f"📋 规则过滤: {len(alert_rules_dict)} -> {len(filtered_rules)}")
# 🚀 优化2: 设备信息预获取
device_sn = data.get('deviceSn')
device_info_cache = None
if device_sn:
try:
device_info_cache = get_device_user_org_info(device_sn)
except Exception as e:
print(f"⚠️ 设备信息获取失败: {e}")
# 现有规则匹配逻辑,使用 filtered_rules 和 device_info_cache
abnormal_counts = {}
alerts_generated = 0
for rule_id, rule in filtered_rules.items():
# [保留现有的规则匹配逻辑]
# 使用 device_info_cache 替代重复查询
# 当触发告警时
if alert_condition_met: # 现有的触发条件判断
# [保留现有的告警创建和保存逻辑]
# 🚀 优化3: 简单通知处理
if device_info_cache:
try:
send_simple_notification(alert_info, device_info_cache)
except Exception as notify_error:
print(f"通知异常: {notify_error}")
alerts_generated += 1
processing_time = round((time.time() - start_time) * 1000, 2)
print(f"⏱️ generate_alerts 完成: 处理{len(filtered_rules)}条规则, 生成{alerts_generated}个告警, 耗时{processing_time}ms")
return alerts_generated
except Exception as e:
print(f"❌ generate_alerts 异常: {e}")
return 0
```
## 📊 预期效果
### 性能提升
- **规则过滤**: 减少 60-80% 不必要的规则处理
- **设备查询**: 消除重复查询,节省 50-70% 数据库调用
- **响应时间**: 整体处理时间减少 40-60%
### 功能增强
- **自动通知**: 告警触发后自动发送通知
- **日志完善**: 更清晰的处理过程日志
- **错误处理**: 更好的异常处理机制
## 🔧 部署建议
### 实施步骤
1. **第一步**: 仅实施规则过滤优化 (风险最小)
2. **第二步**: 添加设备信息缓存 (性能提升明显)
3. **第三步**: 集成通知处理 (功能增强)
### 配置要求
```python
# config.py 中添加
WECHAT_ENABLED = True # 是否启用微信通知
NOTIFICATION_ENABLED = True # 是否启用通知功能
```
### 监控要点
- 规则过滤效率: 过滤前后规则数量
- 设备查询次数: 确认缓存生效
- 通知成功率: 监控通知发送情况
这个方案基于现有代码架构,改动最小,风险可控,可以立即实施并看到效果。
---
*简化版本: v1.0*
*基于现有代码: ljwx-bigscreen/alert.py*