From ad64840cc04dac2278ca02f22ddc02b1a218e9cf Mon Sep 17 00:00:00 2001
From: wanshenmean <cathay_xy@163.com>
Date: 星期三, 15 四月 2026 22:44:18 +0800
Subject: [PATCH] feat(机器人任务): 实现换盘任务假电芯补充逻辑

---
 Code/.omc/state/mission-state.json                                                          |  146 ++++++
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/RobotTaskService.cs                   |    2 
 Code/WMS/WIDESEA_WMSServer/WIDESEA_DTO/Task/WMSTaskDTO.cs                                   |    5 
 Code/.omc/state/agent-replay-80f81c54-c5ed-4867-b777-d2d640ee3b40.jsonl                     |    1 
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoRepository/FakeBatteryPositionRepository.cs   |   90 +++
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_DTO/TaskInfo/WMSTaskDTO.cs                            |    5 
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoRepository/IFakeBatteryPositionRepository.cs |   39 +
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotJob.cs                            |    5 
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/RobotWorkflowOrchestrator.cs  |   64 ++
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoService/IFakeBatteryPositionService.cs       |   49 ++
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs                  |   80 +++
 Code/.omc/state/agent-replay-d836b656-7d6b-4a00-b9ed-f46b82f58345.jsonl                     |   21 
 Code/WMS/WIDESEA_WMSServer/WIDESEA_TaskInfoService/WCS/TaskService_Robot.cs                 |    3 
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotSocketState.cs                    |    8 
 Code/.omc/state/idle-notif-cooldown.json                                                    |    2 
 Code/.omc/state/last-tool-error.json                                                        |    8 
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/FakeBatteryPositionService.cs         |   69 +++
 Code/.omc/state/subagent-tracking.json                                                      |   87 +++
 Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Model/Models/TaskInfo/Dt_FakeBatteryPosition.cs       |   50 ++
 Code/docs/superpowers/plans/2026-04-15-change-pallet-fake-battery.md                        |  640 +++++++++++++++++++++++++++
 20 files changed, 1,358 insertions(+), 16 deletions(-)

diff --git a/Code/.omc/state/agent-replay-80f81c54-c5ed-4867-b777-d2d640ee3b40.jsonl b/Code/.omc/state/agent-replay-80f81c54-c5ed-4867-b777-d2d640ee3b40.jsonl
new file mode 100644
index 0000000..ff39975
--- /dev/null
+++ b/Code/.omc/state/agent-replay-80f81c54-c5ed-4867-b777-d2d640ee3b40.jsonl
@@ -0,0 +1 @@
+{"t":0,"agent":"system","event":"skill_invoked","skill_name":"superpowers:brainstorming"}
diff --git a/Code/.omc/state/agent-replay-d836b656-7d6b-4a00-b9ed-f46b82f58345.jsonl b/Code/.omc/state/agent-replay-d836b656-7d6b-4a00-b9ed-f46b82f58345.jsonl
new file mode 100644
index 0000000..7b34b65
--- /dev/null
+++ b/Code/.omc/state/agent-replay-d836b656-7d6b-4a00-b9ed-f46b82f58345.jsonl
@@ -0,0 +1,21 @@
+{"t":0,"agent":"system","event":"skill_invoked","skill_name":"superpowers:writing-plans"}
+{"t":0,"agent":"system","event":"skill_invoked","skill_name":"superpowers:subagent-driven-development"}
+{"t":0,"agent":"a2061bd","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a2061bd","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":44758}
+{"t":0,"agent":"a33f78a","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a33f78a","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":81574}
+{"t":0,"agent":"a9c381b","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a9c381b","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":81306}
+{"t":0,"agent":"a614ea5","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a614ea5","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":72773}
+{"t":0,"agent":"a3143b3","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a3143b3","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":90995}
+{"t":0,"agent":"a177bc3","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a177bc3","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":88225}
+{"t":0,"agent":"a550b7f","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a550b7f","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":41024}
+{"t":0,"agent":"acd1aa5","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"acd1aa5","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":90649}
+{"t":0,"agent":"a991ee2","agent_type":"general-purpose","event":"agent_start","parent_mode":"none"}
+{"t":0,"agent":"a991ee2","agent_type":"general-purpose","event":"agent_stop","success":true,"duration_ms":246360}
+{"t":0,"agent":"system","event":"skill_invoked","skill_name":"superpowers:finishing-a-development-branch"}
diff --git a/Code/.omc/state/idle-notif-cooldown.json b/Code/.omc/state/idle-notif-cooldown.json
index addf827..83bb211 100644
--- a/Code/.omc/state/idle-notif-cooldown.json
+++ b/Code/.omc/state/idle-notif-cooldown.json
@@ -1,3 +1,3 @@
 {
-  "lastSentAt": "2026-04-15T11:40:34.475Z"
+  "lastSentAt": "2026-04-15T14:42:46.838Z"
 }
\ No newline at end of file
diff --git a/Code/.omc/state/last-tool-error.json b/Code/.omc/state/last-tool-error.json
index f5ba7de..8d171f3 100644
--- a/Code/.omc/state/last-tool-error.json
+++ b/Code/.omc/state/last-tool-error.json
@@ -1,7 +1,7 @@
 {
   "tool_name": "Bash",
-  "tool_input_preview": "{\"command\":\"ls \\\"D:\\\\Git\\\\ShanMeiXinNengYuan\\\\Code\\\\WMS\\\\WIDESEA_WMSClient\\\\src\\\\api\\\\\\\" 2>/dev/null | head -20\",\"description\":\"Check api directory structure\"}",
-  "error": "Exit code 2\n/usr/bin/bash: eval: line 1: unexpected EOF while looking for matching `\"'",
-  "timestamp": "2026-04-13T03:27:59.200Z",
-  "retry_count": 6
+  "tool_input_preview": "{\"command\":\"dotnet build D:/Git/ShanMeiXinNengYuan/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Server.sln\",\"timeout\":300000,\"description\":\"Build WCS solution to verify fix\"}",
+  "error": "Exit code 1\n  姝e湪纭畾瑕佽繕鍘熺殑椤圭洰鈥r\n  鎵�鏈夐」鐩潎鏄渶鏂扮殑锛屾棤娉曡繕鍘熴�俓r\n  WIDESEAWCS_Common -> D:\\Git\\ShanMeiXinNengYuan\\Code\\WCS\\WIDESEAWCS_Server\\WIDESEAWCS_Common\\bin\\Debug\\net8.0\\WIDESEAWCS_Common.dll\r\nD:\\Git\\ShanMeiXinNengYuan\\Code\\WCS\\WIDESEAWCS_Server\\WIDESEAWCS_Communicator\\AllenBrandly\\AllenBrandlyEtherNetCommunicator.cs(110,80): warning CS1570: XML 娉ㄩ噴鍑虹幇 XML 鏍煎紡閿欒 --鈥滅粨鏉熸爣璁扳�減aram鈥濅笌寮�濮嬫爣璁扳�淭鈥濅笉鍖归厤銆傗�� [D:\\Git\\ShanMeiXinNengYuan\\Code\\WCS\\WIDESEAWCS_Server\\WIDESEAWCS_Communicator\\WIDESEAWCS_Communicator.csproj]\r\nD:\\Git\\ShanM...",
+  "timestamp": "2026-04-15T14:12:47.386Z",
+  "retry_count": 1
 }
\ No newline at end of file
diff --git a/Code/.omc/state/mission-state.json b/Code/.omc/state/mission-state.json
index 5cd366a..46bc1bf 100644
--- a/Code/.omc/state/mission-state.json
+++ b/Code/.omc/state/mission-state.json
@@ -1,5 +1,5 @@
 {
-  "updatedAt": "2026-04-15T06:10:46.493Z",
+  "updatedAt": "2026-04-15T14:16:41.286Z",
   "missions": [
     {
       "id": "session:9007b9ea-1eb6-4d24-8fe7-2c3a949eac88:none",
@@ -476,6 +476,150 @@
           "sourceKey": "session-stop:a48e41df38204e6dc"
         }
       ]
+    },
+    {
+      "id": "session:d836b656-7d6b-4a00-b9ed-f46b82f58345:none",
+      "source": "session",
+      "name": "none",
+      "objective": "Session mission",
+      "createdAt": "2026-04-15T14:00:27.304Z",
+      "updatedAt": "2026-04-15T14:16:41.286Z",
+      "status": "done",
+      "workerCount": 9,
+      "taskCounts": {
+        "total": 9,
+        "pending": 0,
+        "blocked": 0,
+        "inProgress": 0,
+        "completed": 9,
+        "failed": 0
+      },
+      "agents": [
+        {
+          "name": "general-purpose:a2061bd",
+          "role": "general-purpose",
+          "ownership": "a2061bd1c8b6f066e",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:01:12.062Z"
+        },
+        {
+          "name": "general-purpose:a33f78a",
+          "role": "general-purpose",
+          "ownership": "a33f78a441c700f07",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:03:00.165Z"
+        },
+        {
+          "name": "general-purpose:a9c381b",
+          "role": "general-purpose",
+          "ownership": "a9c381b5f67087dae",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:04:44.132Z"
+        },
+        {
+          "name": "general-purpose:a614ea5",
+          "role": "general-purpose",
+          "ownership": "a614ea573436c827d",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:06:11.349Z"
+        },
+        {
+          "name": "general-purpose:a3143b3",
+          "role": "general-purpose",
+          "ownership": "a3143b3511395abdc",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:08:04.129Z"
+        },
+        {
+          "name": "general-purpose:a177bc3",
+          "role": "general-purpose",
+          "ownership": "a177bc320ae6cc4dc",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:09:53.582Z"
+        },
+        {
+          "name": "general-purpose:a550b7f",
+          "role": "general-purpose",
+          "ownership": "a550b7f6cb598b4c0",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:10:46.231Z"
+        },
+        {
+          "name": "general-purpose:acd1aa5",
+          "role": "general-purpose",
+          "ownership": "acd1aa52bf3dd06d4",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:12:28.373Z"
+        },
+        {
+          "name": "general-purpose:a991ee2",
+          "role": "general-purpose",
+          "ownership": "a991ee262522932f5",
+          "status": "done",
+          "currentStep": null,
+          "latestUpdate": "completed",
+          "completedSummary": null,
+          "updatedAt": "2026-04-15T14:16:41.286Z"
+        }
+      ],
+      "timeline": [
+        {
+          "id": "session-start:acd1aa52bf3dd06d4:2026-04-15T14:10:57.724Z",
+          "at": "2026-04-15T14:10:57.724Z",
+          "kind": "update",
+          "agent": "general-purpose:acd1aa5",
+          "detail": "started general-purpose:acd1aa5",
+          "sourceKey": "session-start:acd1aa52bf3dd06d4"
+        },
+        {
+          "id": "session-stop:acd1aa52bf3dd06d4:2026-04-15T14:12:28.373Z",
+          "at": "2026-04-15T14:12:28.373Z",
+          "kind": "completion",
+          "agent": "general-purpose:acd1aa5",
+          "detail": "completed",
+          "sourceKey": "session-stop:acd1aa52bf3dd06d4"
+        },
+        {
+          "id": "session-start:a991ee262522932f5:2026-04-15T14:12:34.926Z",
+          "at": "2026-04-15T14:12:34.926Z",
+          "kind": "update",
+          "agent": "general-purpose:a991ee2",
+          "detail": "started general-purpose:a991ee2",
+          "sourceKey": "session-start:a991ee262522932f5"
+        },
+        {
+          "id": "session-stop:a991ee262522932f5:2026-04-15T14:16:41.286Z",
+          "at": "2026-04-15T14:16:41.286Z",
+          "kind": "completion",
+          "agent": "general-purpose:a991ee2",
+          "detail": "completed",
+          "sourceKey": "session-stop:a991ee262522932f5"
+        }
+      ]
     }
   ]
 }
\ No newline at end of file
diff --git a/Code/.omc/state/subagent-tracking.json b/Code/.omc/state/subagent-tracking.json
index c935479..8ac075d 100644
--- a/Code/.omc/state/subagent-tracking.json
+++ b/Code/.omc/state/subagent-tracking.json
@@ -296,10 +296,91 @@
       "status": "completed",
       "completed_at": "2026-04-15T06:10:46.493Z",
       "duration_ms": 51400
+    },
+    {
+      "agent_id": "a2061bd1c8b6f066e",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:00:27.304Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:01:12.062Z",
+      "duration_ms": 44758
+    },
+    {
+      "agent_id": "a33f78a441c700f07",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:01:38.591Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:03:00.165Z",
+      "duration_ms": 81574
+    },
+    {
+      "agent_id": "a9c381b5f67087dae",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:03:22.826Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:04:44.132Z",
+      "duration_ms": 81306
+    },
+    {
+      "agent_id": "a614ea573436c827d",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:04:58.576Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:06:11.349Z",
+      "duration_ms": 72773
+    },
+    {
+      "agent_id": "a3143b3511395abdc",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:06:33.134Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:08:04.129Z",
+      "duration_ms": 90995
+    },
+    {
+      "agent_id": "a177bc320ae6cc4dc",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:08:25.357Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:09:53.582Z",
+      "duration_ms": 88225
+    },
+    {
+      "agent_id": "a550b7f6cb598b4c0",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:10:05.207Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:10:46.231Z",
+      "duration_ms": 41024
+    },
+    {
+      "agent_id": "acd1aa52bf3dd06d4",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:10:57.724Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:12:28.373Z",
+      "duration_ms": 90649
+    },
+    {
+      "agent_id": "a991ee262522932f5",
+      "agent_type": "general-purpose",
+      "started_at": "2026-04-15T14:12:34.926Z",
+      "parent_mode": "none",
+      "status": "completed",
+      "completed_at": "2026-04-15T14:16:41.286Z",
+      "duration_ms": 246360
     }
   ],
-  "total_spawned": 33,
-  "total_completed": 33,
+  "total_spawned": 42,
+  "total_completed": 42,
   "total_failed": 0,
-  "last_updated": "2026-04-15T06:10:46.596Z"
+  "last_updated": "2026-04-15T14:16:41.394Z"
 }
\ No newline at end of file
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_DTO/TaskInfo/WMSTaskDTO.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_DTO/TaskInfo/WMSTaskDTO.cs
index de3829d..d3d36ef 100644
--- a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_DTO/TaskInfo/WMSTaskDTO.cs
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_DTO/TaskInfo/WMSTaskDTO.cs
@@ -66,6 +66,11 @@
         public int Grade { get; set; }
 
         /// <summary>
+        /// 浠诲姟鏁伴噺
+        /// </summary>
+        public int TaskQuantity { get; set; }
+
+        /// <summary>
         /// 
         /// </summary>
         public int WarehouseId { get; set; }
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoRepository/IFakeBatteryPositionRepository.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoRepository/IFakeBatteryPositionRepository.cs
new file mode 100644
index 0000000..72701e1
--- /dev/null
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoRepository/IFakeBatteryPositionRepository.cs
@@ -0,0 +1,39 @@
+using WIDESEAWCS_Core.BaseRepository;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_ITaskInfoRepository
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃粨鍌ㄦ帴鍙�
+    /// </summary>
+    public interface IFakeBatteryPositionRepository : IRepository<Dt_FakeBatteryPosition>
+    {
+        /// <summary>
+        /// 鑾峰彇涓婲涓彲鐢ㄧ殑鍋囩數鑺钩闈㈢偣浣�
+        /// </summary>
+        /// <param name="count">闇�瑕佽幏鍙栫殑鐐逛綅鏁伴噺</param>
+        /// <returns>鍙敤鐐逛綅鍒楄〃锛屾寜PositionIndex鍗囧簭</returns>
+        List<int> GetNextAvailable(int count);
+
+        /// <summary>
+        /// 閲嶇疆鎵�鏈夌偣浣嶄负鏈娇鐢�
+        /// </summary>
+        /// <returns>褰卞搷鐨勮鏁�</returns>
+        int ResetAll();
+
+        /// <summary>
+        /// 鏍囪鎸囧畾鐐逛綅涓哄凡浣跨敤
+        /// </summary>
+        /// <param name="positions">鐐逛綅绱㈠紩鍒楄〃</param>
+        /// <returns>鏄惁鎴愬姛</returns>
+        bool MarkAsUsed(List<int> positions);
+
+        /// <summary>
+        /// 鏍规嵁琛屽拰鍒楄幏鍙栫偣浣嶇储寮�
+        /// </summary>
+        /// <param name="row">琛岋紙1-3锛�</param>
+        /// <param name="col">鍒楋紙1-16锛�</param>
+        /// <returns>鐐逛綅绱㈠紩锛�1-48锛夛紝鎵句笉鍒拌繑鍥瀗ull</returns>
+        int? GetPositionIndex(int row, int col);
+    }
+}
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoService/IFakeBatteryPositionService.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoService/IFakeBatteryPositionService.cs
new file mode 100644
index 0000000..11771e7
--- /dev/null
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoService/IFakeBatteryPositionService.cs
@@ -0,0 +1,49 @@
+using WIDESEAWCS_Core.BaseServices;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_ITaskInfoService
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃湇鍔℃帴鍙�
+    /// </summary>
+    public interface IFakeBatteryPositionService : IService<Dt_FakeBatteryPosition>
+    {
+        /// <summary>
+        /// 鑾峰彇涓婲涓彲鐢ㄧ殑鍋囩數鑺钩闈㈢偣浣�
+        /// </summary>
+        /// <param name="count">闇�瑕佽幏鍙栫殑鐐逛綅鏁伴噺</param>
+        /// <returns>鍙敤鐐逛綅鍒楄〃锛屾寜PositionIndex鍗囧簭</returns>
+        List<int> GetNextAvailable(int count);
+
+        /// <summary>
+        /// 閲嶇疆鎵�鏈夌偣浣嶄负鏈娇鐢�
+        /// </summary>
+        /// <returns>褰卞搷鐨勮鏁�</returns>
+        int ResetAll();
+
+        /// <summary>
+        /// 鏍囪鎸囧畾鐐逛綅涓哄凡浣跨敤
+        /// </summary>
+        /// <param name="positions">鐐逛綅绱㈠紩鍒楄〃</param>
+        /// <returns>鏄惁鎴愬姛</returns>
+        bool MarkAsUsed(List<int> positions);
+
+        /// <summary>
+        /// 鏍规嵁琛屽拰鍒楄幏鍙栫偣浣嶇储寮�
+        /// </summary>
+        /// <param name="row">琛岋紙1-3锛�</param>
+        /// <param name="col">鍒楋紙1-16锛�</param>
+        /// <returns>鐐逛綅绱㈠紩锛�1-48锛夛紝鎵句笉鍒拌繑鍥瀗ull</returns>
+        int? GetPositionIndex(int row, int col);
+
+        /// <summary>
+        /// 鍒濆鍖栧亣鐢佃姱鐐逛綅琛紙48涓偣浣嶏級
+        /// </summary>
+        /// <remarks>
+        /// 浠呭綋琛ㄤ负绌烘椂鎻掑叆1-48鐨勫垵濮嬫暟鎹��
+        /// 3琛屆�16鍒楋紝琛屼紭鍏堟帓鍒椼��
+        /// </remarks>
+        /// <returns>鏄惁鎴愬姛</returns>
+        bool InitializeIfEmpty();
+    }
+}
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Model/Models/TaskInfo/Dt_FakeBatteryPosition.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Model/Models/TaskInfo/Dt_FakeBatteryPosition.cs
new file mode 100644
index 0000000..c06e006
--- /dev/null
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Model/Models/TaskInfo/Dt_FakeBatteryPosition.cs
@@ -0,0 +1,50 @@
+using SqlSugar;
+using WIDESEAWCS_Core.DB.Models;
+
+namespace WIDESEAWCS_Model.Models
+{
+    /// <summary>
+    /// 鍋囩數鑺钩闈㈢偣浣嶈〃
+    /// </summary>
+    /// <remarks>
+    /// 鐢ㄤ簬绠$悊鍋囩數鑺姄鍙栫偣鐨勫钩闈㈢偣浣嶄俊鎭��
+    /// 3琛屆�16鍒楀竷灞�锛屽叡48涓偣浣嶏紙1-48锛夛紝琛屼紭鍏堟帓鍒椼��
+    /// 绗�1琛岋細1-16锛岀2琛岋細17-32锛岀3琛岋細33-48銆�
+    /// </remarks>
+    [SugarTable(nameof(Dt_FakeBatteryPosition), "鍋囩數鑺钩闈㈢偣浣嶈〃")]
+    public class Dt_FakeBatteryPosition : BaseEntity
+    {
+        /// <summary>
+        /// 涓婚敭ID
+        /// </summary>
+        [SugarColumn(IsPrimaryKey = true, IsIdentity = true, ColumnDescription = "涓婚敭ID")]
+        public int Id { get; set; }
+
+        /// <summary>
+        /// 骞抽潰鐐逛綅绱㈠紩锛�1-48锛�
+        /// </summary>
+        /// <remarks>
+        /// 3脳16甯冨眬锛岃浼樺厛锛�1-16涓虹1琛岋紝17-32涓虹2琛岋紝33-48涓虹3琛岋級銆�
+        /// </remarks>
+        [SugarColumn(ColumnDescription = "骞抽潰鐐逛綅绱㈠紩")]
+        public int PositionIndex { get; set; }
+
+        /// <summary>
+        /// 鎵�鍦ㄨ锛�1-3锛�
+        /// </summary>
+        [SugarColumn(ColumnDescription = "鎵�鍦ㄨ")]
+        public int Row { get; set; }
+
+        /// <summary>
+        /// 鎵�鍦ㄥ垪锛�1-16锛�
+        /// </summary>
+        [SugarColumn(ColumnDescription = "鎵�鍦ㄥ垪")]
+        public int Col { get; set; }
+
+        /// <summary>
+        /// 鏄惁宸蹭娇鐢�
+        /// </summary>
+        [SugarColumn(ColumnDescription = "鏄惁宸蹭娇鐢�")]
+        public bool IsUsed { get; set; }
+    }
+}
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoRepository/FakeBatteryPositionRepository.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoRepository/FakeBatteryPositionRepository.cs
new file mode 100644
index 0000000..f66fef7
--- /dev/null
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoRepository/FakeBatteryPositionRepository.cs
@@ -0,0 +1,90 @@
+using WIDESEAWCS_Core.BaseRepository;
+using WIDESEAWCS_ITaskInfoRepository;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_TaskInfoRepository
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃粨鍌ㄥ疄鐜�
+    /// </summary>
+    public class FakeBatteryPositionRepository : RepositoryBase<Dt_FakeBatteryPosition>, IFakeBatteryPositionRepository
+    {
+        public FakeBatteryPositionRepository(IUnitOfWorkManage unitOfWorkManage) : base(unitOfWorkManage)
+        {
+        }
+
+        /// <inheritdoc/>
+        public List<int> GetNextAvailable(int count)
+        {
+            // 鎸夎鍜屽垪鍗囧簭鏌ヨ鎵�鏈夌偣浣�
+            var allPositions = Db.Queryable<Dt_FakeBatteryPosition>()
+                .OrderBy(x => x.Row)
+                .OrderBy(x => x.Col)
+                .ToList();
+
+            // 鎸夎鍒嗙粍锛屽湪姣忚鍐呮煡鎵捐繛缁彲鐢ㄧ殑鐐逛綅
+            var rows = allPositions.GroupBy(p => p.Row).OrderBy(g => g.Key);
+
+            foreach (var rowGroup in rows)
+            {
+                var rowPositions = rowGroup.OrderBy(p => p.Col).ToList();
+
+                // 鍦ㄨ繖涓�琛屽唴鏌ユ壘杩炵画鐨刢ount涓湭浣跨敤鐐逛綅
+                for (int i = 0; i <= rowPositions.Count - count; i++)
+                {
+                    var candidate = rowPositions.Skip(i).Take(count).ToList();
+
+                    // 妫�鏌ヨ繖count涓偣浣嶆槸鍚﹂兘鏄繛缁殑鍒楋紙Col杩炵画锛変笖鏈娇鐢�
+                    bool allAvailable = candidate.All(p => !p.IsUsed);
+                    bool allConsecutive = true;
+                    for (int j = 1; j < candidate.Count; j++)
+                    {
+                        if (candidate[j].Col != candidate[j - 1].Col + 1)
+                        {
+                            allConsecutive = false;
+                            break;
+                        }
+                    }
+
+                    if (allAvailable && allConsecutive)
+                    {
+                        return candidate.Select(p => p.PositionIndex).ToList();
+                    }
+                }
+            }
+
+            // 娌℃湁鎵惧埌杩炵画鐨勭┖鐐逛綅锛岃繑鍥炵┖鍒楄〃
+            return new List<int>();
+        }
+
+        /// <inheritdoc/>
+        public int ResetAll()
+        {
+            return Db.Updateable<Dt_FakeBatteryPosition>()
+                .SetColumns(x => x.IsUsed, false)
+                .ExecuteCommand();
+        }
+
+        /// <inheritdoc/>
+        public bool MarkAsUsed(List<int> positions)
+        {
+            if (positions == null || positions.Count == 0)
+                return true;
+
+            return Db.Updateable<Dt_FakeBatteryPosition>()
+                .SetColumns(x => x.IsUsed, true)
+                .Where(x => positions.Contains(x.PositionIndex))
+                .ExecuteCommand() > 0;
+        }
+
+        /// <inheritdoc/>
+        public int? GetPositionIndex(int row, int col)
+        {
+            var entity = Db.Queryable<Dt_FakeBatteryPosition>()
+                .Where(x => x.Row == row && x.Col == col)
+                .Select(x => new { x.PositionIndex })
+                .First();
+            return entity?.PositionIndex;
+        }
+    }
+}
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/FakeBatteryPositionService.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/FakeBatteryPositionService.cs
new file mode 100644
index 0000000..7016216
--- /dev/null
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/FakeBatteryPositionService.cs
@@ -0,0 +1,69 @@
+using WIDESEAWCS_Core.BaseServices;
+using WIDESEAWCS_ITaskInfoRepository;
+using WIDESEAWCS_ITaskInfoService;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_TaskInfoService
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃湇鍔″疄鐜�
+    /// </summary>
+    public class FakeBatteryPositionService : ServiceBase<Dt_FakeBatteryPosition, IFakeBatteryPositionRepository>, IFakeBatteryPositionService
+    {
+        public FakeBatteryPositionService(IFakeBatteryPositionRepository BaseDal) : base(BaseDal)
+        {
+        }
+
+        /// <inheritdoc/>
+        public List<int> GetNextAvailable(int count)
+        {
+            return BaseDal.GetNextAvailable(count);
+        }
+
+        /// <inheritdoc/>
+        public int ResetAll()
+        {
+            return BaseDal.ResetAll();
+        }
+
+        /// <inheritdoc/>
+        public bool MarkAsUsed(List<int> positions)
+        {
+            return BaseDal.MarkAsUsed(positions);
+        }
+
+        /// <inheritdoc/>
+        public int? GetPositionIndex(int row, int col)
+        {
+            return BaseDal.GetPositionIndex(row, col);
+        }
+
+        /// <inheritdoc/>
+        public bool InitializeIfEmpty()
+        {
+            var existing = BaseDal.QueryFirst(x => true);
+            if (existing != null)
+                return true;
+
+            // 鐢熸垚48涓偣浣嶏細3琛屆�16鍒楋紝琛屼紭鍏�
+            var positions = new List<Dt_FakeBatteryPosition>();
+            for (int row = 1; row <= 3; row++)
+            {
+                for (int col = 1; col <= 16; col++)
+                {
+                    int positionIndex = (row - 1) * 16 + col;
+                    positions.Add(new Dt_FakeBatteryPosition
+                    {
+                        PositionIndex = positionIndex,
+                        Row = row,
+                        Col = col,
+                        IsUsed = false,
+                        Creater = "System"
+                    });
+                }
+            }
+
+            return BaseDal.AddData(positions) > 0;
+        }
+    }
+}
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/RobotTaskService.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/RobotTaskService.cs
index 4941164..894b992 100644
--- a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/RobotTaskService.cs
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/RobotTaskService.cs
@@ -90,7 +90,7 @@
                     RobotTaskState = taskDTO.TaskStatus,
                     RobotGrade = taskDTO.Grade,
                     Creater = "WMS",
-                    RobotTaskTotalNum = 48,
+                    RobotTaskTotalNum = taskDTO.TaskQuantity,
                 };
 
                 BaseDal.AddData(task);
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotJob.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotJob.cs
index c35e485..5d3cf9e 100644
--- a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotJob.cs
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotJob.cs
@@ -104,7 +104,8 @@
             ITaskService taskService,
             ICacheService cache,
             HttpClientHelper httpClientHelper,
-            ILogger<RobotJob> logger)
+            ILogger<RobotJob> logger,
+            IFakeBatteryPositionService fakeBatteryPositionService)
         {
             // 鍒濆鍖栫姸鎬佺鐞嗗櫒锛屼紶鍏ョ紦瀛樻湇鍔�
             _stateManager = new RobotStateManager(cache, _logger);
@@ -115,7 +116,7 @@
             ISocketClientGateway socketGateway = new SocketClientGateway(tcpSocket);
 
             // 鍒濆鍖栦换鍔″鐞嗗櫒
-            _taskProcessor = new RobotTaskProcessor(socketGateway, _stateManager, robotTaskService, taskService, httpClientHelper, _logger);
+            _taskProcessor = new RobotTaskProcessor(socketGateway, _stateManager, robotTaskService, taskService, httpClientHelper, _logger, fakeBatteryPositionService);
 
             // 鍒濆鍖栧鎴风绠$悊鍣�
             _clientManager = new RobotClientManager(tcpSocket, _stateManager, _logger);
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotSocketState.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotSocketState.cs
index 60844dc..6697b01 100644
--- a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotSocketState.cs
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotSocketState.cs
@@ -173,5 +173,13 @@
         /// 褰撹揪鍒� MaxTaskTotalNum (48) 鏃讹紝涓嶅啀涓嬪彂鏂颁换鍔°��
         /// </remarks>
         public int RobotTaskTotalNum { get; set; }
+
+        /// <summary>
+        /// 鏄惁澶勪簬鍋囩數鑺ˉ鍏呮ā寮�
+        /// </summary>
+        /// <remarks>
+        /// 褰撴甯哥數鑺换鍔″畬鎴愬悗璁句负 true锛屾満鍣ㄤ汉浠庡亣鐢佃姱浣嶇疆琛ュ厖鐢佃姱鑷�48涓��
+        /// </remarks>
+        public bool IsInFakeBatteryMode { get; set; }
     }
 }
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs
index cd89884..fb5ef53 100644
--- a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs
@@ -69,6 +69,14 @@
         private readonly HttpClientHelper _httpClientHelper;
 
         /// <summary>
+        /// 鍋囩數鑺钩闈㈢偣浣嶆湇鍔�
+        /// </summary>
+        /// <remarks>
+        /// 鐢ㄤ簬绠$悊鍋囩數鑺钩闈㈢偣浣嶇殑鍒嗛厤鍜岀姸鎬併��
+        /// </remarks>
+        private readonly IFakeBatteryPositionService _fakeBatteryPositionService;
+
+        /// <summary>
         /// 鏃ュ織璁板綍鍣�
         /// </summary>
         private readonly ILogger _logger;
@@ -88,7 +96,8 @@
             IRobotTaskService robotTaskService,
             ITaskService taskService,
             HttpClientHelper httpClientHelper,
-            ILogger logger)
+            ILogger logger,
+            IFakeBatteryPositionService fakeBatteryPositionService)
         {
             _socketClientGateway = socketClientGateway;
             _stateManager = stateManager;
@@ -96,6 +105,7 @@
             _taskService = taskService;
             _httpClientHelper = httpClientHelper;
             _logger = logger;
+            _fakeBatteryPositionService = fakeBatteryPositionService;
         }
 
         /// <summary>
@@ -190,6 +200,74 @@
         }
 
         /// <summary>
+        /// 涓嬪彂鍋囩數鑺彇璐ф寚浠ゅ埌鏈哄櫒浜哄鎴风
+        /// </summary>
+        /// <remarks>
+        /// 鍙戦�佹牸寮忥細Pickbattery,5,{startPosition}-{endPosition}
+        /// 渚嬪锛歅ickbattery,5,1-3 琛ㄧず浠庡亣鐢佃姱浣嶇疆5鎶撳彇锛屽钩闈㈢偣浣�1鍒�3
+        ///
+        /// 涓嬪彂鎴愬姛鍚庯細
+        /// 1. 鏍囪鐐逛綅涓哄凡浣跨敤
+        /// 2. 鏇存柊浠诲姟鐘舵�佷负"鏈哄櫒浜烘墽琛屼腑"
+        /// 3. 瀹夊叏鏇存柊鐘舵�佸埌 Redis
+        /// </remarks>
+        /// <param name="task">瑕佷笅鍙戠殑浠诲姟瀵硅薄</param>
+        /// <param name="state">鏈哄櫒浜哄綋鍓嶇姸鎬�</param>
+        /// <param name="positions">瑕佹姄鍙栫殑骞抽潰鐐逛綅鍒楄〃</param>
+        public async Task SendSocketRobotFakeBatteryPickAsync(Dt_RobotTask task, RobotSocketState state, List<int> positions)
+        {
+            if (positions == null || positions.Count == 0)
+            {
+                _logger.LogWarning("SendSocketRobotFakeBatteryPickAsync锛氬钩闈㈢偣浣嶅垪琛ㄤ负绌猴紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                return;
+            }
+
+            // 璁$畻鐐逛綅鑼冨洿锛屾牸寮忥細1-3
+            int startPos = positions.Min();
+            int endPos = positions.Max();
+            string taskString = $"Pickbattery,5,{startPos}-{endPos}";
+
+            // 鏍囪鐐逛綅涓哄凡浣跨敤
+            _fakeBatteryPositionService.MarkAsUsed(positions);
+
+            // 閫氳繃 Socket 缃戝叧鍙戦�佹寚浠ゅ埌鏈哄櫒浜哄鎴风
+            bool result = await _socketClientGateway.SendToClientAsync(state.IPAddress, taskString);
+
+            if (result)
+            {
+                _logger.LogInformation("涓嬪彂鍋囩數鑺彇璐ф寚浠ゆ垚鍔燂紝鎸囦护: {TaskString}锛岀偣浣�: {Positions}锛岃澶�: {DeviceName}",
+                    taskString, string.Join(",", positions), state.RobotCrane?.DeviceName);
+                QuartzLogger.Info($"涓嬪彂鍋囩數鑺彇璐ф寚浠ゆ垚鍔燂紝鎸囦护: {taskString}", state.RobotCrane?.DeviceName);
+
+                // 鏇存柊浠诲姟鐘舵�佷负"鏈哄櫒浜烘墽琛屼腑"
+                task.RobotTaskState = TaskRobotStatusEnum.RobotExecuting.GetHashCode();
+
+                // 灏嗕换鍔″叧鑱斿埌鐘舵�佸璞�
+                state.CurrentTask = task;
+
+                if (_stateManager.TryUpdateStateSafely(state.IPAddress, state))
+                {
+                    await _robotTaskService.UpdateRobotTaskAsync(task);
+                }
+            }
+            else
+            {
+                _logger.LogError("涓嬪彂鍋囩數鑺彇璐ф寚浠ゅけ璐ワ紝鎸囦护: {TaskString}锛岃澶�: {DeviceName}", taskString, state.RobotCrane?.DeviceName);
+                QuartzLogger.Error($"涓嬪彂鍋囩數鑺彇璐ф寚浠ゅけ璐ワ紝鎸囦护: {taskString}", state.RobotCrane?.DeviceName);
+            }
+        }
+
+        /// <summary>
+        /// 鑾峰彇涓婲涓彲鐢ㄧ殑鍋囩數鑺钩闈㈢偣浣�
+        /// </summary>
+        /// <param name="count">闇�瑕佽幏鍙栫殑鐐逛綅鏁伴噺</param>
+        /// <returns>鍙敤鐐逛綅鍒楄〃</returns>
+        public List<int> GetNextAvailableFakeBatteryPositions(int count)
+        {
+            return _fakeBatteryPositionService.GetNextAvailable(count);
+        }
+
+        /// <summary>
         /// 澶勭悊鍏ュ簱浠诲姟鍥炰紶锛堟媶鐩�/缁勭洏/鎹㈢洏鍦烘櫙锛�
         /// </summary>
         /// <remarks>
diff --git a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/RobotWorkflowOrchestrator.cs b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/RobotWorkflowOrchestrator.cs
index f5c193d..e0211a5 100644
--- a/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/RobotWorkflowOrchestrator.cs
+++ b/Code/WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/RobotWorkflowOrchestrator.cs
@@ -237,13 +237,13 @@
                     || task.RobotTaskType == RobotTaskTypeEnum.ChangePallet.GetHashCode();
             }
 
-            // 濡傛灉鏄粍鐩樹换鍔★紙鍖呮嫭鎹㈢洏锛�
+            // 濡傛灉鏄粍鐩樹换鍔�
             if (task.RobotTaskType == RobotTaskTypeEnum.GroupPallet.GetHashCode())
             {
                 // 鐢熸垚鎵樼洏鏉$爜鍓嶇紑
                 const string prefix = "TRAY";
 
-                // 鐢熸垚涓や釜鎵樼洏鏉$爜锛堢敤浜庣粍鐩樻搷浣滐級
+                // 鐢熸垚涓や釜鎵樼洏鏉$爜锛堢敤浜庣粍鐩樻搷浣滐級锛堟祴璇曠敤锛屽悗缁鍙栫嚎浣撴潯鐮侊級
                 string trayBarcode1 = RobotBarcodeGenerator.GenerateTrayBarcode(prefix);
                 string trayBarcode2 = RobotBarcodeGenerator.GenerateTrayBarcode(prefix);
 
@@ -282,6 +282,66 @@
                     QuartzLogger.Error($"鐢熸垚鎵樼洏鏉$爜澶辫触", stateForUpdate.RobotCrane.DeviceName);
                 }
             }
+            else if (task.RobotTaskType == RobotTaskTypeEnum.ChangePallet.GetHashCode())
+            {
+                // 鎹㈢洏浠诲姟
+                // 鐩爣锛氭甯哥數鑺姄鍙栧畬鎴愬悗锛岃ˉ鍏呭亣鐢佃姱鑷�48涓�
+                const int targetTotal = 48;
+                const int fakeBatteryPickPosition = 5;  // 鍋囩數鑺姄鍙栦綅缃�
+                const int pickCountPerExecution = 4;     // 姣忔鎶撳彇鏁伴噺
+
+                int targetNormalCount = task.RobotTaskTotalNum;  // 姝e父鐢佃姱鐩爣鏁伴噺
+                int currentCompletedCount = stateForUpdate.RobotTaskTotalNum;  // 宸插畬鎴愭暟閲�
+
+                // 濡傛灉鐩爣鏁伴噺涓�48锛岀洿鎺ヤ笅鍙戞甯镐换鍔�
+                if (targetNormalCount == targetTotal)
+                {
+                    await _taskProcessor.SendSocketRobotPickAsync(task, stateForUpdate);
+                }
+                // 濡傛灉宸插畬鎴愭暟閲忓皬浜庣洰鏍囨暟閲忥紝缁х画鎶撳彇姝e父鐢佃姱
+                else if (currentCompletedCount < targetNormalCount)
+                {
+                    await _taskProcessor.SendSocketRobotPickAsync(task, stateForUpdate);
+                }
+                // 姝e父鐢佃姱宸插畬鎴愶紝杩涘叆鍋囩數鑺ˉ鍏呮ā寮�
+                else if (currentCompletedCount == targetNormalCount && !stateForUpdate.IsInFakeBatteryMode)
+                {
+                    // 棣栨杩涘叆鍋囩數鑺ā寮忥紝璁剧疆鏍囧織
+                    stateForUpdate.IsInFakeBatteryMode = true;
+                    _logger.LogInformation("HandlePutFinishedStateAsync锛氭甯哥數鑺姄鍙栧畬鎴愶紝杩涘叆鍋囩數鑺ˉ鍏呮ā寮忥紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                    QuartzLogger.Info($"姝e父鐢佃姱鎶撳彇瀹屾垚锛岃繘鍏ュ亣鐢佃姱琛ュ厖妯″紡", stateForUpdate.RobotCrane?.DeviceName);
+                }
+
+                // 濡傛灉澶勪簬鍋囩數鑺ˉ鍏呮ā寮忥紝璁$畻骞朵笅鍙戣ˉ鏁颁换鍔�
+                if (stateForUpdate.IsInFakeBatteryMode)
+                {
+                    int remaining = targetTotal - currentCompletedCount;
+                    if (remaining > 0)
+                    {
+                        // 璁$畻姣忔鎶撳彇鐨勬暟閲忥紙鏈�澶�4涓級
+                        int pickCount = Math.Min(pickCountPerExecution, remaining);
+
+                        // 鑾峰彇鍙敤鐨勫亣鐢佃姱骞抽潰鐐逛綅
+                        var positions = _taskProcessor.GetNextAvailableFakeBatteryPositions(pickCount);
+                        if (positions.Count == 0)
+                        {
+                            _logger.LogError("HandlePutFinishedStateAsync锛氭棤鍙敤鍋囩數鑺偣浣嶏紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                            QuartzLogger.Error($"鏃犲彲鐢ㄥ亣鐢佃姱鐐逛綅", stateForUpdate.RobotCrane?.DeviceName);
+                            return;
+                        }
+
+                        // 涓嬪彂鍋囩數鑺彇璐ф寚浠�
+                        await _taskProcessor.SendSocketRobotFakeBatteryPickAsync(task, stateForUpdate, positions);
+                    }
+                    else
+                    {
+                        // 鍋囩數鑺ˉ鍏呭畬鎴愶紝閲嶇疆鏍囧織
+                        stateForUpdate.IsInFakeBatteryMode = false;
+                        _logger.LogInformation("HandlePutFinishedStateAsync锛氭崲鐩樹换鍔″畬鎴愶紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                        QuartzLogger.Info($"鎹㈢洏浠诲姟瀹屾垚", stateForUpdate.RobotCrane?.DeviceName);
+                    }
+                }
+            }
             else
             {
                 // 闈炵粍鐩樹换鍔★紝鐩存帴鍙戦�佸彇璐ф寚浠�
diff --git a/Code/WMS/WIDESEA_WMSServer/WIDESEA_DTO/Task/WMSTaskDTO.cs b/Code/WMS/WIDESEA_WMSServer/WIDESEA_DTO/Task/WMSTaskDTO.cs
index 3313000..00a9a46 100644
--- a/Code/WMS/WIDESEA_WMSServer/WIDESEA_DTO/Task/WMSTaskDTO.cs
+++ b/Code/WMS/WIDESEA_WMSServer/WIDESEA_DTO/Task/WMSTaskDTO.cs
@@ -67,6 +67,11 @@
         public int Grade { get; set; }
 
         /// <summary>
+        /// 浠诲姟鏁伴噺
+        /// </summary>
+        public int TaskQuantity { get; set; }
+
+        /// <summary>
         /// 
         /// </summary>
         public int WarehouseId { get; set; }
diff --git a/Code/WMS/WIDESEA_WMSServer/WIDESEA_TaskInfoService/WCS/TaskService_Robot.cs b/Code/WMS/WIDESEA_WMSServer/WIDESEA_TaskInfoService/WCS/TaskService_Robot.cs
index 82b24b2..c897ea3 100644
--- a/Code/WMS/WIDESEA_WMSServer/WIDESEA_TaskInfoService/WCS/TaskService_Robot.cs
+++ b/Code/WMS/WIDESEA_WMSServer/WIDESEA_TaskInfoService/WCS/TaskService_Robot.cs
@@ -100,7 +100,7 @@
                     if (string.IsNullOrWhiteSpace(stockPalletCode))
                         return WebResponseContent.Instance.Error("婧愭墭鐩樺彿涓嶈兘涓虹┖");
 
-                    stockInfo = await _stockInfoService.GetStockInfoAsync(stockPalletCode);
+                    stockInfo = await _stockInfoService.Repository.QueryDataNavFirstAsync(x => x.PalletCode == stockPalletCode);
                     if (stockInfo == null)
                         return WebResponseContent.Instance.Error($"鎵樼洏[{stockPalletCode}]搴撳瓨涓嶅瓨鍦�");
 
@@ -134,6 +134,7 @@
                     return WebResponseContent.Instance.Error($"鏈烘鎵媨taskName}浠诲姟鍒涘缓澶辫触");
 
                 var wmstaskDto = _mapper.Map<WMSTaskDTO>(task) ?? new WMSTaskDTO();
+                wmstaskDto.TaskQuantity = stock.Details?.Sum(d => d.Quantity) ?? 0;
                 return WebResponseContent.Instance.OK($"鏈烘鎵媨taskName}浠诲姟鍒涘缓鎴愬姛", wmstaskDto);
             }
             catch (Exception ex)
diff --git a/Code/docs/superpowers/plans/2026-04-15-change-pallet-fake-battery.md b/Code/docs/superpowers/plans/2026-04-15-change-pallet-fake-battery.md
new file mode 100644
index 0000000..3e5daa5
--- /dev/null
+++ b/Code/docs/superpowers/plans/2026-04-15-change-pallet-fake-battery.md
@@ -0,0 +1,640 @@
+# 鎹㈢洏浠诲姟鍋囩數鑺ˉ鍏呴�昏緫 Implementation Plan
+
+> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking.
+
+**Goal:** 鍦� `HandlePutFinishedStateAsync` 涓疄鐜版崲鐩樹换鍔$殑鐗规畩閫昏緫锛氬綋 `task.RobotTaskTotalNum != 48` 鏃讹紝姝e父鐢佃姱浠诲姟瀹屾垚鍚庨渶琛ュ厖鍋囩數鑺嚦48涓��
+
+**Architecture:** 鎹㈢洏浠诲姟鍒嗕袱闃舵鎵ц锛�(1) 姝e父鐢佃姱鎶撳彇闃舵锛�(2) 鍋囩數鑺ˉ鍏呴樁娈点�傚亣鐢佃姱浠庝綅缃�5鎶撳彇锛屾寚浠ゆ牸寮� `Pickbattery,5,1-3`銆傛柊澧� `Dt_FakeBatteryPosition` 琛ㄧ鐞�3脳16骞抽潰鐐逛綅鐨勫崰鐢ㄧ姸鎬併��
+
+**Tech Stack:** C# / .NET 6, SqlSugar ORM, Redis缂撳瓨
+
+---
+
+## File Structure
+
+```
+WCS/WIDESEAWCS_Server/WIDESEAWCS_Model/Models/TaskInfo/
+  + Dt_FakeBatteryPosition.cs          # 鍋囩數鑺钩闈㈢偣浣嶈〃瀹炰綋
+
+WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoRepository/
+  + IFakeBatteryPositionRepository.cs  # 鍋囩數鑺綅缃粨鍌ㄦ帴鍙�
+
+WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoRepository/
+  + FakeBatteryPositionRepository.cs   # 鍋囩數鑺綅缃粨鍌ㄥ疄鐜�
+
+WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoService/
+  + IFakeBatteryPositionService.cs     # 鍋囩數鑺綅缃湇鍔℃帴鍙�
+
+WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/
+  + FakeBatteryPositionService.cs      # 鍋囩數鑺綅缃湇鍔″疄鐜�
+
+WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/
+  = RobotSocketState.cs                # +IsInFakeBatteryMode 鏍囧織
+  = RobotTaskProcessor.cs              # +SendSocketRobotFakeBatteryPickAsync 鏂规硶
+
+WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/
+  = RobotWorkflowOrchestrator.cs      # 瀹炵幇 ChangePallet 鍒嗘敮瀹屾暣閫昏緫
+```
+
+---
+
+## Task 1: 鍒涘缓鍋囩數鑺钩闈㈢偣浣嶈〃瀹炰綋
+
+**Files:**
+- Create: `WCS/WIDESEAWCS_Server/WIDESEAWCS_Model/Models/TaskInfo/Dt_FakeBatteryPosition.cs`
+
+- [ ] **Step 1: 鍒涘缓 Dt_FakeBatteryPosition.cs**
+
+```csharp
+using SqlSugar;
+using WIDESEAWCS_Core.DB.Models;
+
+namespace WIDESEAWCS_Model.Models
+{
+    /// <summary>
+    /// 鍋囩數鑺钩闈㈢偣浣嶈〃
+    /// </summary>
+    /// <remarks>
+    /// 鐢ㄤ簬绠$悊鍋囩數鑺姄鍙栫偣鐨勫钩闈㈢偣浣嶄俊鎭��
+    /// 3琛屆�16鍒楀竷灞�锛屽叡48涓偣浣嶏紙1-48锛夛紝琛屼紭鍏堟帓鍒椼��
+    /// 绗�1琛岋細1-16锛岀2琛岋細17-32锛岀3琛岋細33-48銆�
+    /// </remarks>
+    [SugarTable(nameof(Dt_FakeBatteryPosition), "鍋囩數鑺钩闈㈢偣浣嶈〃")]
+    public class Dt_FakeBatteryPosition : BaseEntity
+    {
+        /// <summary>
+        /// 涓婚敭ID
+        /// </summary>
+        [SugarColumn(IsPrimaryKey = true, IsIdentity = true, ColumnDescription = "涓婚敭ID")]
+        public int Id { get; set; }
+
+        /// <summary>
+        /// 骞抽潰鐐逛綅绱㈠紩锛�1-48锛�
+        /// </summary>
+        /// <remarks>
+        /// 3脳16甯冨眬锛岃浼樺厛锛�1-16涓虹1琛岋紝17-32涓虹2琛岋紝33-48涓虹3琛岋級銆�
+        /// </remarks>
+        [SugarColumn(ColumnDescription = "骞抽潰鐐逛綅绱㈠紩")]
+        public int PositionIndex { get; set; }
+
+        /// <summary>
+        /// 鎵�鍦ㄨ锛�1-3锛�
+        /// </summary>
+        [SugarColumn(ColumnDescription = "鎵�鍦ㄨ")]
+        public int Row { get; set; }
+
+        /// <summary>
+        /// 鎵�鍦ㄥ垪锛�1-16锛�
+        /// </summary>
+        [SugarColumn(ColumnDescription = "鎵�鍦ㄥ垪")]
+        public int Col { get; set; }
+
+        /// <summary>
+        /// 鏄惁宸蹭娇鐢�
+        /// </summary>
+        [SugarColumn(ColumnDescription = "鏄惁宸蹭娇鐢�")]
+        public bool IsUsed { get; set; }
+    }
+}
+```
+
+- [ ] **Step 2: Commit**
+
+```bash
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_Model/Models/TaskInfo/Dt_FakeBatteryPosition.cs
+git commit -m "feat(Robot): 娣诲姞鍋囩數鑺钩闈㈢偣浣嶈〃瀹炰綋 Dt_FakeBatteryPosition"
+```
+
+---
+
+## Task 2: 鍒涘缓鍋囩數鑺綅缃粨鍌ㄥ眰
+
+**Files:**
+- Create: `WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoRepository/IFakeBatteryPositionRepository.cs`
+- Create: `WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoRepository/FakeBatteryPositionRepository.cs`
+
+- [ ] **Step 1: 鍒涘缓 IFakeBatteryPositionRepository.cs**
+
+```csharp
+using WIDESEAWCS_Core.BaseRepository;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_ITaskInfoRepository
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃粨鍌ㄦ帴鍙�
+    /// </summary>
+    public interface IFakeBatteryPositionRepository : IRepository<Dt_FakeBatteryPosition>
+    {
+        /// <summary>
+        /// 鑾峰彇涓婲涓彲鐢ㄧ殑鍋囩數鑺钩闈㈢偣浣�
+        /// </summary>
+        /// <param name="count">闇�瑕佽幏鍙栫殑鐐逛綅鏁伴噺</param>
+        /// <returns>鍙敤鐐逛綅鍒楄〃锛屾寜PositionIndex鍗囧簭</returns>
+        List<int> GetNextAvailable(int count);
+
+        /// <summary>
+        /// 閲嶇疆鎵�鏈夌偣浣嶄负鏈娇鐢�
+        /// </summary>
+        /// <returns>褰卞搷鐨勮鏁�</returns>
+        int ResetAll();
+
+        /// <summary>
+        /// 鏍囪鎸囧畾鐐逛綅涓哄凡浣跨敤
+        /// </summary>
+        /// <param name="positions">鐐逛綅绱㈠紩鍒楄〃</param>
+        /// <returns>鏄惁鎴愬姛</returns>
+        bool MarkAsUsed(List<int> positions);
+
+        /// <summary>
+        /// 鏍规嵁琛屽拰鍒楄幏鍙栫偣浣嶇储寮�
+        /// </summary>
+        /// <param name="row">琛岋紙1-3锛�</param>
+        /// <param name="col">鍒楋紙1-16锛�</param>
+        /// <returns>鐐逛綅绱㈠紩锛�1-48锛夛紝鎵句笉鍒拌繑鍥瀗ull</returns>
+        int? GetPositionIndex(int row, int col);
+    }
+}
+```
+
+- [ ] **Step 2: 鍒涘缓 FakeBatteryPositionRepository.cs**
+
+```csharp
+using WIDESEAWCS_Core.BaseRepository;
+using WIDESEAWCS_ITaskInfoRepository;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_TaskInfoRepository
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃粨鍌ㄥ疄鐜�
+    /// </summary>
+    public class FakeBatteryPositionRepository : RepositoryBase<Dt_FakeBatteryPosition>, IFakeBatteryPositionRepository
+    {
+        public FakeBatteryPositionRepository(IUnitOfWorkManage unitOfWorkManage) : base(unitOfWorkManage)
+        {
+        }
+
+        /// <inheritdoc/>
+        public List<int> GetNextAvailable(int count)
+        {
+            return Db.Queryable<Dt_FakeBatteryPosition>()
+                .Where(x => !x.IsUsed)
+                .OrderBy(x => x.PositionIndex)
+                .Take(count)
+                .Select(x => x.PositionIndex)
+                .ToList();
+        }
+
+        /// <inheritdoc/>
+        public int ResetAll()
+        {
+            return Db.Updateable<Dt_FakeBatteryPosition>()
+                .SetColumns(x => x.IsUsed, false)
+                .ExecuteCommand();
+        }
+
+        /// <inheritdoc/>
+        public bool MarkAsUsed(List<int> positions)
+        {
+            if (positions == null || positions.Count == 0)
+                return true;
+
+            return Db.Updateable<Dt_FakeBatteryPosition>()
+                .SetColumns(x => x.IsUsed, true)
+                .Where(x => positions.Contains(x.PositionIndex))
+                .ExecuteCommand() > 0;
+        }
+
+        /// <inheritdoc/>
+        public int? GetPositionIndex(int row, int col)
+        {
+            return Db.Queryable<Dt_FakeBatteryPosition>()
+                .Where(x => x.Row == row && x.Col == col)
+                .Select(x => x.PositionIndex)
+                .FirstOrDefault();
+        }
+    }
+}
+```
+
+- [ ] **Step 3: Commit**
+
+```bash
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoRepository/IFakeBatteryPositionRepository.cs
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoRepository/FakeBatteryPositionRepository.cs
+git commit -m "feat(Robot): 娣诲姞鍋囩數鑺綅缃粨鍌ㄥ眰"
+```
+
+---
+
+## Task 3: 鍒涘缓鍋囩數鑺綅缃湇鍔″眰
+
+**Files:**
+- Create: `WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoService/IFakeBatteryPositionService.cs`
+- Create: `WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/FakeBatteryPositionService.cs`
+
+- [ ] **Step 1: 鍒涘缓 IFakeBatteryPositionService.cs**
+
+```csharp
+using WIDESEAWCS_Core.BaseServices;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_ITaskInfoService
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃湇鍔℃帴鍙�
+    /// </summary>
+    public interface IFakeBatteryPositionService : IService<Dt_FakeBatteryPosition>
+    {
+        /// <summary>
+        /// 鑾峰彇涓婲涓彲鐢ㄧ殑鍋囩數鑺钩闈㈢偣浣�
+        /// </summary>
+        /// <param name="count">闇�瑕佽幏鍙栫殑鐐逛綅鏁伴噺</param>
+        /// <returns>鍙敤鐐逛綅鍒楄〃锛屾寜PositionIndex鍗囧簭</returns>
+        List<int> GetNextAvailable(int count);
+
+        /// <summary>
+        /// 閲嶇疆鎵�鏈夌偣浣嶄负鏈娇鐢�
+        /// </summary>
+        /// <returns>褰卞搷鐨勮鏁�</returns>
+        int ResetAll();
+
+        /// <summary>
+        /// 鏍囪鎸囧畾鐐逛綅涓哄凡浣跨敤
+        /// </summary>
+        /// <param name="positions">鐐逛綅绱㈠紩鍒楄〃</param>
+        /// <returns>鏄惁鎴愬姛</returns>
+        bool MarkAsUsed(List<int> positions);
+
+        /// <summary>
+        /// 鏍规嵁琛屽拰鍒楄幏鍙栫偣浣嶇储寮�
+        /// </summary>
+        /// <param name="row">琛岋紙1-3锛�</param>
+        /// <param name="col">鍒楋紙1-16锛�</param>
+        /// <returns>鐐逛綅绱㈠紩锛�1-48锛夛紝鎵句笉鍒拌繑鍥瀗ull</returns>
+        int? GetPositionIndex(int row, int col);
+
+        /// <summary>
+        /// 鍒濆鍖栧亣鐢佃姱鐐逛綅琛紙48涓偣浣嶏級
+        /// </summary>
+        /// <remarks>
+        /// 浠呭綋琛ㄤ负绌烘椂鎻掑叆1-48鐨勫垵濮嬫暟鎹��
+        /// 3琛屆�16鍒楋紝琛屼紭鍏堟帓鍒椼��
+        /// </remarks>
+        /// <returns>鏄惁鎴愬姛</returns>
+        bool InitializeIfEmpty();
+    }
+}
+```
+
+- [ ] **Step 2: 鍒涘缓 FakeBatteryPositionService.cs**
+
+```csharp
+using WIDESEAWCS_Core.BaseServices;
+using WIDESEAWCS_ITaskInfoRepository;
+using WIDESEAWCS_Model.Models;
+
+namespace WIDESEAWCS_TaskInfoService
+{
+    /// <summary>
+    /// 鍋囩數鑺綅缃湇鍔″疄鐜�
+    /// </summary>
+    public class FakeBatteryPositionService : ServiceBase<Dt_FakeBatteryPosition, IFakeBatteryPositionRepository>, IFakeBatteryPositionService
+    {
+        public FakeBatteryPositionService(IFakeBatteryPositionRepository BaseDal) : base(BaseDal)
+        {
+        }
+
+        /// <inheritdoc/>
+        public List<int> GetNextAvailable(int count)
+        {
+            return BaseDal.GetNextAvailable(count);
+        }
+
+        /// <inheritdoc/>
+        public int ResetAll()
+        {
+            return BaseDal.ResetAll();
+        }
+
+        /// <inheritdoc/>
+        public bool MarkAsUsed(List<int> positions)
+        {
+            return BaseDal.MarkAsUsed(positions);
+        }
+
+        /// <inheritdoc/>
+        public int? GetPositionIndex(int row, int col)
+        {
+            return BaseDal.GetPositionIndex(row, col);
+        }
+
+        /// <inheritdoc/>
+        public bool InitializeIfEmpty()
+        {
+            var existing = BaseDal.QueryFirst(x => true);
+            if (existing != null)
+                return true;
+
+            // 鐢熸垚48涓偣浣嶏細3琛屆�16鍒楋紝琛屼紭鍏�
+            var positions = new List<Dt_FakeBatteryPosition>();
+            for (int row = 1; row <= 3; row++)
+            {
+                for (int col = 1; col <= 16; col++)
+                {
+                    int positionIndex = (row - 1) * 16 + col;
+                    positions.Add(new Dt_FakeBatteryPosition
+                    {
+                        PositionIndex = positionIndex,
+                        Row = row,
+                        Col = col,
+                        IsUsed = false,
+                        Creater = "System"
+                    });
+                }
+            }
+
+            return BaseDal.AddData(positions) > 0;
+        }
+    }
+}
+```
+
+- [ ] **Step 3: Commit**
+
+```bash
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_ITaskInfoService/IFakeBatteryPositionService.cs
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_TaskInfoService/FakeBatteryPositionService.cs
+git commit -m "feat(Robot): 娣诲姞鍋囩數鑺綅缃湇鍔″眰"
+```
+
+---
+
+## Task 4: 淇敼 RobotSocketState 娣诲姞 IsInFakeBatteryMode 鏍囧織
+
+**Files:**
+- Modify: `WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotSocketState.cs:175` (鍦� `RobotTaskTotalNum` 灞炴�у悗娣诲姞)
+
+- [ ] **Step 1: 娣诲姞 IsInFakeBatteryMode 灞炴��**
+
+鍦� `RobotSocketState.cs` 鐨� `RobotTaskTotalNum` 灞炴�у悗娣诲姞锛�
+
+```csharp
+        /// <summary>
+        /// 鏈哄櫒浜哄凡澶勭悊鐨勪换鍔℃�绘暟
+        /// </summary>
+        public int RobotTaskTotalNum { get; set; }
+
+        /// <summary>
+        /// 鏄惁澶勪簬鍋囩數鑺ˉ鍏呮ā寮�
+        /// </summary>
+        /// <remarks>
+        /// 褰撴甯哥數鑺换鍔″畬鎴愬悗璁句负 true锛屾満鍣ㄤ汉浠庡亣鐢佃姱浣嶇疆琛ュ厖鐢佃姱鑷�48涓��
+        /// </remarks>
+        public bool IsInFakeBatteryMode { get; set; }
+```
+
+- [ ] **Step 2: Commit**
+
+```bash
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotSocketState.cs
+git commit -m "feat(Robot): RobotSocketState 娣诲姞 IsInFakeBatteryMode 鏍囧織"
+```
+
+---
+
+## Task 5: 淇敼 RobotTaskProcessor 娣诲姞鍋囩數鑺彇璐ф寚浠ゆ柟娉�
+
+**Files:**
+- Modify: `WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs` (鍦� `SendSocketRobotPickAsync` 鍚庢坊鍔犳柊鏂规硶)
+
+- [ ] **Step 1: 娣诲姞 IFakeBatteryPositionService 渚濊禆**
+
+鍦� `RobotTaskProcessor` 鏋勯�犲嚱鏁颁腑娣诲姞锛�
+
+```csharp
+private readonly IFakeBatteryPositionService _fakeBatteryPositionService;
+
+// 鏋勯�犲嚱鏁板弬鏁颁腑娣诲姞锛�
+, IFakeBatteryPositionService fakeBatteryPositionService
+
+// 鏋勯�犲嚱鏁拌祴鍊硷細
+_fakeBatteryPositionService = fakeBatteryPositionService;
+```
+
+- [ ] **Step 2: 娣诲姞 SendSocketRobotFakeBatteryPickAsync 鏂规硶**
+
+鍦� `SendSocketRobotPickAsync` 鏂规硶鍚庢坊鍔狅細
+
+```csharp
+        /// <summary>
+        /// 涓嬪彂鍋囩數鑺彇璐ф寚浠ゅ埌鏈哄櫒浜哄鎴风
+        /// </summary>
+        /// <remarks>
+        /// 鍙戦�佹牸寮忥細Pickbattery,5,{startPosition}-{endPosition}
+        /// 渚嬪锛歅ickbattery,5,1-3 琛ㄧず浠庡亣鐢佃姱浣嶇疆5鎶撳彇锛屽钩闈㈢偣浣�1鍒�3
+        ///
+        /// 涓嬪彂鎴愬姛鍚庯細
+        /// 1. 鏍囪鐐逛綅涓哄凡浣跨敤
+        /// 2. 鏇存柊浠诲姟鐘舵�佷负"鏈哄櫒浜烘墽琛屼腑"
+        /// 3. 瀹夊叏鏇存柊鐘舵�佸埌 Redis
+        /// </remarks>
+        /// <param name="task">瑕佷笅鍙戠殑浠诲姟瀵硅薄</param>
+        /// <param name="state">鏈哄櫒浜哄綋鍓嶇姸鎬�</param>
+        /// <param name="positions">瑕佹姄鍙栫殑骞抽潰鐐逛綅鍒楄〃</param>
+        public async Task SendSocketRobotFakeBatteryPickAsync(Dt_RobotTask task, RobotSocketState state, List<int> positions)
+        {
+            if (positions == null || positions.Count == 0)
+            {
+                _logger.LogWarning("SendSocketRobotFakeBatteryPickAsync锛氬钩闈㈢偣浣嶅垪琛ㄤ负绌猴紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                return;
+            }
+
+            // 璁$畻鐐逛綅鑼冨洿锛屾牸寮忥細1-3
+            int startPos = positions.Min();
+            int endPos = positions.Max();
+            string taskString = $"Pickbattery,5,{startPos}-{endPos}";
+
+            // 鏍囪鐐逛綅涓哄凡浣跨敤
+            _fakeBatteryPositionService.MarkAsUsed(positions);
+
+            // 閫氳繃 Socket 缃戝叧鍙戦�佹寚浠ゅ埌鏈哄櫒浜哄鎴风
+            bool result = await _socketClientGateway.SendToClientAsync(state.IPAddress, taskString);
+
+            if (result)
+            {
+                _logger.LogInformation("涓嬪彂鍋囩數鑺彇璐ф寚浠ゆ垚鍔燂紝鎸囦护: {TaskString}锛岀偣浣�: {Positions}锛岃澶�: {DeviceName}",
+                    taskString, string.Join(",", positions), state.RobotCrane?.DeviceName);
+                QuartzLogger.Info($"涓嬪彂鍋囩數鑺彇璐ф寚浠ゆ垚鍔燂紝鎸囦护: {taskString}", state.RobotCrane?.DeviceName);
+
+                // 鏇存柊浠诲姟鐘舵�佷负"鏈哄櫒浜烘墽琛屼腑"
+                task.RobotTaskState = TaskRobotStatusEnum.RobotExecuting.GetHashCode();
+
+                // 灏嗕换鍔″叧鑱斿埌鐘舵�佸璞�
+                state.CurrentTask = task;
+
+                if (_stateManager.TryUpdateStateSafely(state.IPAddress, state))
+                {
+                    await _robotTaskService.UpdateRobotTaskAsync(task);
+                }
+            }
+            else
+            {
+                _logger.LogError("涓嬪彂鍋囩數鑺彇璐ф寚浠ゅけ璐ワ紝鎸囦护: {TaskString}锛岃澶�: {DeviceName}", taskString, state.RobotCrane?.DeviceName);
+                QuartzLogger.Error($"涓嬪彂鍋囩數鑺彇璐ф寚浠ゅけ璐ワ紝鎸囦护: {taskString}", state.RobotCrane?.DeviceName);
+            }
+        }
+```
+
+- [ ] **Step 3: Commit**
+
+```bash
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs
+git commit -m "feat(Robot): RobotTaskProcessor 娣诲姞鍋囩數鑺彇璐ф寚浠ゆ柟娉�"
+```
+
+---
+
+## Task 6: 瀹炵幇 HandlePutFinishedStateAsync 涓殑 ChangePallet 瀹屾暣閫昏緫
+
+**Files:**
+- Modify: `WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/RobotWorkflowOrchestrator.cs:285-300`
+
+- [ ] **Step 1: 瀹炵幇 ChangePallet 鍒嗘敮閫昏緫**
+
+灏嗙幇鏈夌殑鍗犱綅浠g爜鏇挎崲涓猴細
+
+```csharp
+            else if (task.RobotTaskType == RobotTaskTypeEnum.ChangePallet.GetHashCode())
+            {
+                // 鎹㈢洏浠诲姟
+                // 鐩爣锛氭甯哥數鑺姄鍙栧畬鎴愬悗锛岃ˉ鍏呭亣鐢佃姱鑷�48涓�
+                const int targetTotal = 48;
+                const int fakeBatteryPickPosition = 5;  // 鍋囩數鑺姄鍙栦綅缃�
+                const int pickCountPerExecution = 4;     // 姣忔鎶撳彇鏁伴噺
+
+                int targetNormalCount = task.RobotTaskTotalNum;  // 姝e父鐢佃姱鐩爣鏁伴噺
+                int currentCompletedCount = stateForUpdate.RobotTaskTotalNum;  // 宸插畬鎴愭暟閲�
+
+                // 濡傛灉鐩爣鏁伴噺涓�48锛岀洿鎺ヤ笅鍙戞甯镐换鍔�
+                if (targetNormalCount == targetTotal)
+                {
+                    await _taskProcessor.SendSocketRobotPickAsync(task, stateForUpdate);
+                }
+                // 濡傛灉宸插畬鎴愭暟閲忓皬浜庣洰鏍囨暟閲忥紝缁х画鎶撳彇姝e父鐢佃姱
+                else if (currentCompletedCount < targetNormalCount)
+                {
+                    await _taskProcessor.SendSocketRobotPickAsync(task, stateForUpdate);
+                }
+                // 姝e父鐢佃姱宸插畬鎴愶紝杩涘叆鍋囩數鑺ˉ鍏呮ā寮�
+                else if (currentCompletedCount == targetNormalCount && !stateForUpdate.IsInFakeBatteryMode)
+                {
+                    // 棣栨杩涘叆鍋囩數鑺ā寮忥紝璁剧疆鏍囧織
+                    stateForUpdate.IsInFakeBatteryMode = true;
+                    _logger.LogInformation("HandlePutFinishedStateAsync锛氭甯哥數鑺姄鍙栧畬鎴愶紝杩涘叆鍋囩數鑺ˉ鍏呮ā寮忥紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                    QuartzLogger.Info($"姝e父鐢佃姱鎶撳彇瀹屾垚锛岃繘鍏ュ亣鐢佃姱琛ュ厖妯″紡", stateForUpdate.RobotCrane?.DeviceName);
+                }
+
+                // 濡傛灉澶勪簬鍋囩數鑺ˉ鍏呮ā寮忥紝璁$畻骞朵笅鍙戣ˉ鏁颁换鍔�
+                if (stateForUpdate.IsInFakeBatteryMode)
+                {
+                    int remaining = targetTotal - currentCompletedCount;
+                    if (remaining > 0)
+                    {
+                        // 璁$畻姣忔鎶撳彇鐨勬暟閲忥紙鏈�澶�4涓級
+                        int pickCount = Math.Min(pickCountPerExecution, remaining);
+
+                        // 鑾峰彇鍙敤鐨勫亣鐢佃姱骞抽潰鐐逛綅
+                        var positions = _taskProcessor.GetNextAvailableFakeBatteryPositions(pickCount);
+                        if (positions.Count == 0)
+                        {
+                            _logger.LogError("HandlePutFinishedStateAsync锛氭棤鍙敤鍋囩數鑺偣浣嶏紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                            QuartzLogger.Error($"鏃犲彲鐢ㄥ亣鐢佃姱鐐逛綅", stateForUpdate.RobotCrane?.DeviceName);
+                            return;
+                        }
+
+                        // 涓嬪彂鍋囩數鑺彇璐ф寚浠�
+                        await _taskProcessor.SendSocketRobotFakeBatteryPickAsync(task, stateForUpdate, positions);
+                    }
+                    else
+                    {
+                        // 鍋囩數鑺ˉ鍏呭畬鎴愶紝閲嶇疆鏍囧織
+                        stateForUpdate.IsInFakeBatteryMode = false;
+                        _logger.LogInformation("HandlePutFinishedStateAsync锛氭崲鐩樹换鍔″畬鎴愶紝浠诲姟鍙�: {TaskNum}", task.RobotTaskNum);
+                        QuartzLogger.Info($"鎹㈢洏浠诲姟瀹屾垚", stateForUpdate.RobotCrane?.DeviceName);
+                    }
+                }
+            }
+```
+
+- [ ] **Step 2: 鍦� RobotTaskProcessor 涓坊鍔� GetNextAvailableFakeBatteryPositions 杈呭姪鏂规硶**
+
+鍦� `RobotTaskProcessor` 涓坊鍔狅細
+
+```csharp
+        /// <summary>
+        /// 鑾峰彇涓婲涓彲鐢ㄧ殑鍋囩數鑺钩闈㈢偣浣�
+        /// </summary>
+        /// <param name="count">闇�瑕佽幏鍙栫殑鐐逛綅鏁伴噺</param>
+        /// <returns>鍙敤鐐逛綅鍒楄〃</returns>
+        public List<int> GetNextAvailableFakeBatteryPositions(int count)
+        {
+            return _fakeBatteryPositionService.GetNextAvailable(count);
+        }
+```
+
+- [ ] **Step 3: Commit**
+
+```bash
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/Workflow/RobotWorkflowOrchestrator.cs
+git add WCS/WIDESEAWCS_Server/WIDESEAWCS_Tasks/RobotJob/RobotTaskProcessor.cs
+git commit -m "feat(Robot): 瀹炵幇鎹㈢洏浠诲姟鍋囩數鑺ˉ鍏呴�昏緫"
+```
+
+---
+
+## Task 7: 楠岃瘉鏋勫缓
+
+- [ ] **Step 1: 杩愯 dotnet build**
+
+```bash
+dotnet build WCS/WIDESEAWCS_Server/WIDESEAWCS_Server.sln
+```
+
+- [ ] **Step 2: 妫�鏌ユ槸鍚︽湁缂栬瘧閿欒**
+
+---
+
+## 闄勫綍锛氭暟鎹簱鍒濆鍖朣QL
+
+```sql
+-- 鍒濆鍖栧亣鐢佃姱骞抽潰鐐逛綅琛紙48涓偣浣嶏細3琛屆�16鍒楋紝琛屼紭鍏堬級
+-- 绗�1琛岋細1-16锛岀2琛岋細17-32锛岀3琛岋細33-48
+IF NOT EXISTS (SELECT 1 FROM Dt_FakeBatteryPosition)
+BEGIN
+    INSERT INTO Dt_FakeBatteryPosition (PositionIndex, Row, Col, IsUsed, Creater, CreateDate)
+    SELECT
+        ((row - 1) * 16 + col) AS PositionIndex,
+        row AS Row,
+        col AS Col,
+        0 AS IsUsed,
+        'System' AS Creater,
+        GETDATE() AS CreateDate
+    FROM (SELECT 1 AS row UNION SELECT 2 UNION SELECT 3) AS rows
+    CROSS JOIN (SELECT 1 AS col UNION SELECT 2 UNION SELECT 3 UNION SELECT 4 UNION SELECT 5 UNION SELECT 6
+                UNION SELECT 7 UNION SELECT 8 UNION SELECT 9 UNION SELECT 10 UNION SELECT 11 UNION SELECT 12
+                UNION SELECT 13 UNION SELECT 14 UNION SELECT 15 UNION SELECT 16) AS cols
+    ORDER BY row, col;
+END
+```
+
+---
+
+**Plan complete and saved to `docs/superpowers/plans/2026-04-15-change-pallet-fake-battery.md`. Two execution options:**
+
+**1. Subagent-Driven (recommended)** - I dispatch a fresh subagent per task, review between tasks, fast iteration
+
+**2. Inline Execution** - Execute tasks in this session using executing-plans, batch execution with checkpoints
+
+**Which approach?**

--
Gitblit v1.9.3