diff --git a/README.md b/README.md index 290ec13..7a9dd25 100644 --- a/README.md +++ b/README.md @@ -158,7 +158,7 @@ "chargeDurationSeconds": 120, // 如果在充电状态,已充电时长(秒) "errorCode": 0, // 0表示无错误,其他值表示特定错误类型 "message": "Status normal", // 附加信息,例如错误描述 - "activeTaskId": "session_xyz123" // 如果设备当前正在执行某个任务或会话,上报其ID + "activeTaskId": "session_xyz123" // 如果设备当前正在执行某个充电会话,上报其会话ID。后端主要通过ACK中的task_id来驱动任务和会话状态变更,此字段更多用于状态同步或辅助信息。 } ``` @@ -196,44 +196,67 @@ * **统一下行指令主题格式**: `yupi_mqtt_power_project/robot/command/{spotUid}` * `{spotUid}`: 目标充电桩的唯一标识符。 * **消息格式 (Payload)**: JSON。 - JSON消息体内部包含了具体的指令类型和所需参数。 + JSON消息体内部包含了具体的指令类型和所需参数。后端 `MqttServiceImpl.sendCommand` 方法会自动向 payload 中注入 `taskId`。 - **示例 - 移动到车位指令 (后端实际发送格式):** - 此指令指示机器人移动到指定车位。**机器人到达后将自动进入充电状态并上报。** - 后端实际发送的指令可能使用 `command` 字段。 + **示例 - `MOVE_TO_SPOT` 指令 (后端实际发送格式):** ```json { "command": "MOVE", - "target_spot_uid": "SPOT_UID_001", - "taskId": "backend_task_id_for_ack_789", - "sessionId": "session_abc_123" + "targetSpotUid": "SPOT_UID_001", + "sessionId": "session_xyz123", // 充电会话ID,由后端业务逻辑注入 + "taskId": 123 // 机器人任务ID,由MqttServiceImpl自动注入 } ``` - * 单片机固件 (`esp32_robot_firmware`) 已兼容解析 `command` 或 `commandType` 字段作为指令类型。 + *说明:单片机固件已兼容处理 `command` 字段为 `MOVE` 的指令,并将其映射为 `MOVE_TO_SPOT` 行为。* - **示例 - 停止充电指令 (STOP_CHARGE):** + **示例 - `STOP_CHARGE` 指令:** ```json { - "commandType": "STOP_CHARGE", - "taskId": "backend_task_id_for_ack_000", - "sessionId": "session_abc_123" // 关联的充电会话ID + "command": "STOP_CHARGE", + "sessionId": "session_xyz123", // 充电会话ID + "taskId": 456 // 机器人任务ID,由MqttServiceImpl自动注入 } ``` - **示例 - 开始充电指令 (START_CHARGE):** - **注意: 此指令当前未被后端主动使用。业务逻辑已调整为机器人到达车位后自动开始充电 (`MOVE_TO_SPOT` 完成即充电)。保留此指令定义主要为了兼容性或未来可能的扩展。单片机固件目前仅简单ACK此指令。** + **示例 - `START_CHARGE` 指令 (目前后端不再主动发送,仅作兼容性说明):** ```json { - "commandType": "START_CHARGE", - "taskId": "backend_task_id_for_ack_111", - "sessionId": "session_def_456" // 关联的充电会话ID + "command": "START_CHARGE", + "sessionId": "session_xyz123", // 充电会话ID + "taskId": 789 // 机器人任务ID,由MqttServiceImpl自动注入 } ``` - * **单片机处理逻辑**: 单片机收到消息后,需解析JSON负载,识别 `commandType`,提取 `taskId` (用于后续ACK),并获取其他指令参数来执行相应操作。 - * 对于 `MOVE_TO_SPOT` (或后端发送的`MOVE`): 执行移动,到达后自动转换到 `CHARGING` 状态,并上报符合后端期望格式的ACK (包含`command_ack`, `task_id`, `success`等)及新状态。 - * 对于 `STOP_CHARGE`: 停止充电(如断开继电器),更新状态为 `COMPLETED` (或 `IDLE`),并上报符合后端期望格式的ACK及新状态。 - * 对于 `START_CHARGE` (当前): 仅发送符合后端期望格式的ACK表示收到指令。 +### 4.3. 单片机主要指令处理逻辑 + +#### 4.3.1. `MOVE_TO_SPOT` 指令处理 + +* **指令接收**: 单片机收到 `command` 为 `MOVE` 的指令。 +* **执行流程**: + 1. 解析 `targetSpotUid`,开始向目标车位移动。 + 2. 将自身 `actualRobotStatus` 更新为 `MOVING`,并周期性上报状态。 + 3. 成功到达目标车位后,根据“到达即充电”的业务逻辑,机器人**立即**将自身 `actualRobotStatus` 更新为 `CHARGING`。 + 4. 向后端发送 `MOVE_TO_SPOT` 任务的 ACK 消息,其中 `success` 为 `true`,`actualRobotStatus` 为 `CHARGING`。 +* **后端响应**: 后端收到 ACK 后,将 `RobotTask` 标记为 `COMPLETED`,并调用 `ChargingSessionServiceImpl.handleRobotArrival()` 将充电会话状态更新为 `CHARGING_STARTED`,记录充电开始时间。 + +#### 4.3.2. `STOP_CHARGE` 指令处理 + +* **指令接收**: 单片机收到 `command` 为 `STOP_CHARGE` 的指令。 +* **执行流程**: + 1. 停止充电。 + 2. 将自身 `actualRobotStatus` 更新为 `IDLE` 或 `AVAILABLE`。 + 3. 向后端发送 `STOP_CHARGE` 任务的 ACK 消息,其中 `success` 为 `true`。 +* **后端响应**: 后端收到 ACK 后,将 `RobotTask` 标记为 `COMPLETED`,并调用 `ChargingSessionServiceImpl.handleChargingEnd()` 处理充电结束、费用计算和会话终结。 + +#### 4.3.3. `START_CHARGE` 指令处理 + +* **指令接收**: 单片机收到 `command` 为 `START_CHARGE` 的指令。 +* **执行流程**: + 1. 开始充电。 + 2. 将自身 `actualRobotStatus` 更新为 `CHARGING`。 + 3. 向后端发送 `START_CHARGE` 任务的 ACK 消息,其中 `success` 为 `true`。 +* **后端响应**: 后端收到 ACK 后,将 `RobotTask` 标记为 `COMPLETED`,并调用 `ChargingSessionServiceImpl.handleChargingStart()` 处理充电开始。 +* **重要说明**: **在当前“到达即充电”的业务逻辑下,后端不再主动向机器人发送 `START_CHARGE` MQTT 指令。机器人完成 `MOVE_TO_SPOT` 任务并到达车位后,会立即自动开始充电并上报 `CHARGING` 状态。此指令的保留主要是为了兼容性或未来可能的业务扩展。** ### 4.3. 单片机开发关键逻辑 (基于 `esp32_robot_firmware`) 1. **配置 (`config.h`)**: 仔细配置WiFi凭据、MQTT Broker、`DEVICE_UID`以及所有硬件引脚。 @@ -346,4 +369,4 @@ * (可选) 进一步优化Payload的展示,例如对JSON格式的Payload进行美化或提供折叠/展开功能。 * (可选) 根据实际需求,考虑日志数据的定期归档或清理策略的实现。 * 考虑引入更高级的 MQTT 特性,如QoS、遗嘱消息等。 -* 前端 UI/UX 持续打磨,提升用户体验。 \ No newline at end of file +* 前端 UI/UX 持续打磨,提升用户体验。 \ No newline at end of file