charging-cabinet/tasks/017-fix-review-issues.md

96 lines
3.1 KiB
Markdown
Raw Normal View History

# 任务017重构审查问题修复
## 目标
修复TCP服务重构审查发现的P0/P1问题。
## 修复清单
### P0Redis类型冲突
**位置:** `device-server/src/main.rs`
**问题:** `register_node``SET`string类型`heartbeat``HSET`hash类型同一key操作触发`WRONGTYPE`错误。
**修复:** 统一用HSET
```rust
// 节点注册
async fn register_node(redis: &Redis, node_id: &str, ip: &str, tcp_port: u16) {
redis.hset(&format!("node:{}", node_id), &[
("ip", ip),
("tcp_port", &tcp_port.to_string()),
("status", "online"),
("last_heartbeat", &Instant::now().elapsed().as_secs().to_string()),
]).await;
redis.expire(&format!("node:{}", node_id), 300).await;
}
// 节点心跳
async fn heartbeat(redis: &Redis, node_id: &str) {
redis.hset(&format!("node:{}", node_id), &[
("last_heartbeat", &Instant::now().elapsed().as_secs().to_string()),
]).await;
redis.expire(&format!("node:{}", node_id), 300).await;
}
```
### P1节点管理双轨制
**问题:** API服务维护内存`NodeRegistry`设备服务直接写Redis两者不关联。
**修复方案A推荐** API服务从Redis读取节点信息
```rust
// API服务节点列表
async fn list_nodes(redis: &Redis) -> Result<Json<Vec<NodeInfo>>> {
let keys = redis.keys("node:*").await?;
let mut nodes = Vec::new();
for key in keys {
let node_id = key.strip_prefix("node:").unwrap();
let info: HashMap<String, String> = redis.hgetall(&key).await?;
nodes.push(NodeInfo {
id: node_id.to_string(),
ip: info.get("ip").cloned().unwrap_or_default(),
tcp_port: info.get("tcp_port").and_then(|p| p.parse().ok()).unwrap_or(0),
status: info.get("status").cloned().unwrap_or_default(),
last_heartbeat: info.get("last_heartbeat").cloned().unwrap_or_default(),
});
}
Ok(Json(nodes))
}
```
**修复方案B** 设备服务通过HTTP注册到API服务
- 设备服务启动时POST到`/api/nodes/register`
- API服务存内存
- 心跳POST到`/api/nodes/:id/heartbeat`
- 注销POST到`/api/nodes/:id/deregister`
### P2配置系统
**问题:** 代码用`dotenvy`读环境变量config.toml形同虚设。
**修复:** 二选一
- 方案A`toml` crate读config.toml
- 方案B删除config.toml只用.env
### P3协议结构体重复
**问题:** `DeviceMessage`等结构体在两个服务中重复定义。
**修复:** 暂不处理后续提取shared crate时统一。
### P4限流器同步Mutex
**问题:** 限流器用`std::sync::Mutex`,不符合异步规范。
**修复:** 改用`tokio::sync::Mutex``RwLock`
## 质量约束
1. 完成代码后执行 `cargo check` + `cargo clippy`,零报错零警告
2. 分层拆分单函数≤80行命名语义化完整注释
3. 所有外部IO/网络请求异常捕获禁止裸panic
4. 分支逻辑全覆盖,不遗漏兜底分支
5. 常量抽离不使用废弃API
6. Rust内存安全合理管理所有权禁用unsafe无合理理由