From f1a64ab92120ffc0f1b1cf2c4848528a0d6b5d18 Mon Sep 17 00:00:00 2001
From: fy36 <1046342473@qq.com>
Date: 星期一, 28 七月 2025 18:42:41 +0800
Subject: [PATCH] 一系列脚本更新

---
 lua_code/Lua/GK-API-05-InboundSync.lua           |  525 +++++++++
 lua_code/Lua/GK-API-09-Count_Pan_Sync.lua        |  297 +++++
 lua_code/Lua/GK-API-01-SKU_Sync.lua              |  790 +++++---------
 lua_code/Lua/GK-API-03-SKU-Batch_Sync.lua        |  271 +++++
 lua_code/Lua/GK-API-06-Outbound_Sync.lua         |  187 +++
 lua_code/Lua/GK-API-04-Receipt_Sync.lua          |  292 +++++
 lua_code/Lua/GK-API-08-Outbound_Priority_Chg.lua |  334 ++++++
 lua_code/Lua/GK-API-11-StockQuery.lua            |  251 ++++
 lua_code/Lua/GK-API-07-Order_Cancel.lua          |   10 
 lua_code/Lua/GK-API-02-Storer_Sync.lua           |  247 ++++
 10 files changed, 2,684 insertions(+), 520 deletions(-)

diff --git a/lua_code/Lua/GK-API-01-SKU_Sync.lua b/lua_code/Lua/GK-API-01-SKU_Sync.lua
index 65e2d0f..a8c19d6 100644
--- a/lua_code/Lua/GK-API-01-SKU_Sync.lua
+++ b/lua_code/Lua/GK-API-01-SKU_Sync.lua
@@ -1,7 +1,7 @@
 --[[ 
     缂栫爜: GK-API-001
     鍚嶇О: 鐩樼偣璁″垝鍚屾
-    浣滆�: HAN
+    浣滆�: Yuanfeng
     鏃ユ湡: 2025-1-29
 
     鍏ュ彛鍑芥暟锛�SKU_Sync
@@ -19,326 +19,170 @@
        V2.3 绉婚櫎error瀛楁锛屽悎骞跺埌message涓�        V2.4 鏂板SKU_GRID_PARM瀛楁
        V2.5 2025-07-01 SKU_GRID鏂欑鏍煎弬鏁颁紭鍖栦负鏍规嵁cell_type 鑷姩鍚屾
-
-<?xml version="1.0" encoding="UTF-8"?>
-<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
-    <soap:Header xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
-</soap:Header>
-    <soapenv:Body>
-        <v1:inCommodityReq xmlns:v1="http://www.gkht.com/Information/INV/Ebs/Schemas/InCommodity/V1.0">
-            <v1:COMMODITY_Input>
-                <v1:RESTHeader>
-                    <v1:Responsibility/>
-                    <v1:RespApplication/>
-                    <v1:SecurityGroup/>
-                    <v1:NLSLanguage>SIMPLIFIED CHINESE</v1:NLSLanguage>
-                    <v1:Org_Id>0</v1:Org_Id>
-                </v1:RESTHeader>
-                <v1:InputParameters>
-                    <v1:COMMODITY_TB>
-                        <!--1 or more repetitions:-->
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM125262</v1:skuId>
-                            <v1:storerId>TGKHMB</v1:storerId>
-                            <v1:skuName>Exceed ABT寰瓟娑傚眰楂嬭嚰鏉�2mm</v1:skuName>
-                            <v1:skuDec>Exceed ABT寰瓟娑傚眰楂嬭嚰鏉�2mm</v1:skuDec>
-                            <v1:spec>Acetabular Shell PC 52 x 62mm</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>501927908583</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM141234</v1:skuId>
-                            <v1:storerId>CGKHTY</v1:storerId>
-                            <v1:skuName>Biomet 鍥哄畾鍗佸瓧鍨嬫焺鑳骞冲彴鍋囦綋 75mm</v1:skuName>
-                            <v1:skuDec>Biomet 鍥哄畾鍗佸瓧鍨嬫焺鑳骞冲彴鍋囦綋 75mm</v1:skuDec>
-                            <v1:spec>75mm</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>.5</v1:length>
-                            <v1:width>.5</v1:width>
-                            <v1:height>.5</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>1</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM141234</v1:skuId>
-                            <v1:storerId>GGKHN1</v1:storerId>
-                            <v1:skuName>Biomet 鍥哄畾鍗佸瓧鍨嬫焺鑳骞冲彴鍋囦綋 75mm</v1:skuName>
-                            <v1:skuDec>-</v1:skuDec>
-                            <v1:spec>75mm</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType>C</v1:abcType>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions/>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>088030400832</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM141234</v1:skuId>
-                            <v1:storerId>TGKHMB</v1:storerId>
-                            <v1:skuName>Biomet 鍥哄畾鍗佸瓧鍨嬫焺鑳骞冲彴鍋囦綋 75mm</v1:skuName>
-                            <v1:skuDec>Biomet 鍥哄畾鍗佸瓧鍨嬫焺鑳骞冲彴鍋囦綋 75mm</v1:skuDec>
-                            <v1:spec>75mm</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>088030400832</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM141234</v1:skuId>
-                            <v1:storerId>TGKRTH</v1:storerId>
-                            <v1:skuName>Biomet 鍥哄畾鍗佸瓧鍨嬫焺鑳骞冲彴鍋囦綋 75mm</v1:skuName>
-                            <v1:skuDec>-</v1:skuDec>
-                            <v1:spec>75mm</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>088030400832</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM141234</v1:skuId>
-                            <v1:storerId>TNMGGK</v1:storerId>
-                            <v1:skuName>Biomet 鍥哄畾鍗佸瓧鍨嬫焺鑳骞冲彴鍋囦綋 75mm</v1:skuName>
-                            <v1:skuDec>-</v1:skuDec>
-                            <v1:spec>75mm</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>088030400832</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM154720</v1:skuId>
-                            <v1:storerId>CGKHTY</v1:storerId>
-                            <v1:skuName>Oxford绗笁浠e崟楂佽啙鍏宠妭楠ㄦ按娉ュ瀷瑙e墫鍨嬫爣鍑嗚儷楠ㄥ簳鏉�宸﹁啙鍐呬晶 Size B</v1:skuName>
-                            <v1:skuDec>Oxford绗笁浠e崟楂佽啙鍏宠妭楠ㄦ按娉ュ瀷瑙e墫鍨嬫爣鍑嗚儷楠ㄥ簳鏉�宸﹁啙鍐呬晶 Size B</v1:skuDec>
-                            <v1:spec>宸﹁啙鍐呬晶 Size B</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>501927938886</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM154720</v1:skuId>
-                            <v1:storerId>GGKHN1</v1:storerId>
-                            <v1:skuName>Oxford绗笁浠e崟楂佽啙鍏宠妭楠ㄦ按娉ュ瀷瑙e墫鍨嬫爣鍑嗚儷楠ㄥ簳鏉�宸﹁啙鍐呬晶 Size B</v1:skuName>
-                            <v1:skuDec>-</v1:skuDec>
-                            <v1:spec>宸﹁啙鍐呬晶 Size B</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType>C</v1:abcType>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions/>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>501927938886</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM154720</v1:skuId>
-                            <v1:storerId>TGKHMB</v1:storerId>
-                            <v1:skuName>Oxford绗笁浠e崟楂佽啙鍏宠妭楠ㄦ按娉ュ瀷瑙e墫鍨嬫爣鍑嗚儷楠ㄥ簳鏉�宸﹁啙鍐呬晶 Size B</v1:skuName>
-                            <v1:skuDec>Oxford绗笁浠e崟楂佽啙鍏宠妭楠ㄦ按娉ュ瀷瑙e墫鍨嬫爣鍑嗚儷楠ㄥ簳鏉�宸﹁啙鍐呬晶 Size B</v1:skuDec>
-                            <v1:spec>宸﹁啙鍐呬晶 Size B</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>501927938886</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                        <v1:COMMODITY_TB_ITEM>
-                            <v1:skuId>BM154720</v1:skuId>
-                            <v1:storerId>TNMGGK</v1:storerId>
-                            <v1:skuName>Oxford绗笁浠e崟楂佽啙鍏宠妭楠ㄦ按娉ュ瀷瑙e墫鍨嬫爣鍑嗚儷楠ㄥ簳鏉�宸﹁啙鍐呬晶 Size B</v1:skuName>
-                            <v1:skuDec>-</v1:skuDec>
-                            <v1:spec>宸﹁啙鍐呬晶 Size B</v1:spec>
-                            <v1:packageCode>浠�/v1:packageCode>
-                            <v1:packageQty>1</v1:packageQty>
-                            <v1:goodsUnit>浠�/v1:goodsUnit>
-                            <v1:length>10</v1:length>
-                            <v1:width>10</v1:width>
-                            <v1:height>10</v1:height>
-                            <v1:abcType/>
-                            <v1:isBatchMgr>0</v1:isBatchMgr>
-                            <v1:isSnMgr>0</v1:isSnMgr>
-                            <v1:isSnStorageMgr>0</v1:isSnStorageMgr>
-                            <v1:imgUrl/>
-                            <v1:cidtype>A</v1:cidtype>
-                            <v1:productLine>BM-鍏宠妭</v1:productLine>
-                            <v1:storageConditions>鏄�/v1:storageConditions>
-                            <v1:skuType>small</v1:skuType>
-                            <v1:maxCount>120</v1:maxCount>
-                            <v1:bMaxCount/>
-                            <v1:cMaxCount/>
-                            <v1:dMaxCount/>
-                            <v1:eMaxCount/>
-                            <v1:fMaxCount/>
-                            <v1:upc>501927938886</v1:upc>
-                        </v1:COMMODITY_TB_ITEM>
-                    </v1:COMMODITY_TB>
-                </v1:InputParameters>
-            </v1:COMMODITY_Input>
-        </v1:inCommodityReq>
-    </soapenv:Body>
-</soapenv:Envelope>
-
---]] wms_base = require("wms_base")
+       V2.6 鏈鏇存柊涓昏閽堝SKU鏂欑鏍煎弬鏁帮紙SKU_GridBox_Parm锛夊悓姝ラ�杈戣繘琛屼紭鍖栵紝
+       瑙e喅浜嗗湪涓嶅悓cid_type鍙樻洿鍦烘櫙涓嬬殑鏂欐牸澶勭悊闂锛岀‘淇濇暟鎹悓姝ョ殑鍑嗙‘鎬у拰瀹屾暣鎬с�
+       
+       ]] wms_base = require("wms_base")
 xml = require("oi_base_xml")
-mobox = require("OILua_JavelinExt")
 m3 = require("oi_base_mobox")
 
+-- 鍒涘缓鎴栨洿鏂癝KU_UPC鏉$爜璁板綍锛堥噸鏋勭増锛�+-- @param strLuaDEID: Lua鏁版嵁浜ゆ崲ID
+-- @param storer: 璐т富缂栫爜
+-- @param item_code: SKU缂栫爜
+-- @param upc_code: UPC鏉$爜
+-- @return: 杩斿洖涓や釜鍊�(閿欒鐮� 閿欒淇℃伅/鎴愬姛淇℃伅)
+-- 鍒涘缓鎴栨洿鏂癝KU_UPC鏉$爜璁板綍锛堜紭鍖栫増锛�+-- @param strLuaDEID: Lua鏁版嵁浜ゆ崲ID
+-- @param storer: 璐т富缂栫爜
+-- @param item_code: SKU缂栫爜
+-- @param upc_code: UPC鏉$爜
+-- @return: 杩斿洖涓や釜鍊�(閿欒鐮� 閿欒淇℃伅/鎴愬姛淇℃伅)
+local function create_or_update_sku_upc(strLuaDEID, storer, item_code, upc_code)
+    local nRet, strRetInfo
+
+    -- 1. 妫�煡UPC鏄惁鏈夋晥
+    if not upc_code or upc_code == '' then
+        -- lua.debugex(strLuaDEID, "UPC涓虹┖", "璐т富:"..storer..", SKU:"..item_code)
+        return 0, "UPC涓虹┖锛岃烦杩囧鐞� -- 淇敼涓鸿繑鍥�琛ㄧず璺宠繃
+    end
+
+    -- 2. 妫�煡璇KU鐨刄PC璁板綍鏄惁宸插瓨鍦紙涓夊瓧娈典富閿鏌ワ級
+    local strCondition = string.format("S_STORER = '%s' AND S_ITEM_CODE = '%s'", storer, item_code)
+    nRet, strRetInfo = mobox.existThisData(strLuaDEID, "SKU_UPC", strCondition)
+    if nRet ~= 0 then
+        local errMsg = "妫�煡SKU_UPC璁板綍澶辫触: " .. tostring(strRetInfo)
+        return 1, errMsg
+    end
+
+    -- 3. 澶勭悊妫�煡缁撴灉
+    if strRetInfo == 'yes' then
+        -- 璁板綍宸插瓨鍦ㄤ笖瀹屽叏鐩稿悓锛岀洿鎺ヨ烦杩�+        local updateAttr = string.format("S_UPC_CODE='%s'", upc_code);
+        local nRet, strRetInfo = mobox.updateDataAttrByCondition(strLuaDEID, "SKU_UPC", strCondition, updateAttr)
+        if (nRet ~= 0) then
+            return 1, "鏁版嵁鏇存柊澶辫触!" .. strRetInfo
+        else
+            lua.DebugEx(strLuaDEID, "鏁版嵁鏇存柊鎴愬姛....", strRetInfo)
+            return 0, "UPC 宸叉洿鏂� .. strRetInfo
+        end
+
+        -- 鍙綔涓烘洿鏂版搷浣�+        local sku_upc = m3.AllocObject(strLuaDEID, "SKU_UPC")
+        sku_upc.storer = storer
+        sku_upc.item_code = item_code
+        sku_upc.upc_code = upc_code
+        nRet, strRetInfo = m3.UpdateDataObj(strLuaDEID, sku_upc)
+        if nRet ~= 0 then
+            local errMsg = "鏇存柊SKU_UPC澶辫触: " .. tostring(strRetInfo)
+            return 1, errMsg
+        end
+        return 0, "SKU_UPC宸插瓨鍦ㄤ笖鐩稿悓锛岃烦杩囧鐞�
+    end
+
+    -- 5. 鍒涘缓鏂拌褰�+    local sku_upc = m3.AllocObject(strLuaDEID, "SKU_UPC")
+    sku_upc.storer = storer
+    sku_upc.item_code = item_code
+    sku_upc.upc_code = upc_code
+
+    nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, sku_upc)
+    if nRet ~= 0 then
+        local errMsg = "鍒涘缓SKU_UPC澶辫触: " .. tostring(strRetInfo)
+        return 1, errMsg
+    end
+    return 0, "鍒涘缓SKU_UPC鎴愬姛"
+end
+
+-- 鍒涘缓/鏇存柊SKU瀵瑰簲鐨勮揣鍝佹枡绠辨牸鍙傛暟
+-- 涓嶅啀渚濊禆cell_type浣滀负鎴鑼冨洿锛岃�鏄鏌ユ墍鏈塵axCount~fMaxCount瀛楁
+-- @param strLuaDEID: Lua鏁版嵁浜ゆ崲ID
+-- @param skuModel: SKU妯″瀷瀵硅薄
+-- @param sku_input_data: 杈撳叆鏁版嵁
+-- @return: 杩斿洖閿欒鐮佸拰閿欒淇℃伅
+local function create_or_update_sku_gridbox(strLuaDEID, skuModel, sku_input_data)
+    local strRetInfo
+
+    -- 1. 鑾峰彇榛樿瀹瑰櫒绫诲瀷缂栫爜
+    local nConstRet, CONST_CTD_CODE = wms_base.Get_sConst2("WMS_Default_CNTR_Type")
+    if nConstRet ~= 0 then
+        return 1, "鑾峰彇榛樿瀹瑰櫒绫诲瀷瀹氫箟缂栫爜澶辫触: " .. CONST_CTD_CODE
+    end
+    -- 2. 瀹氫箟鏂欑鏍肩被鍨嬩笌瀛楁鏄犲皠鍏崇郴
+    local gridbox_types = {
+        A = {
+            field = "maxCount",
+            value = sku_input_data.maxCount
+        },
+        B = {
+            field = "bMaxCount",
+            value = sku_input_data.bMaxCount
+        },
+        C = {
+            field = "cMaxCount",
+            value = sku_input_data.cMaxCount
+        },
+        D = {
+            field = "dMaxCount",
+            value = sku_input_data.dMaxCount
+        },
+        E = {
+            field = "eMaxCount",
+            value = sku_input_data.eMaxCount
+        },
+        F = {
+            field = "fMaxCount",
+            value = sku_input_data.fMaxCount
+        }
+    }
+    -- 3. 澶勭悊鎵�湁鏂欑鏍肩被鍨�+    for cell_type, type_info in pairs(gridbox_types) do
+        local loading_limit = lua.Get_NumAttrValue(type_info.value) or 0
+
+        -- 鍙湁褰撻檺鍒跺�澶т簬0鏃舵墠澶勭悊
+        if loading_limit > 0 then
+            -- 绮剧‘鏌ヨ璇ョ被鍨嬬殑鏂欑鏍艰褰�+            local strCondition = string.format(
+                "S_ITEM_CODE = '%s' AND S_STORER = '%s' AND S_CTD_CODE='%s' AND S_CELL_TYPE='%s'", skuModel.item_code,
+                skuModel.storer, CONST_CTD_CODE, cell_type)
+            local nRet, existing_records = m3.GetDataObjByCondition(strLuaDEID, "SKU_GridBox_Parm", strCondition)
+
+            if nRet == 0 then
+                -- 璁板綍瀛樺湪锛屾洿鏂扮幇鏈夎褰�+                local update_gridbox_obj = {{
+                    id = existing_records.id,
+                    attrs = {{
+                        attr = "N_LOADING_LIMIT",
+                        value = loading_limit
+                    }}
+                }}
+                nRet, strRetInfo =
+                    mobox.updateDataObj(strLuaDEID, "SKU_GridBox_Parm", lua.table2str(update_gridbox_obj))
+                if nRet ~= 0 then
+                    return 1, string.format("鏇存柊%s绫诲瀷鏂欑鏍煎睘鎬уけ璐� %s", cell_type, strRetInfo)
+                end
+            elseif nRet == 1 then
+                -- 璁板綍涓嶅瓨鍦紝鍒涘缓鏂拌褰�+                local gridbox = m3.AllocObject(strLuaDEID, "SKU_GridBox_Parm")
+                gridbox.item_code = skuModel.item_code
+                gridbox.storer = skuModel.storer
+                gridbox.ctd_code = CONST_CTD_CODE
+                gridbox.loading_limit = loading_limit
+                gridbox.cell_type = cell_type
+                nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, gridbox)
+                if nRet ~= 0 then
+                    return 1, string.format("鍒涘缓%s绫诲瀷鏂欑鏍煎け璐� %s", cell_type, strRetInfo)
+                end
+            else
+                -- 鏌ヨ鍑洪敊
+                return 1, string.format("鏌ヨ%s绫诲瀷鏂欑鏍艰褰曞け璐� %s", cell_type,
+                    existing_records or "鏈煡閿欒")
+            end
+        end
+    end
+
+    return 0, "鏂欑鏍煎弬鏁板鐞嗗畬鎴�
+end
 -- 鍒涘缓缁熶竴杩斿洖缁撴灉锛堜慨鏀瑰悗鐗堟湰锛岀Щ闄rror瀛楁锛� function Create_result(flag, code, msg)
     return {
@@ -350,13 +194,10 @@
 
 -- 鍒涘缓鎴栨洿鏂癎K_PROLINE鏁版嵁(鐢熶骇绾挎暟鎹�
 local function create_or_update_proline(strLuaDEID, proline_no, proline_name)
-    local nRet, strRetInfo
-
     -- 鍒嗛厤GK_PROLINE瀵硅薄
     local proline = m3.AllocObject(strLuaDEID, "GK_PROLINE")
     proline.proline_no = proline_no
     proline.proline_name = proline_name
-
     -- 妫�煡鏄惁宸插瓨鍦�     local strCondition = string.format("S_PROLINE_NO = '%s'", proline_no)
     local nRet, id, strRetInfo = mobox.getDataObjAttrByKeyAttr(strLuaDEID, "GK_PROLINE", strCondition)
@@ -380,7 +221,6 @@
                 value = proline_name
             }}
         }}
-
         nRet, strRetInfo = mobox.updateDataObj(strLuaDEID, "GK_PROLINE", lua.table2str(update_proline_obj))
         if nRet ~= 0 then
             return 1, "鏇存柊GK_PROLINE澶辫触: " .. strRetInfo
@@ -389,204 +229,99 @@
     return 0, strRetInfo
 end
 
--- 鍒涘缓SKU_UPC
-local function create_sku_upc(strLuaDEID, storer, item_code, upc_code)
-    local nRet, strRetInfo
-    if (upc_code == '' or upc_code == nil) then
-        return 0
+-- 閲嶆瀯鍚庣殑build_sku_grid_json鍑芥暟
+-- 鐜板湪瀹屽叏鍩轰簬鏁版嵁搴撲腑鐨勫疄闄呮枡鏍艰褰曠敓鎴怞SON
+-- @param strLuaDEID: Lua鏁版嵁浜ゆ崲ID
+-- @param item_code: SKU缂栫爜
+-- @param storer: 璐т富缂栫爜
+-- @return: 杩斿洖涓や釜鍊�(JSON瀛楃涓� 閿欒淇℃伅)
+local function build_sku_grid_json(strLuaDEID, item_code, storer)
+    -- 1. 鑾峰彇榛樿瀹瑰櫒绫诲瀷缂栫爜
+    local nConstRet, CONST_CTD_CODE = wms_base.Get_sConst2("WMS_Default_CNTR_Type")
+    if nConstRet ~= 0 then
+        return "", "鑾峰彇榛樿瀹瑰櫒绫诲瀷瀹氫箟缂栫爜澶辫触: " .. CONST_CTD_CODE
     end
 
-    local sku_upc = m3.AllocObject(strLuaDEID, "SKU_UPC")
-    sku_upc.storer = storer
-    sku_upc.item_code = item_code
-    sku_upc.upc_code = upc_code
-    nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, sku_upc)
+    -- 2. 鏌ヨ璇KU鎵�湁鐜版湁鐨勬枡绠辨牸璁板綍
+    local strCondition = string.format("S_ITEM_CODE = '%s' AND S_STORER = '%s' AND S_CTD_CODE='%s'", item_code, storer,
+        CONST_CTD_CODE)
+    local nRet, grid_records = m3.QueryDataObject(strLuaDEID, "SKU_GridBox_Parm", strCondition)
 
-    return nRet, strRetInfo
-end
-
-
--- 鏂板sku_grid_parm JSON瀛楃涓诧紝鍦⊿KU 鍒涘缓鐨勬椂鍊欐彃鍏son鏁版嵁
-local function build_sku_grid_parm(ctd_code, sku_input_data, cell_type)
-    -- 濡傛灉cell_type涓虹┖鍒欒烦杩�-    if not cell_type or cell_type == "" then
-        return ""
+    -- 3. 澶勭悊鏌ヨ缁撴灉
+    if nRet ~= 0 then
+        return "", "鏌ヨSKU_GridBox_Parm璁板綍澶辫触: " .. (grid_records or "鏈煡閿欒")
     end
 
-    -- 瀹氫箟鍩虹json妗嗘灦缁撴瀯锛堟斁鍦ㄦ暟缁勪腑锛�+    -- 4. 鏋勫缓鍩虹JSON缁撴瀯
     local grid_def = {{
-        ctd_code = ctd_code,
+        ctd_code = CONST_CTD_CODE,
         cell_def = {}
     }}
 
-    -- 鏍规嵁cell_type纭畾澶勭悊鑼冨洿
-    local types_to_process = {}
-    if cell_type == "A" then
-        types_to_process = {"A"}
-    elseif cell_type == "B" then
-        types_to_process = {"A", "B"}
-    elseif cell_type == "C" then
-        types_to_process = {"A", "B", "C"}
-    elseif cell_type == "D" then
-        types_to_process = {"A", "B", "C", "D"}
-    elseif cell_type == "E" then
-        types_to_process = {"A", "B", "C", "D", "E"}
-    elseif cell_type == "F" then
-        types_to_process = {"A", "B", "C", "D", "E", "F"}
-    else
-        -- 鏈煡绫诲瀷锛岄粯璁ゅ彧澶勭悊A绫诲瀷
-        types_to_process = {"A"}
-    end
+    -- 5. 澶勭悊鏌ヨ鍒扮殑璁板綍
+    if grid_records and #grid_records > 0 then
+        for _, record in ipairs(grid_records) do
+            -- 灏嗗睘鎬ф暟缁勮浆鎹负瀵硅薄
+            local record_obj = m3.KeyValueAttrsToObjAttr(record.attrs)
 
-    -- 瀹氫箟鏂欑绫诲瀷涓庡搴斿瓧娈电殑鏄犲皠
-    local grid_mapping = {
-        A = {loading_limit = sku_input_data.maxCount},
-        B = {loading_limit = sku_input_data.bMaxCount},
-        C = {loading_limit = sku_input_data.cMaxCount},
-        D = {loading_limit = sku_input_data.dMaxCount},
-        E = {loading_limit = sku_input_data.eMaxCount},
-        F = {loading_limit = sku_input_data.fMaxCount}
-    }
+            -- 鎻愬彇闇�鐨勫瓧娈�+            local cell_type = record_obj.S_CELL_TYPE or ""
+            local loading_limit = lua.Get_NumAttrValue(record_obj.N_LOADING_LIMIT) or 0
+            local load_capacity = lua.Get_NumAttrValue(record_obj.F_LOAD_CAPACITY) or loading_limit -- 榛樿绛変簬loading_limit
 
-    -- 鏋勫缓cell_def鏁扮粍
-    for _, type_key in ipairs(types_to_process) do
-        local grid = grid_mapping[type_key]
-        local limit = lua.Get_NumAttrValue(grid.loading_limit) or 0
-        if limit > 0 then  -- 鍙湁褰撻檺鍒跺�澶т簬0鏃舵墠娣诲姞
-            table.insert(grid_def[1].cell_def, {
-                cell_type = type_key,
-                loading_limit = limit,
-                load_capacity = limit
-            })
-        end
-    end
-
-    lua.DebugEx(strLuaDEID, "grid", grid_def)
-    return lua.table2str(grid_def)
-end
-
--- 鍒涘缓/鏇存柊SKU瀵瑰簲鐨勮揣鍝佹枡绠辨牸鍙傛暟
--- skuModel 鏄暟鎹簱瀹氫箟鐨勬暟鎹ā鍨媠ku锛屼篃灏辨槸Alloc鎵�垱寤虹殑SKU瀵硅薄銆�-local function create_or_update_sku_gridbox(strLuaDEID, skuModel, sku_input_data)
-    local strRetInfo
-    -- 鑾峰彇榛樿瀹瑰櫒绫诲瀷缂栫爜
-    local nConstRet, CONST_CTD_CODE = wms_base.Get_sConst2("WMS_Default_CNTR_Type")
-    if nConstRet ~= 0 then
-        return 1, "鑾峰彇榛樿瀹瑰櫒绫诲瀷瀹氫箟缂栫爜澶辫触: " .. CONST_CTD_CODE
-    end
-
-    -- 濡傛灉cell_type涓虹┖鍒欒烦杩�-    if not skuModel.cell_type or skuModel.cell_type == "" then
-        return 0, "cell_type涓虹┖锛岃烦杩囨枡绠辨牸鍙傛暟澶勭悊"
-    end
-
-    -- 鏍规嵁cell_type纭畾澶勭悊鑼冨洿
-    local types_to_process = {}
-    if skuModel.cell_type == "A" then
-        types_to_process = {"A"}
-    elseif skuModel.cell_type == "B" then
-        types_to_process = {"A", "B"}
-    elseif skuModel.cell_type == "C" then
-        types_to_process = {"A", "B", "C"}
-    elseif skuModel.cell_type == "D" then
-        types_to_process = {"A", "B", "C", "D"}
-    elseif skuModel.cell_type == "E" then
-        types_to_process = {"A", "B", "C", "D", "E"}
-    elseif skuModel.cell_type == "F" then
-        types_to_process = {"A", "B", "C", "D", "E", "F"}
-    else
-        -- 鏈煡绫诲瀷锛岄粯璁ゅ彧澶勭悊A绫诲瀷
-        types_to_process = {"A"}
-    end
-
-    -- 瀹氫箟鏂欑鏍肩被鍨嬩笌瀵瑰簲瀛楁鐨勬槧灏�-    local gridbox_types = {
-        A = sku_input_data.maxCount,
-        B = sku_input_data.bMaxCount,
-        C = sku_input_data.cMaxCount,
-        D = sku_input_data.dMaxCount,
-        E = sku_input_data.eMaxCount,
-        F = sku_input_data.fMaxCount
-    }
-
-    -- 澶勭悊姣忕鏂欑鏍肩被鍨�-    for _, type_key in ipairs(types_to_process) do
-        local loading_limit = lua.Get_NumAttrValue(gridbox_types[type_key]) or 0
-        if loading_limit <= 0 then  -- 鍙湁褰撻檺鍒跺�澶т簬0鏃舵墠澶勭悊
-            goto continue
-        end
-        
-        -- 绮剧‘鏌ヨ璇ョ被鍨嬬殑鏂欑鏍艰褰�-        local strCondition = string.format(
-            "S_ITEM_CODE = '%s' AND S_STORER = '%s' AND S_CTD_CODE='%s' AND S_CELL_TYPE='%s'", 
-            skuModel.item_code, skuModel.storer, CONST_CTD_CODE, type_key)
-        local nRet, existing_records = m3.GetDataObjByCondition(strLuaDEID, "SKU_GridBox_Parm", strCondition)
-        
-        if nRet == 0 then
-            -- 鏇存柊鐜版湁璁板綍
-            local update_gridbox_obj = {{
-                id = existing_records.id,
-                attrs = {{
-                    attr = "N_LOADING_LIMIT",
-                    value = loading_limit
-                }}
-            }}
-
-            nRet, strRetInfo = mobox.updateDataObj(strLuaDEID, "SKU_GridBox_Parm", lua.table2str(update_gridbox_obj))
-            if nRet ~= 0 then
-                return 1, string.format("鏇存柊%s绫诲瀷鏂欑鏍煎睘鎬уけ璐� %s", type_key, strRetInfo)
+            -- 鍙湁褰撳�鏈夋晥鏃舵墠娣诲姞鍒癑SON
+            if cell_type ~= "" and loading_limit > 0 then
+                table.insert(grid_def[1].cell_def, {
+                    cell_type = cell_type,
+                    loading_limit = loading_limit,
+                    load_capacity = load_capacity
+                })
             end
-        elseif nRet == 1 then
-            -- 鍒涘缓鏂拌褰�-            local gridbox = m3.AllocObject(strLuaDEID, "SKU_GridBox_Parm")
-            gridbox.item_code = skuModel.item_code
-            gridbox.storer = skuModel.storer
-            gridbox.ctd_code = CONST_CTD_CODE
-            gridbox.loading_limit = loading_limit
-            gridbox.cell_type = type_key
-
-            nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, gridbox)
-            if nRet ~= 0 then
-                return 1, string.format("鍒涘缓%s绫诲瀷鏂欑鏍煎け璐� %s", type_key, strRetInfo)
-            end
-        else
-            -- 鏌ヨ鍑洪敊
-            return 1, string.format("鏌ヨ%s绫诲瀷鏂欑鏍艰褰曞け璐� %s", type_key, existing_records or "鏈煡閿欒")
         end
-        
-        ::continue::
     end
 
-    return 0, "鏂欑鏍煎弬鏁板鐞嗗畬鎴�
+    -- 6. 杞崲涓篔SON瀛楃涓�+    local json_str = lua.table2str(grid_def)
+    -- -- lua.debugex(strLuaDEID, "鐢熸垚鐨刧rid_json", json_str)
+
+    return json_str
 end
 -- 鍒涘缓鎴栨洿鏂癝KU涓绘暟鎹�+-- @param  sku_input_data: 瀹為檯涓婂氨鏄姤鏂囦腑鐨勶細sku_data.COMMODITY_TB_ITEM 涓嬮潰鐨勫瓧娈靛唴瀹� local function create_sku(strLuaDEID, sku_input_data)
     local nRet, strRetInfo
-    local err_msg = ''
+    -- 棣栧厛鏍¢獙cidtype鏄惁涓虹┖
+    if not sku_input_data.cidtype or sku_input_data.cidtype == '' then
+        return 1, "skuId涓猴細" .. sku_input_data.skuId .. "鐨勯�閰嶆枡鏍糲idtype涓嶅厑璁镐负绌猴紒"
+    end
+
     -- 鑾峰彇绯荤粺甯搁噺
     -- 鑾峰彇榛樿瀹瑰櫒绫诲瀷缂栫爜
     local nConstRet, CONST_CTD_CODE = wms_base.Get_sConst2("WMS_Default_CNTR_Type")
     if nConstRet ~= 0 then
         return 1, "鑾峰彇榛樿瀹瑰櫒绫诲瀷瀹氫箟缂栫爜澶辫触: " .. CONST_CTD_CODE
     end
-    -- 鏂板SKU_grid_param
-    local sku_grid_parm = build_sku_grid_parm(CONST_CTD_CODE, sku_input_data, sku_input_data.cidtype)
-    lua.DebugEx(strLuaDEID, "sku_grid_parm", sku_grid_parm)
+    if (sku_input_data.cidtype == nil or sku_input_data.cidtype == '') then
+        return 1, "skuId涓猴細" .. sku_input_data.skuId .. "鐨勯�閰嶆枡鏍糲idtype涓嶅厑璁镐负绌猴紒"
+    end
+
     -- 棣栧厛妫�煡SKU鏄惁宸插瓨鍦�     local strCondition = string.format("S_ITEM_CODE = '%s' AND S_STORER = '%s'", sku_input_data.skuId,
         sku_input_data.storerId)
-    local nRet, existing_sku = m3.GetDataObjByCondition(strLuaDEID, "SKU", strCondition)
-    -- lua.DebugEx(strLuaDEID, "鑾峰彇鏉′欢鏌ヨ锛�, existing_sku)
-    if nRet > 1 then
-        return 1, "妫�煡SKU鏄惁瀛樺湪鏃跺け璐� " .. (existing_sku or "鏈煡閿欒")
+
+    local existSKUnRet, existingSKU = mobox.existThisData(strLuaDEID, "SKU", strCondition)
+    lua.DebugEx(strLuaDEID, "妫�煡SKU鏄惁瀛樺湪杩斿洖缁撴灉", existingSKU);
+
+    if existSKUnRet ~= 0 then
+        return 1, "妫�煡SKU鏄惁瀛樺湪鏃跺け璐� " .. (existingSKU or "鏈煡閿欒")
     end
 
     -- 鍒嗛厤SKU瀵硅薄骞惰缃睘鎬�     local sku = m3.AllocObject(strLuaDEID, "SKU")
     sku.item_code = sku_input_data.skuId
     sku.storer = sku_input_data.storerId
-    sku.short_name = sku_input_data.skuName
-    sku.item_name = sku_input_data.skuDec
+    sku.item_name = sku_input_data.skuName
+    sku.note = sku_input_data.skuDec
     sku.spec = sku_input_data.spec
     sku.unit = sku_input_data.goodsUnit
     sku.long = lua.Get_NumAttrValue(sku_input_data.length) or 0
@@ -600,24 +335,46 @@
     sku.cell_type = sku_input_data.cidtype
     sku.item_type = sku_input_data.skuType
     sku.loading_limit = lua.Get_NumAttrValue(sku_input_data.maxCount) or 0
+    sku.sku_grid_parm = '[{"ctd_code":"CTD-001","cell_def":{}}]'; -- 鍏堢粰涓粯璁ゅ�
+
+    -- 2025-07-21 鏂板涓昏〃瀛楁
     sku.udf01 = sku_input_data.productLine or ""
-    sku.udf03 = sku_input_data.isSnStorageMgr or ""
-    sku.udf02 = sku_input_data.storageConditions or ""
-    sku.udf04 = sku_input_data.packageCode or ""
-    sku.udf05 = lua.Get_NumAttrValue(sku_input_data.packageQty) or 0
-    sku.sku_grid_parm = sku_grid_parm;
-    -- lua.DebugEx(strLuaDEID, "鏇存柊/鍒涘缓鏁版嵁缁撴灉锛�, sku)
-    if nRet == 1 then
-        -- SKU涓嶅瓨鍦紝鍒涘缓鏂拌褰�-        nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, sku)
-        if nRet ~= 0 then
-            return 1, "鍒涘缓SKU澶辫触: " .. strRetInfo .. " skuId = " .. sku_input_data.skuId
+    sku.udf02 = sku_input_data.registerNo or "" -- 娉ㄥ唽璇佸彿
+    sku.udf03 = sku_input_data.companyName or "" -- 鐢熶骇浼佷笟
+    sku.udf04 = sku_input_data.certCompanyName or "" -- 璇佷欢鐢熶骇鍘傚
+    sku.udf05 = sku_input_data.consignCompanyWTName or "" -- 濮旀墭鐢熶骇鍘傚
+    sku.udf06 = sku_input_data.sterilizationDate or "" -- 鐏弻鏃ユ湡
+    sku.udf06 = sku_input_data.ex1 or "" -- 鎵╁睍瀛楁1
+    sku.udf07 = sku_input_data.ex2 or "" -- 鎵╁睍瀛楁2
+    sku.udf08 = sku_input_data.ex3 or "" -- 鎵╁睍瀛楁3
+    -- 1. 鍏堝鐞嗘枡绠辨牸鍙傛暟锛堢‘淇濇暟鎹簱璁板綍鏈�柊锛�+    local nRet, strRetInfo = create_or_update_sku_gridbox(strLuaDEID, sku, sku_input_data)
+    if nRet ~= 0 then
+        return 1, "澶勭悊SKU_GridBox_Parm澶辫触: " .. strRetInfo
+    end
+
+    -- 2. 鍩轰簬鏁版嵁搴撳疄闄呰褰曠敓鎴怞SON锛堜笉鍐嶄緷璧栦紶鍏ョ殑cidtype锛�+    local sku_grid_parm, err = build_sku_grid_json(strLuaDEID, sku.item_code, sku.storer)
+    if err then
+        return 1, "鐢熸垚SKU_GRID_PARM澶辫触: " .. err
+    end
+    sku.sku_grid_parm = sku_grid_parm -- 鐩存帴鏇存柊SKU瀵硅薄鐨勫睘鎬�+
+    -- SKU涓嶅瓨鍦紝鍒涘缓鏂拌褰�+    if existingSKU == 'no' then
+        lua.DebugEx(strLuaDEID, "SKU涓嶅瓨鍦紝鍒涘缓鏂拌褰�);
+        local createnRet, strRetInfo = m3.CreateDataObj(strLuaDEID, sku)
+        if createnRet ~= 0 then
+            return 1, "鍒涘缓SKU澶辫触: 淇℃伅锛� .. strRetInfo
         end
     else
         -- SKU宸插瓨鍦紝鏇存柊璁板綍
         local update_sku_obj = {{
-            id = existing_sku.id,
+            id = sku.id,
             attrs = {{
+                attr = "S_CTD_CODE",
+                value = CONST_CTD_CODE
+            }, {
                 attr = "S_ITEM_NAME",
                 value = sku.item_name
             }, {
@@ -632,6 +389,9 @@
             }, {
                 attr = "S_SHORT_NAME",
                 value = sku.short_name
+            }, {
+                attr = "S_NOTE",
+                value = sku.note
             }, {
                 attr = "S_ABCTYPE",
                 value = sku.abc_type
@@ -675,12 +435,21 @@
                 attr = "S_UDF05",
                 value = sku.udf05
             }, {
+                attr = "S_UDF06",
+                value = sku.udf06
+            }, {
+                attr = "S_UDF07",
+                value = sku.udf07
+            }, {
+                attr = "S_UDF08",
+                value = sku.udf08
+            }, {
                 attr = "S_SKU_GRID_PARM",
                 value = sku.sku_grid_parm
             }}
         }}
         nRet, strRetInfo = mobox.updateDataObj(strLuaDEID, "SKU", lua.table2str(update_sku_obj))
-        -- lua.DebugEx(strLuaDEID, "鏇存柊杩斿洖鍊�, nRet)
+        lua.DebugEx(strLuaDEID, "鏇存柊SKU瀵硅薄缁撴灉", nRet .. "  " .. strRetInfo);
         if nRet ~= 0 then
             return 1, "鏇存柊SKU灞炴�澶辫触: " .. strRetInfo
         end
@@ -697,29 +466,28 @@
     end
 
     -- 澶勭悊SKU_UPC鏉$爜
-    local upc_codes = {sku_input_data.sptm, sku_input_data.barcode1, sku_input_data.barcode2, sku_input_data.barcode3,
-                       sku_input_data.barcode_pk, sku_input_data.upc}
-
-    for _, upc_code in ipairs(upc_codes) do
-        if upc_code and upc_code ~= '' then
-            nRet, strRetInfo = create_sku_upc(strLuaDEID, sku.storer, sku.item_code, upc_code)
-            if nRet ~= 0 then
-                return 1, "鍒涘缓SKU_UPC澶辫触: " .. strRetInfo .. " UPC: " .. upc_code
-            end
+    -- 澶勭悊SKU_UPC鏉$爜锛堜慨鏀瑰悗鐗堟湰锛�+    -- 鍦╟reate_sku鍑芥暟涓鐞哠KU_UPC鏉$爜鐨勯儴鍒嗕慨鏀逛负锛�+    local upc_code = sku_input_data.upc
+    if upc_code and upc_code ~= '' then
+        nRet, strRetInfo = create_or_update_sku_upc(strLuaDEID, sku.storer, sku.item_code, upc_code)
+        if nRet ~= 0 then
+            -- lua.debugex(strLuaDEID, "澶勭悊SKU_UPC澶辫触", strRetInfo)
+            return 1, "澶勭悊SKU_UPC澶辫触: " .. strRetInfo
         end
+        -- lua.debugex(strLuaDEID, "澶勭悊SKU_UPC鎴愬姛", upc_code)
     end
-
     -- 澶勭悊SKU_GridBox_Parm鏂欑鏍煎弬鏁�-    nRet, strRetInfo = create_or_update_sku_gridbox(strLuaDEID, sku, sku_input_data)
+    local nRet, strRetInfo = create_or_update_sku_gridbox(strLuaDEID, sku, sku_input_data)
     if nRet ~= 0 then
         return 1, "澶勭悊SKU_GridBox_Parm澶辫触: " .. strRetInfo
     end
-
     return 0
 end
 
 -- Main鍑芥暟
 function SKU_Sync(strLuaDEID)
+    m3.PrintLuaDEInfo(strLuaDEID)
     -- 鍒濆鍖栨渶缁堢粨鏋�     local FinalRes = Create_result()
 
diff --git a/lua_code/Lua/GK-API-02-Storer_Sync.lua b/lua_code/Lua/GK-API-02-Storer_Sync.lua
new file mode 100644
index 0000000..6993c0b
--- /dev/null
+++ b/lua_code/Lua/GK-API-02-Storer_Sync.lua
@@ -0,0 +1,247 @@
+--[[ 
+    缂栫爜: GK-API-01
+    鍚嶇О: 璐т富淇℃伅鍚屾鎺ュ彛
+    浣滆�: PMN
+    鏃ユ湡: 2025-5-20
+
+    鍏ュ彛鍑芥暟锛歋torer_Sync
+    鍔熻兘璇存槑:
+        1. 鎺ユ敹璐т富淇℃伅鍚屾璇锋眰
+        2. 鍒ゆ柇璐т富鏄惁瀛樺湪
+        3. 鎵ц鏂板鎴栦慨鏀�+        4. 杩斿洖澶勭悊缁撴灉
+
+    杈撳叆XML绀轰緥:    
+    <soapenv:Envelope
+    xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
+    <soap:Header
+        xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
+    </soap:Header>
+    <soapenv:Body>
+        <v1:InCompanyReq
+            xmlns:v1="http://www.gkht.com/Information/INV/Ebs/Schemas/InCompany/V1.0">
+            <v1:Company_Input>
+                <v1:RESTHeader>
+                    <v1:Responsibility/>
+                    <v1:RespApplication/>
+                    <v1:SecurityGroup/>
+                    <v1:NLSLanguage>SIMPLIFIED CHINESE</v1:NLSLanguage>
+                    <v1:Org_Id>0</v1:Org_Id>
+                </v1:RESTHeader>
+                <v1:InputParameters>
+                    <v1:COMPANY_TB>
+                        <!--1 or more repetitions:-->
+                        <v1:COMPANY_TB_ITEM>
+                            <v1:companyCode>CBJJT1</v1:companyCode>
+                            <v1:companyName>鍖椾含浜嘲鏃ユ櫉绉戞妧鏈夐檺鍏徃</v1:companyName>
+                            <v1:contactName></v1:contactName>
+                            <v1:contactPhone></v1:contactPhone>
+                            <v1:contactAddress></v1:contactAddress>
+                            <v1:memo>涓�/v1:memo>
+                        </v1:COMPANY_TB_ITEM>
+						     <v1:COMPANY_TB_ITEM>
+                            <v1:companyCode>CBJJXK</v1:companyCode>
+                            <v1:companyName>鍖椾含鍚夐懌搴峰晢璐告湁闄愬叕鍙�/v1:companyName>
+                            <v1:contactName></v1:contactName>
+                            <v1:contactPhone></v1:contactPhone>
+                            <v1:contactAddress></v1:contactAddress>
+                            <v1:memo>涓�/v1:memo>
+                        </v1:COMPANY_TB_ITEM>
+                    </v1:COMPANY_TB>
+                </v1:InputParameters>
+            </v1:Company_Input>
+        </v1:InCompanyReq>
+    </soapenv:Body>
+</soapenv:Envelope>
+--]]
+
+wms_base = require("wms_base")
+xml = require("oi_base_xml")
+
+-- 妫�煡璐т富鏄惁瀛樺湪
+local function check_storer_exists(strLuaDEID, storer_item)
+    local storerId = storer_item.storerId
+
+    local strCondition = string.format("S_STORER = '%s' ", storerId)
+    local nRet, id, strRetInfo = mobox.getDataObjAttrByKeyAttr(strLuaDEID, "STORER", strCondition)
+    
+    if nRet > 1 then
+        return nRet, "妫�煡璐т富鏄惁瀛樺湪鏃跺嚭閿� " .. strRetInfo
+    elseif nRet == 1 then
+        return 1, "璐т富涓嶅瓨鍦�  -- 涓嶅瓨鍦�+    else
+        return 0, id  -- 瀛樺湪
+    end
+end
+
+-- 鏂板璐т富
+local function create_storer(strLuaDEID, storer_data)
+    local storer = m3.AllocObject(strLuaDEID, "STORER")
+    local nRet1, CONST_WH = wms_base.Get_sConst2(strLuaDEID, "WMS_Default_Warehouse")
+    local storerCode = storer_data.storerId
+    -- 瀛楁鏄犲皠
+    storer.storer = storerCode
+    storer.storer_name = storerCode
+    storer.company_code = storer_data.companyCode
+    storer.company_name = storer_data.companyName
+    storer.contact_name = storer_data.contactName or ""
+    storer.contact_phone = storer_data.contactPhone or ""
+    storer.contact_address = storer_data.contactAddress or ""
+    storer.note = storer_data.memo or ""
+    storer.default_wh_code = CONST_WH
+    
+    local nRet, result = m3.CreateDataObj(strLuaDEID, storer)
+    return nRet, result
+end
+
+-- 鏇存柊璐т富淇℃伅
+local function update_storer(strLuaDEID, storer_id, storer_data)
+    local update_storer_obj = {
+            {
+                id = storer_id,
+                attrs = {
+                    { attr = "S_COMPANY_CODE", value = storer_data.companyCode },
+                    { attr = "S_COMPANY_NAME", value = storer_data.companyName },
+                    { attr = "S_STORER_NAME", value = storer_data.companyName },
+                    { attr = "S_CONTACT_NAME", value = storer_data.contactName },
+                    { attr = "S_CONTACT_PHONE", value = storer_data.contactPhone },
+                    { attr = "S_CONTACT_ADDRESS", value = storer_data.contactAddress },
+                    { attr = "S_NOTE", value = storer_data.memo },
+                }
+            }
+        }
+    
+    local nRet, result = mobox.updateDataObj( strLuaDEID, "STORER", lua.table2str(update_storer_obj) )
+    return nRet, result
+end
+
+-- 澶勭悊鍗曚釜璐т富璁板綍
+local function process_storer_item(strLuaDEID, storer_item)
+    
+    -- 1. 妫�煡璐т富鏄惁瀛樺湪
+    local nRet, result = check_storer_exists(strLuaDEID, storer_item)
+    if nRet > 1 then
+        return nRet, result
+    end
+    
+    -- 2. 瀛樺湪鍒欐洿鏂帮紝涓嶅瓨鍦ㄥ垯鏂板
+    if nRet == 0 then
+        local storer_id = result
+        -- 璐т富瀛樺湪锛屾洿鏂颁俊鎭�+        nRet, result = update_storer(strLuaDEID, storer_id, storer_item)
+        if nRet ~= 0 then
+            return nRet, "鏇存柊璐т富淇℃伅澶辫触: " .. tostring(result)
+        end
+        return 0, {action = "update", id = storer_id}
+    else
+        -- 璐т富涓嶅瓨鍦紝鏂板
+        nRet, result = create_storer(strLuaDEID, storer_item)
+        if nRet ~= 0 then
+            return nRet, "鏂板璐т富澶辫触: " .. tostring(result)
+        end
+        return 0, {action = "create", id = result}
+    end
+end
+
+function Storer_Sync(strLuaDEID)
+    local nRet, strRetInfo, nErr
+    local err_msg
+    nErr = 0
+    local isStop = 0
+    local err = {}
+    
+    -- m3.PrintLuaDEInfo(strLuaDEID)
+    
+    -- 1. 鑾峰彇鎺ュ彛杈撳叆鏁版嵁
+    local soap_xml
+    nRet, soap_xml = mobox.getCurEditDataPacket(strLuaDEID)
+    if nRet ~= 0 then 
+        lua.Stop(strLuaDEID, "鏃犳硶鑾峰彇鏁版嵁鍖� " .. soap_xml)
+        isStop = 3
+        return
+    end
+    
+    -- 2. 瑙f瀽XML
+    local parsed_data
+    nRet, parsed_data = xml.parse(soap_xml)
+    if nRet ~= 0 then
+        lua.Stop(strLuaDEID, "鎺ュ彛杈撳叆鐨刋ML鏍煎紡闈炴硶!")
+        isStop = 3
+        return
+    end
+    
+    -- 3. 鎻愬彇璐т富鏁版嵁
+    local company_data = parsed_data.Envelope.Body.InCompanyReq.Company_Input
+    local input_params = company_data.InputParameters
+    local company_tb = input_params.COMPANY_TB
+    
+    -- 澶勭悊鍗曟潯鎴栧鏉¤揣涓绘暟鎹�+    local storer_items = {}
+    if company_tb.COMPANY_TB_ITEM[1] ~= nil then
+        storer_items = company_tb.COMPANY_TB_ITEM
+    else
+        storer_items = {company_tb.COMPANY_TB_ITEM}
+    end
+    
+    -- 4. 澶勭悊姣忔潯璐т富璁板綍
+    for i, item in ipairs(storer_items) do
+        local storer_data = {
+            storerId = item.storerId,
+            companyCode = item.companyCode,
+            companyName = item.companyName,
+            contactName = item.contactName or "",
+            contactPhone = item.contactPhone or "",
+            contactAddress = item.contactAddress or "",
+            memo = item.memo or ""
+        }
+        
+        -- 蹇呭~瀛楁鏍¢獙
+        if not storer_data.companyCode or storer_data.companyCode == "" then
+            err_msg = string.format("绗�d鏉¤褰� companyCode涓嶈兘涓虹┖", i)
+            wms_base.Warning(strLuaDEID, 1, 601, err_msg, "浠嶨K-WMS绯荤粺鍚屾璐т富淇℃伅")
+            nErr = nErr + 1
+            err[nErr] = err_msg
+            lua.Stop(strLuaDEID, err_msg)
+            isStop = 5
+        end
+        
+        if not storer_data.companyName or storer_data.companyName == "" then
+            err_msg = string.format("绗�d鏉¤褰� companyName涓嶈兘涓虹┖", i)
+            wms_base.Warning(strLuaDEID, 1, 601, err_msg, "浠嶨K-WMS绯荤粺鍚屾璐т富淇℃伅")
+            nErr = nErr + 1
+            err[nErr] = err_msg
+            lua.Stop(strLuaDEID, err_msg)
+            isStop = 5
+        end
+
+        if not storer_data.storerId or storer_data.storerId == "" then
+            err_msg = string.format("绗�d鏉¤褰� storerId涓嶈兘涓虹┖", i)
+            wms_base.Warning(strLuaDEID, 1, 601, err_msg, "浠嶨K-WMS绯荤粺鍚屾璐т富淇℃伅")
+            nErr = nErr + 1
+            err[nErr] = err_msg
+            lua.Stop(strLuaDEID, err_msg)
+            isStop = 5
+        end
+        
+        -- 澶勭悊璐т富璁板綍
+        nRet, result = process_storer_item(strLuaDEID, storer_data)
+        if nRet ~= 0 then
+            err_msg = result
+            wms_base.Warning(strLuaDEID, 1, 601, err_msg, "浠嶨K-WMS绯荤粺鍚屾璐т富淇℃伅")
+            nErr = nErr + 1
+            err[nErr] = err_msg
+            lua.Stop(strLuaDEID, err_msg)
+            isStop = 5
+        end
+    end
+    
+    -- 5. 杩斿洖鍝嶅簲
+    local response = {
+        flag = nErr > 0 and "failure" or "success",
+        code = nErr,
+        message = nErr > 0 and table.concat(err, "; ") or "澶勭悊鎴愬姛",
+    }
+    
+    local xml_result = xml.json_to_xml(response, "response")
+    mobox.returnValue(strLuaDEID, 0, xml_result, isStop)
+end
\ No newline at end of file
diff --git a/lua_code/Lua/GK-API-03-SKU-Batch_Sync.lua b/lua_code/Lua/GK-API-03-SKU-Batch_Sync.lua
new file mode 100644
index 0000000..7c1c1de
--- /dev/null
+++ b/lua_code/Lua/GK-API-03-SKU-Batch_Sync.lua
@@ -0,0 +1,271 @@
+--[[
+缂栫爜: GK-API-03
+鍚嶇О: 鍟嗗搧鎵规鍚屾鎺ュ彛
+浣滆�: yuanfeng
+鏃ユ湡: 2025/5/13
+鍏ュ彛鍑芥暟锛欱atch_Sync
+鏉ユ簮椤圭洰: 鍥界椤圭洰
+
+鍔熻兘璇存槑:
+    1. 鍒涘缓銆佽鐩朑K_BATCH瀹炰綋
+    2. 鏇存柊INV_Detail鐩稿叧鑷畾涔夊瓧娈�+
+鍙樻洿鍘嗗彶:
+v0.0.2 - 鏍煎紡楠岃瘉涓嶉�杩囩殑杩斿洖鎶ユ枃
+v0.0.3 - CG_Detail寮冪敤锛屽彉鏇翠负搴撳瓨琛↖NV_Detail
+v2.0 - 2025-07-16 浼樺寲浠g爜缁撴瀯锛屼繚鎸佸師鏈変笟鍔¢�杈戯紝缁熶竴杩斿洖鏍煎紡
+v2.1 - 2025-07-16 淇SQL娉ㄥ叆鍜岀壒娈婂瓧绗﹀鐞嗛棶棰�+
+--]] local mobox = require("OILua_JavelinExt")
+local m3 = require("oi_base_mobox")
+local xml = require("oi_base_xml")
+local wms_base = require("wms_base")
+
+-- 瀹炰綋鏍囪瘑
+local CLSID_GKbatch = "GK_BATCH"
+local CLSID_INVdetail = "INV_Detail"
+
+-- 鍒涘缓缁熶竴杩斿洖缁撴灉
+function Create_result(flag, code, msg)
+    return {
+        flag = flag or "success",
+        code = code or "0",
+        message = msg or ""
+    }
+end
+
+-- SQL杞箟澶勭悊
+local function sql_escape(value)
+    if value == nil then
+        return ""
+    end
+    value = tostring(value)
+    -- 杞箟鍗曞紩鍙枫�鍙嶆枩鏉犮�鐧惧垎鍙枫�涓嬪垝绾跨瓑鐗规畩瀛楃
+    value = string.gsub(value, "(['\\%%_])", "\\%1")
+    return value
+end
+-- 鏋勫缓鎵规鏁版嵁瀵硅薄锛堜慨鏀筩onsign_company_name澶勭悊锛�+local function buildBatchData(dataSet)
+    local consign_company_name = lua.Get_StrAttrValue(dataSet.consignCompanyWTName)
+    -- 鐗规畩澶勭悊鍙嶆枩鏉�+    if consign_company_name == "\\" then
+        consign_company_name = "\\\\" -- 灏嗗崟涓弽鏂滄潬杞箟涓哄弻鍙嶆枩鏉�+    end
+
+    return {
+        storer_no = lua.Get_StrAttrValue(dataSet.storerId),
+        item_code = lua.Get_StrAttrValue(dataSet.skuId),
+        owner_no = lua.Get_StrAttrValue(dataSet.ownerId),
+        wms_bn = lua.Get_StrAttrValue(dataSet.batchNo),
+        batch_no = lua.Get_StrAttrValue(dataSet.produceCode),
+        product_date = lua.Get_StrAttrValue(dataSet.productDate),
+        expiry_date = lua.Get_StrAttrValue(dataSet.expiryDate),
+        register_no = lua.Get_StrAttrValue(dataSet.registerNo),
+        company_name = lua.Get_StrAttrValue(dataSet.companyName),
+        cert_company_name = lua.Get_StrAttrValue(dataSet.certCompanyName),
+        consign_company_name = consign_company_name, -- 浣跨敤澶勭悊鍚庣殑鍊�+        sterilization_date = lua.Get_StrAttrValue(dataSet.sterilizationData),
+        note = lua.Get_StrAttrValue(dataSet.memo),
+        ex1 = lua.Get_StrAttrValue(dataSet.ex1),
+        ex2 = lua.Get_StrAttrValue(dataSet.ex2),
+        ex3 = lua.Get_StrAttrValue(dataSet.ex3)
+    }
+end
+
+-- 鍒涘缓鎴栨洿鏂版壒娆℃暟鎹�+local function create_or_update_batch(strLuaDEID, dataSet)
+    -- 鏋勫缓鏌ヨ鏉′欢
+    local strCondition = string.format("S_STORER = '%s' AND S_ITEM_CODE = '%s' AND S_OWNER = '%s' AND S_WMS_BN = '%s'",
+        sql_escape(lua.Get_StrAttrValue(dataSet.storerId)), sql_escape(lua.Get_StrAttrValue(dataSet.skuId)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.ownerId)), sql_escape(lua.Get_StrAttrValue(dataSet.batchNo)))
+
+    -- 妫�煡鎵规鏄惁瀛樺湪
+    local nRet, id, strRetInfo = mobox.getDataObjAttrByKeyAttr(strLuaDEID, CLSID_GKbatch, strCondition)
+
+    -- 鏋勫缓鎵规鏁版嵁锛堜細璋冪敤淇敼鍚庣殑buildBatchData锛�+    local batch_data = buildBatchData(dataSet)
+
+    if nRet == 0 then
+        -- 鎵规瀛樺湪锛屾洿鏂拌褰�+        local update_batch_obj = {{
+            id = id,
+            attrs = {{
+                attr = "S_BATCH_NO",
+                value = batch_data.batch_no
+            }, {
+                attr = "D_PRODUCT_DATE",
+                value = batch_data.product_date
+            }, {
+                attr = "D_EXPIRY_DATE",
+                value = batch_data.expiry_date
+            }, {
+                attr = "S_REGISTER_NO",
+                value = batch_data.register_no
+            }, {
+                attr = "S_COMPANY_NAME",
+                value = batch_data.company_name
+            }, {
+                attr = "S_CERT_COMPANY_NAME",
+                value = batch_data.cert_company_name
+            }, {
+                attr = "S_CONSIGN_COMPANY_NAME",
+                value = batch_data.consign_company_name -- 杩欓噷宸茬粡鏄鐞嗚繃鐨勫�
+            }, {
+                attr = "D_STERILIZATION_DATE",
+                value = batch_data.sterilization_date
+            }, {
+                attr = "S_NOTE",
+                value = batch_data.note
+            }, {
+                attr = "S_EX1",
+                value = batch_data.ex1
+            }, {
+                attr = "S_EX2",
+                value = batch_data.ex2
+            }, {
+                attr = "S_EX3",
+                value = batch_data.ex3
+            }}
+        }}
+
+        nRet, strRetInfo = mobox.updateDataObj(strLuaDEID, CLSID_GKbatch, lua.table2str(update_batch_obj))
+        if nRet ~= 0 then
+            return 1, "鏇存柊鎵规鏁版嵁澶辫触: " .. strRetInfo
+        end
+    elseif nRet == 1 then
+        -- 鎵规涓嶅瓨鍦紝鍒涘缓鏂拌褰�+        local batch = m3.AllocObject(strLuaDEID, CLSID_GKbatch)
+        batch.storer_no = batch_data.storer_no
+        batch.item_code = batch_data.item_code
+        batch.owner_no = batch_data.owner_no
+        batch.wms_bn = batch_data.wms_bn
+        batch.batch_no = batch_data.batch_no
+        batch.product_date = batch_data.product_date
+        batch.expiry_date = batch_data.expiry_date
+        batch.register_no = batch_data.register_no
+        batch.company_name = batch_data.company_name
+        batch.cert_company_name = batch_data.cert_company_name
+        batch.consign_company_name = batch_data.consign_company_name
+        batch.sterilization_date = batch_data.sterilization_date
+        batch.note = batch_data.note
+        batch.ex1 = batch_data.ex1
+        batch.ex2 = batch_data.ex2
+        batch.ex3 = batch_data.ex3
+
+        nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, batch)
+        if nRet ~= 0 then
+            return 1, "鍒涘缓鎵规鏁版嵁澶辫触: " .. strRetInfo
+        end
+    else
+        return 1, "鏌ヨ鎵规鏁版嵁澶辫触: " .. strRetInfo
+    end
+
+    return 0
+end
+
+-- 鏇存柊搴撳瓨鏄庣粏鏁版嵁
+local function update_inv_detail(strLuaDEID, dataSet)
+    -- 鏋勫缓鏌ヨ鏉′欢
+    local strCondition = string.format("S_STORER = '%s' AND S_OWNER = '%s' AND S_ITEM_CODE = '%s' AND S_WMS_BN = '%s'",
+        sql_escape(lua.Get_StrAttrValue(dataSet.storerId)), sql_escape(lua.Get_StrAttrValue(dataSet.ownerId)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.skuId)), sql_escape(lua.Get_StrAttrValue(dataSet.batchNo)))
+
+    -- 鏋勫缓鏇存柊瀛楁
+    local strUpdateSql = string.format("S_BATCH_NO = '%s', D_PRD_DATE = '%s', D_EXP_DATE = '%s', " ..
+                                           "S_UDF01 = '%s', S_UDF02 = '%s', S_UDF03 = '%s', " ..
+                                           "S_UDF04 = '%s', S_UDF05 = '%s', " ..
+                                           "S_UDF06 = '%s', S_UDF07 = '%s', S_UDF08 = '%s'",
+        sql_escape(lua.Get_StrAttrValue(dataSet.produceCode)), sql_escape(lua.Get_StrAttrValue(dataSet.productDate)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.expiryDate)), sql_escape(lua.Get_StrAttrValue(dataSet.registerNo)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.companyName)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.certCompanyName)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.consignCompanyWTName)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.sterilizationDate)), sql_escape(lua.Get_StrAttrValue(dataSet.ex1)),
+        sql_escape(lua.Get_StrAttrValue(dataSet.ex2)), sql_escape(lua.Get_StrAttrValue(dataSet.ex3)))
+    -- 鎵ц鏇存柊
+    local nRet, strRetInfo = mobox.updateDataAttrByCondition(strLuaDEID, CLSID_INVdetail, strCondition, strUpdateSql)
+    if nRet ~= 0 then
+        return 1, "鏇存柊搴撳瓨鏄庣粏澶辫触: " .. strRetInfo
+    end
+
+    return 0
+end
+
+-- 澶勭悊鍗曟潯鎵规鏁版嵁
+local function process_batch_item(strLuaDEID, dataSet)
+    -- 澶勭悊鎵规鏁版嵁
+    local nRet, err_msg = create_or_update_batch(strLuaDEID, dataSet)
+    if nRet ~= 0 then
+        return 1, err_msg
+    end
+
+    -- 鏇存柊搴撳瓨鏄庣粏
+    lua.DebugEx(strLuaDEID, "鍑嗗鏇存柊鐨勫簱瀛樻槑缁嗘暟鎹� ", lua.table2str(dataSet))
+    nRet, err_msg = update_inv_detail(strLuaDEID, dataSet)
+    if nRet ~= 0 then
+        return 1, err_msg
+    end
+
+    return 0
+end
+
+-- 涓诲嚱鏁�+function Batch_Sync(strLuaDEID)
+    -- 鍒濆鍖栨渶缁堢粨鏋�+    local FinalRes = Create_result()
+
+    -- 1. 鑾峰彇xml鏁版嵁鍖�+    local nRet, soap_xml = mobox.getCurEditDataPacket(strLuaDEID)
+    if nRet ~= 0 then
+        FinalRes = Create_result("failure", "201", "鏃犳硶鑾峰彇鏁版嵁鍖� " .. soap_xml)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "鑾峰彇鏁版嵁鍖呭け璐�, FinalRes)
+        return
+    end
+
+    -- 2. 瑙f瀽xml
+    local nRet, parsed_data = xml.parse(soap_xml)
+    if nRet ~= 0 then
+        FinalRes = Create_result("failure", "202", "xml鏍煎紡闈炴硶")
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "xml鏍煎紡闈炴硶", FinalRes)
+        return
+    end
+
+    -- 3. 鎻愬彇鎵规鏁版嵁
+    local batch_data = parsed_data.Envelope.Body.InBatchGoodsReq.BatchGoods_Input.InputParameters.BATCHGOODS_TB
+    if not batch_data or not batch_data.BATCHGOODS_TB_ITEM then
+        FinalRes = Create_result("failure", "203", "xml鏁版嵁鏍煎紡閿欒锛岀己灏態ATCHGOODS_TB_ITEM")
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "xml鏁版嵁鏍煎紡閿欒", FinalRes)
+        return
+    end
+
+    -- 4. 缁熶竴澶勭悊锛氱‘淇漛atch_items鏄暟缁�+    local batch_items = batch_data.BATCHGOODS_TB_ITEM
+    if batch_items[1] == nil then
+        batch_items = {batch_items}
+    end
+
+    -- 5. 閬嶅巻鎵�湁鎵规鏁版嵁
+    for i = 1, #batch_items do
+        local batch_item = batch_items[i]
+        local nRet, err_msg = process_batch_item(strLuaDEID, batch_item)
+        if nRet ~= 0 then
+            wms_base.Warning(strLuaDEID, 1, 601, err_msg, "浠嶨K-WMS绯荤粺鍚屾鎵规淇℃伅")
+            FinalRes = Create_result("failure", "204", "鎵规鍚屾澶辫触: " .. err_msg)
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "鎵规鍚屾澶辫触: " .. batch_item.batchNo, FinalRes)
+            return
+        end
+    end
+
+    -- 6. 杩斿洖鎴愬姛
+    FinalRes = Create_result("success", "0", "鎵规鍚屾鎴愬姛")
+    local xml_result = xml.json_to_xml(FinalRes, "response")
+    mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+end
diff --git a/lua_code/Lua/GK-API-04-Receipt_Sync.lua b/lua_code/Lua/GK-API-04-Receipt_Sync.lua
new file mode 100644
index 0000000..b9383ea
--- /dev/null
+++ b/lua_code/Lua/GK-API-04-Receipt_Sync.lua
@@ -0,0 +1,292 @@
+--[[
+ 缂栫爜: GK-API-04
+ 鍚嶇О: GK-WMS-Receipt_Sync 
+ 浣滆�: 琚佸嘲
+ 鍏ュ彛鍑芥暟锛歊eceipt_Sync 
+ 鍔熻兘璇存槑: 鎺ユ敹涓婃父绯荤粺鐨刋ML鏁版嵁锛屽垱寤烘敹璐у崟涓昏〃锛圧eceipt_Order锛夊拰鏄庣粏璁板綍锛圧eceipt_Detail锛夈�
+ 杈撳叆鍙傛暟: xmlData锛圶ML鏍煎紡鐨勫瓧绗︿覆锛�+ 杩斿洖鍙傛暟: xml 鏍煎紡鐨勫搷搴旀姤鏂囷細
+ 褰㈠锛�+ <response>
+    <message>鏀惰揣鍗曞凡瀛樺湪</message>
+    <code>204</code>
+    <flag>failure</flag>
+    <error>鏀惰揣鍗昜SO2025050701]宸插瓨鍦�/error>
+ </response>
+ 
+ 璋冪敤绀轰緥: Receipt_Sync(xmlData)
+ 娉ㄦ剰浜嬮」: 1. 杈撳叆鍙傛暟xmlData涓篨ML鏍煎紡鐨勫瓧绗︿覆锛屽寘鍚簡鏀惰揣鍗曚富琛ㄥ拰鏄庣粏璁板綍鐨勬暟鎹�
+          2. 鍑芥暟浼氳В鏋怷ML鏁版嵁锛屽苟灏嗗叾鎻掑叆鍒版暟鎹簱涓�
+          3. 鍏佽xml 浼犲叆1鏉℃垨鑰呭鏉℃敹璐у崟涓昏〃鏁版嵁锛屾瘡鏉℃敹璐у崟涓昏〃鏁版嵁鍙互鍖呭惈澶氭潯鏀惰揣鍗曟槑缁嗘暟鎹�
+
+ 鍙樻洿鍘嗗彶: 2025-05-14 浼樺寲杩斿洖缁撴灉澶勭悊
+ 
+ XML 鎶ユ枃绀轰緥濡備笅锛�+<soapenv:Envelope
+    xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
+    <soap:Header
+        xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
+    </soap:Header>
+    <soapenv:Body>
+        <v1:InSmallPieceReq
+            xmlns:v1="http://www.gkht.com/InReceive/INV/Ebs/Schemas/InSmallPiece/V1.0">
+            <v1:SmallPiece_Input>
+                <v1:RESTHeader>
+                    <v1:Responsibility/>
+                    <v1:RespApplication/>
+                    <v1:SecurityGroup/>
+                    <v1:NLSLanguage>SIMPLIFIED CHINESE</v1:NLSLanguage>
+                    <v1:Org_Id>0</v1:Org_Id>
+                </v1:RESTHeader>
+                <v1:InputParameters>
+                        <!--1 or more repetitions:-->
+                       <v1:SmallPiece_TB>
+                           <v1:orderNo>SO2025050601</v1:orderNo>
+                           <v1:asnNo>KPD00001</v1:asnNo>
+                           <v1:storerId>CGKHTY</v1:storerId>
+                           <v1:ownerId>CGKHTY</v1:ownerId>
+                           <v1:orderDate>2025-05-06</v1:orderDate>
+				            	    <v1:priority>0</v1:priority>
+					     		<v1:memo></v1:memo>
+				        		<v1:SmallPiece_TB_ITEM>
+                            <v1:orderItemId>1</v1:orderItemId>
+                            <v1:skuId>XR33201-2L080B</v1:skuId>
+                            <v1:skuStatus>AVL</v1:skuStatus>
+                            <v1:qty>2</v1:qty>
+					    			<v1:batchNo>PHI00000000000001309</v1:batchNo>
+                            <v1:produceCode>YL201125</v1:produceCode>
+					    			<v1:productDate>2016-04-23</v1:productDate>
+					    			<v1:expiryDate>2099-12-31</v1:expiryDate>
+					    			<v1:registerNo>鍥介鑽洃姊帮紙鍑�瀛�012</v1:registerNo>
+                        </v1:SmallPiece_TB_ITEM>
+					     	<v1:SmallPiece_TB_ITEM>
+                            <v1:orderItemId>2</v1:orderItemId>
+                            <v1:skuId>KH32803017</v1:skuId>
+                            <v1:skuStatus>AVL</v1:skuStatus>
+                            <v1:qty>5</v1:qty>
+					      		<v1:batchNo>PHI00000000000001308</v1:batchNo>
+                            <v1:produceCode>YL2011256</v1:produceCode>
+					     		<v1:productDate>2023-04-23</v1:productDate>
+					     		<v1:expiryDate>2099-12-31</v1:expiryDate>
+					      		<v1:registerNo></v1:registerNo>
+                        </v1:SmallPiece_TB_ITEM>
+                    </v1:SmallPiece_TB>
+                </v1:InputParameters>
+            </v1:SmallPiece_Input>
+        </v1:InSmallPieceReq>
+    </soapenv:Body>
+</soapenv:Envelope>
+--]] wms_base = require("wms_base")
+xml = require("oi_base_xml")
+mobox = require("OILua_JavelinExt")
+m3 = require("oi_base_mobox")
+function Create_result(flag, code, msg)
+    return {
+        flag = flag or "success",
+        code = code or "0",
+        message = msg or ""
+    }
+end
+function Receipt_Sync(strLuaDEID)
+    -- 鍒濆鍖栨渶缁堢粨鏋�+    local FinalRes = Create_result()
+    -- 1. 鑾峰彇 xml 鏁版嵁鍖�+    local nRet, soap_xml = mobox.getCurEditDataPacket(strLuaDEID)
+    if nRet ~= 0 then
+        FinalRes = Create_result("failure", "201", "鏃犳硶鑾峰彇鏁版嵁鍖� " .. soap_xml)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "鑾峰彇鏁版嵁鍖呭け璐�, soap_xml)
+        return
+    end
+
+    -- lua.DEbugEx(strLuaDEID, "鑾峰彇鍒扮殑鏁版嵁鍖�, soap_xml)
+
+    -- 2. 瑙f瀽 xml
+    local nRet, parsed_data = xml.parse(soap_xml)
+    if nRet ~= 0 then
+        FinalRes = Create_result("failure", "202", "xml 鏍煎紡闈炴硶" .. parsed_data)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "xml鏍煎紡闈炴硶", parsed_data)
+        return
+    end
+
+    -- 3. 鎻愬彇涓昏〃鏁版嵁
+    local receipt_data = parsed_data.Envelope.Body.InSmallPieceReq.SmallPiece_Input
+    local input_params = receipt_data.InputParameters
+
+    -- 妫�煡鏄惁瀛樺湪 SmallPiece_TB
+    if not input_params or not input_params.SmallPiece_TB then
+        FinalRes = Create_result("failure", "203", "xml 鏁版嵁鏍煎紡閿欒锛岀己灏�SmallPiece_TB")
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "xml 鏁版嵁鏍煎紡閿欒", xml_result)
+        return
+    end
+
+    -- 4. 缁熶竴澶勭悊锛氱‘淇�receipt_headers 鏄暟缁勶紙鍗充娇鍙湁涓�釜涓昏〃锛�+    local receipt_headers = input_params.SmallPiece_TB
+    if receipt_headers[1] == nil then
+        receipt_headers = {receipt_headers}
+    end
+
+    -- 5. 鑾峰彇绯荤粺甯搁噺
+    local RetWH_COE, CONST_WH = wms_base.Get_sConst2("WMS_Default_Warehouse")
+    local RetFAC_COE, CONST_FACTORY = wms_base.Get_sConst2("WMS_Default_Factory")
+
+    -- 浠撳簱甯搁噺寮傚父鎹曡幏
+    if (RetWH_COE ~= 0) then
+        FinalRes = Create_result("failure", "204", "鑾峰彇浠撳簱甯搁噺澶辫触" .. CONST_WH)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "鑾峰彇绯荤粺甯搁噺锛歐MS_Default_Warehouse 澶辫触", xml_result)
+        return
+    end
+
+    -- 宸ュ巶甯搁噺寮傚父鎹曡幏
+    if (RetFAC_COE ~= 0) then
+        FinalRes = Create_result("failure", "204", "鑾峰彇宸ュ巶甯搁噺澶辫触" .. CONST_FACTORY)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "鑾峰彇绯荤粺甯搁噺锛歐MS_Default_Factory", xml_result)
+        return
+    end
+    -- 6. 閬嶅巻鎵�湁鏀惰揣鍗�+    for i = 1, #receipt_headers do
+        local header = receipt_headers[i]
+        -- 妫�煡鏀惰揣鍗曟槸鍚﹀凡瀛樺湪
+        local strCondition = string.format("S_NO = '%s'", header.orderNo)
+        -- lua.DEbugEx(strLuaDEID, "鏌ヨ鏀惰揣鍗曟潯浠�, strCondition)
+        local nRet, retReceipt = m3.GetDataObjByCondition(strLuaDEID, "Receipt_Order", strCondition)
+
+        if nRet == 0 then
+            -- 鏌ヨ鎴愬姛涓旀壘鍒拌褰曪紝璇存槑鏀惰揣鍗曞凡瀛樺湪
+            -- lua.DEbugEx(strLuaDEID, "鏌ヨ鎴愬姛锛屾敹璐у崟宸插瓨鍦�, retReceipt)
+            FinalRes = Create_result("failure", "1", "鏀惰揣鍗昜" .. header.orderNo .. "]宸插瓨鍦�)
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "鏀惰揣鍗曞凡瀛樺湪", retReceipt)
+            return
+        elseif nRet ~= 1 then
+            -- 鏌ヨ鍑洪敊
+            -- lua.DEbugEx(strLuaDEID, "鏌ヨ鍑洪敊", retReceipt)
+            FinalRes = Create_result("failure", "206",
+                "妫�煡鏀惰揣鍗昜" .. header.orderNo .. "]鏃跺嚭閿� " .. retReceipt)
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "妫�煡鏀惰揣鍗曟槸鍚﹀瓨鍦ㄦ椂鍑洪敊", xml_result)
+            return
+        end
+
+        -- 鍒涘缓涓昏〃鏁版嵁
+        local receipt = m3.AllocObject(strLuaDEID, "Receipt_Order")
+        receipt.no = header.orderNo
+        receipt.asn_no = header.asnNo
+        receipt.op_date = header.orderDate
+        receipt.priority = header.priority
+        receipt.note = header.memo or ""
+        receipt.bs_type = "SMALL_PIECE"
+        receipt.factory = CONST_FACTORY
+        receipt.wh_code = CONST_WH
+
+        -- 妫�煡鏄惁宸插瓨鍦ㄧ浉鍚屽叧閿瓧鐨勮褰�+        local nRet, ret_info = m3.CreateDataObj(strLuaDEID, receipt)
+        if nRet ~= 0 then
+            -- 鍐嶆妫�煡鏄惁鐪熺殑瀛樺湪
+            local nRetCheck, retReceiptCheck = m3.GetDataObjByCondition(strLuaDEID, "Receipt_Order", strCondition)
+            if nRetCheck == 0 then
+                FinalRes = Create_result("failure", "205", "鏀惰揣鍗昜" .. header.orderNo .. "]宸插瓨鍦�)
+            else
+                FinalRes = Create_result("failure", "207",
+                    "鏀惰揣鍗昜" .. header.orderNo .. "]鍒涘缓澶辫触: " .. ret_info)
+            end
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "鍒涘缓鏀惰揣鍗曚富琛ㄥけ璐�, ret_info)
+            return
+        end
+
+        -- 妫�煡鏄庣粏鏁版嵁鏄惁瀛樺湪
+        if header.SmallPiece_TB_ITEM == nil then
+            -- lua.DEbugEx(strLuaDEID, "璀﹀憡锛氭敹璐у崟 " .. header.orderNo .. " 鏃犳槑缁嗘暟鎹�)
+            FinalRes = Create_result("failure", "208", "鏀惰揣鍗昜" .. header.orderNo .. "]鏃犳槑缁嗘暟鎹�)
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "鏀惰揣鍗曟棤鏄庣粏鏁版嵁", xml_result)
+            return
+        end
+
+        -- 7. 閬嶅巻褰撳墠鏀惰揣鍗曠殑鎵�湁鏄庣粏鏁版嵁
+        local details = header.SmallPiece_TB_ITEM
+        -- 纭繚 details 鏄暟缁勶紙鍗充娇鍙湁涓�釜鏄庣粏锛�+        if details[1] == nil then
+            details = {details}
+        end
+
+        for j = 1, #details do
+            local item = details[j]
+            -- 鍏堟楠宻kuId鏄惁瀛樺湪
+            local strCondition = string.format("S_ITEM_CODE= '%s' AND S_STORER = '%s'", item.skuId, header.storerId)
+            -- 鎵ц鏌ヨ
+            local nRet, receiptInfo = m3.GetDataObjByCondition(strLuaDEID, "SKU", strCondition)
+            if (nRet ~= 0) then
+                -- lua.DEbugEx(strLuaDEID, "SKU鏌ヨ鍑洪敊",
+                    -- "ITEM_CODE: " .. item.skuId .. ", 閿欒淇℃伅: " .. receiptInfo)
+                FinalRes = Create_result("failure", "207",
+                    "妫�煡 SKU 鏄惁瀛樺湪鏃跺嚭閿�SKU ID涓�" .. item.skuId .. ", 閿欒: " .. receiptInfo)
+                local xml_result = xml.json_to_xml(FinalRes, "response")
+                mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+                lua.Stop(strLuaDEID, "鏌ヨ澶辫触", xml_result)
+                return
+            elseif (receiptInfo == "") then
+                -- lua.DEbugEx(strLuaDEID, "鏌ヨ涓虹┖", "ITEM_CODE:" .. item.skuId)
+                FinalRes = Create_result("failure", "208", "鏌ヨ鏁版嵁涓虹┖锛欼TEM_CODE : " .. item.skuId)
+                local xml_result = xml.json_to_xml(FinalRes, "response")
+                mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+                lua.Stop(strLuaDEID, "鐗╂枡鏁版嵁涓嶅瓨鍦�, xml_result)
+                return
+            end
+
+            -- 鍒涘缓鏄庣粏鏁版嵁
+            local receipt_detail = m3.AllocObject(strLuaDEID, "Receipt_Detail")
+            receipt_detail.row_no = item.orderItemId
+            receipt_detail.receipt_no = header.orderNo
+            receipt_detail.qty = lua.Get_NumAttrValue(item.qty) or 0
+            receipt_detail.acc_put_qty = lua.Get_NumAttrValue("0")
+            receipt_detail.acc_unq_qty = lua.Get_NumAttrValue("0")
+            receipt_detail.acc_c_qty = lua.Get_NumAttrValue("0")
+            receipt_detail.item_code = item.skuId
+            receipt_detail.item_state = item.skuStatus
+            receipt_detail.item_name = receiptInfo.item_name or ""
+            receipt_detail.wu = "kg"
+            receipt_detail.batch_no = item.produceCode
+            receipt_detail.wms_bn = item.batchNo
+            receipt_detail.prd_date = item.productDate
+            receipt_detail.exp_date = item.expiryDate
+            receipt_detail.udf01 = item.registerNo
+            receipt_detail.storer = header.storerId
+            receipt_detail.owner = header.ownerId
+            receipt_detail.item_name = receiptInfo.item_name or ""
+            receipt_detail.net_weight = receiptInfo.weight or 0
+            receipt_detail.gross_weight = receiptInfo.weight or 0
+            receipt_detail.uom = receiptInfo.uom or ""
+
+            -- lua.DEbugEx(strLuaDEID, "鍒涘缓鏄庣粏鏁版嵁:", receipt_detail)
+            local nRet, ret_info = m3.CreateDataObj(strLuaDEID, receipt_detail)
+            if nRet ~= 0 then
+                FinalRes = Create_result("failure", "208", "鍒涘缓鏀惰揣鏄庣粏澶辫触: " .. ret_info)
+                local xml_result = xml.json_to_xml(FinalRes, "response")
+                mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+                -- lua.DEbugEx(strLuaDEID, "鍒涘缓鏀惰揣鏄庣粏澶辫触", xml_result)
+                lua.Stop(strLuaDEID, "鍒涘缓鏀惰揣鏄庣粏澶辫触", ret_info)
+                return
+            end
+        end
+    end
+
+    -- 8. 杩斿洖鎴愬姛
+    FinalRes = Create_result("success", "0", "鏀惰揣鍗曞垱寤烘垚鍔�)
+    local xml_result = xml.json_to_xml(FinalRes, "response")
+    mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+end
diff --git a/lua_code/Lua/GK-API-05-InboundSync.lua b/lua_code/Lua/GK-API-05-InboundSync.lua
new file mode 100644
index 0000000..ec31590
--- /dev/null
+++ b/lua_code/Lua/GK-API-05-InboundSync.lua
@@ -0,0 +1,525 @@
+--[[
+    缂栫爜:   GK-API-05
+    鍚嶇О:   灏忎欢浠诲姟鍒涘缓鎺ュ彛
+    浣滆�:   Peter fang
+    鏃ユ湡:   2025-05-13
+
+    鍏ュ彛鍑芥暟锛�Inbound_Sync
+    鏉ユ簮椤圭洰锛�鍥界椤圭洰
+    
+    鍔熻兘璇存槑锛�+        1. 鎺ユ敹鏉ヨ嚜涓婃父绯荤粺鐨刋ML鏍煎紡鏁版嵁锛屽苟瑙f瀽璇ユ暟鎹紝鍒涘缓Inbound Order鍙奍nbound Detail
+        2. 鍒涘缓Inbound Palletization鍙奍nbound Pallet Detail
+]]
+
+wms_base = require( "wms_base" )
+xml=require( "oi_base_xml" )
+wms_pallet = require( "wms_palletizing" )
+
+-- 鍒涘缓缁熶竴杩斿洖缁撴灉
+local function create_result(flag, code, msg)
+    return {
+        flag = flag or "success",
+        code = code or "0",
+        message = msg or ""
+    }
+end
+
+local function return_value(strLuaDEID, success,err_msg)
+    if success==false then
+        lua.Stop( strLuaDEID, err_msg )
+    end
+    local flag = "success"
+    local code="0"
+    if success==true then
+        flag = "success"
+        code="0"
+    else
+        flag = "failure"
+        code="1"
+    end
+    local result= create_result( flag, code, err_msg )
+    local xml_result = xml.json_to_xml(result, "response")
+    local value=0
+    if flag=="success" then
+        value=0
+    else
+        value=3
+    end 
+    mobox.returnValue(strLuaDEID,1,xml_result,value)
+end
+
+local function count_cell_list(t)
+    local count = 0
+    for cell,group in pairs(t) do
+        if(cell~=nil and cell~="") then
+            count = count + 1
+        end
+    end
+    return count
+end
+
+local function group_by(t, key)
+    local result = {}
+    local getKey = type(key) == "function" and key or function(item)
+        return item[key]
+    end
+    for _, item in ipairs(t) do
+        local groupKey = getKey(item)
+        if groupKey ~= nil then
+            if not result[groupKey] then
+                result[groupKey] = {}
+            end
+            table.insert(result[groupKey], item)
+        end
+    end
+    return result
+end
+
+local function goods_count(items)
+    local group_table = group_by(items, "skuId")
+    local count = 0
+    for _ in pairs(group_table) do
+        count = count + 1
+    end
+    return count
+end
+
+local function sku_count(items)
+    local qty=0
+    for _,v in ipairs(items) do
+        if v.qty~=nil then
+            qty=qty+lua.Get_NumAttrValue(v.qty)
+        end
+    end
+    return qty
+end
+
+local function get_celltype(group,cid)
+    local spec="A"
+    local cellItems={}
+    for _,cell in ipairs(group) do
+        table.insert(cellItems,cell)
+    end
+    local by_cell=group_by(cellItems,"boxCode")
+    local cellCount=count_cell_list(by_cell)
+    if (cellCount==1) then
+        spec="A"
+    elseif (cellCount==2) then
+        spec="B"
+    elseif (cellCount==3) then
+        spec="C"    
+    elseif (cellCount==4) then
+        spec="D"
+    elseif (cellCount==6) then
+        spec="E"
+    elseif (cellCount==8) then
+        spec="F"
+    else
+        return 1, "鏂欐牸鏁伴噺"..cellCount.. "鏂欑瑙勬牸瓒呭嚭绯荤粺瀹氫箟锛乧ntr_code= "..cid
+    end
+    return 0, spec
+end
+
+local function create_inbound_pallet(strLuaDEID,inboundData,items)
+    local nRet,strRetInfo
+    local by_pallet=group_by(items,"cid")
+    for cid, group in pairs(by_pallet) do
+        if cid~=nil and cid~="" then
+            if(group[1].boxCode~=nil and group[1].boxCode~="") then
+                local spec
+                nRet, spec = get_celltype(group,cid)
+                if nRet ~= 0 then
+                    return 1, spec
+                end
+                local detail_item_data = {}
+                for _,cell in ipairs(group) do
+                    local strTableName = "TN_SKU"
+                    local strFieldList = '["S_UDF01"]'
+                    local strCondition =string.format("S_STORER='%s' AND S_ITEM_CODE='%s'",inboundData.storerId,cell.skuId)
+                    nRet, strRetInfo=mobox.queryTable(strLuaDEID,strTableName, strFieldList,1, strCondition, "")
+                    if (nRet ~= 0) then
+                        return 1,"鏌ヨSKU淇℃伅澶辫触!"..strRetInfo
+                    end
+                    local sku_info = json.decode(strRetInfo)
+                    if not sku_info or #sku_info == 0 then
+                        return 1,"SKU淇℃伅涓嶅瓨鍦�..cell.skuId
+                    end
+                    local sudf01 = sku_info[1].S_UDF01
+
+                    local item_detail 
+                    item_detail = m3.AllocObject2( strLuaDEID, "INB_Pallet_Detail")
+                    item_detail.S_CNTR_CODE = cid
+                    local seg = lua.split(cell.boxCode, '-' )
+                    if ( #seg ~= 2 ) then
+                        return 1,"鏂欐牸鍙锋牸寮忛敊璇�..cell.boxCode
+                    end
+                    item_detail.S_CELL_NO =spec.."-".. lua.StrToNumber(seg[2])
+                    item_detail.S_CELL_CODE=cell.boxCode
+                    item_detail.S_ITEM_CODE = cell.skuId
+                    item_detail.S_ITEM_NAME = cell.skuId
+                    item_detail.S_ITEM_STATE=cell.skuStatus
+                    item_detail.S_STORER=inboundData.storerId
+                    item_detail.S_OWNER=inboundData.ownerId
+                    item_detail.F_QTY = cell.qty
+                    item_detail.S_UDF01=sudf01
+                    item_detail.S_UDF02=cell.registerNo
+                    item_detail.S_WMS_BN = cell.batchNo
+                    item_detail.S_BATCH_NO = cell.produceCode
+                    item_detail.D_PRD_DATE = cell.productDate
+                    item_detail.D_EXP_DATE = cell.expiryDate
+                    item_detail.S_BS_TYPE="GK_IN_TASK"
+                    item_detail.S_BS_NO=inboundData.taskId
+                    item_detail.N_BS_ROW_NO=cell.row_no
+
+                    table.insert(detail_item_data, item_detail)
+                end
+                nRet, strRetInfo = wms_pallet.Add_INB_Pallet_Detail( strLuaDEID, cid, detail_item_data,"GK_IN_TASK",inboundData.taskId)
+                if nRet ~= 0 then
+                    return 1,"鐢熸垚鐮佺洏淇℃伅澶辫触".. strRetInfo
+                end                     
+            end
+        end
+    end
+    return 0, ""
+end
+local function create_container(strLuaDEID,inboundData,items)
+    local nRet,strRetInfo
+    local by_pallet=group_by(items,"cid")
+    for cid, group in pairs(by_pallet) do
+        if cid~=nil and cid~="" then
+            if(group[1].boxCode~=nil and group[1].boxCode~="") then
+                local spec
+                nRet, spec = get_celltype(group,cid)
+                if nRet ~= 0 then
+                    lua.DebugEx(strLuaDEID, "create_container", group[1].boxCode.. "cid="..cid)
+                    return 1, spec
+                end
+            nRet, strRetInfo = wms.wms_GetConst("WMS_Default_CNTR_Type")
+                if (nRet ~= 0) then
+                    return 1, "鑾峰彇榛樿瀹瑰櫒绫诲瀷澶辫触锛�..strRetInfo
+                end
+                local container_type_info = strRetInfo
+                local strObjID
+                local strCondition =string.format("S_CODE='%s'",cid)
+                nRet,strObjID,strRetInfo=mobox.getDataObjAttrByKeyAttr(strLuaDEID,"Container",strCondition)
+                if nRet ~= 0 then   
+                    return 1,cid.."瀹瑰櫒涓嶅瓨鍦�"..strRetInfo
+                end
+                local update_container_obj={
+                {
+                    id = strObjID,
+                    attrs = {
+                        { attr = "S_CTD_CODE", value =container_type_info }, -- 鏂欑绫诲瀷
+                        { attr = "S_SPEC", value = spec }, -- 鏂欑瑙勬牸
+                    }
+                }}
+                nRet, strRetInfo = mobox.updateDataObj( strLuaDEID, "Container", lua.table2str(update_container_obj) )
+                if (nRet ~= 0 ) then 
+                    return 1,"鏇存柊銆怌ontainer銆戝睘鎬уけ璐�"..strRetInfo
+                end    
+            end
+        end
+    end
+    return 0, ""
+end
+
+local function create_inbound_detail(strLuaDEID,detail)
+    local nRet, strRetInfo
+
+    local inbound_detail = m3.AllocObject( strLuaDEID,"Inbound_Detail")
+    inbound_detail.row_no=detail.row_no
+    inbound_detail.io_no=detail.io_no
+    inbound_detail.storer=detail.storer
+    inbound_detail.owner=detail.owner
+    inbound_detail.bs_row_no=detail.bs_row_no
+    inbound_detail.item_code=detail.item_code
+    inbound_detail.item_name=detail.item_name
+    inbound_detail.item_state=detail.item_state
+    inbound_detail.qty=detail.qty
+    inbound_detail.wms_bn=detail.wms_bn
+    inbound_detail.batch_no=detail.batch_no
+    inbound_detail.prd_date=detail.prd_date
+    inbound_detail.exp_date=detail.exp_date
+    inbound_detail.ext_attr1=detail.registerNo
+    inbound_detail.note=detail.note
+
+    local strTableName = "TN_SKU"
+    local strFieldList = '["S_UDF01"]'
+    local strCondition =string.format("S_STORER='%s' AND S_ITEM_CODE='%s'",detail.storer,detail.item_code)
+    nRet, strRetInfo=mobox.queryTable(strLuaDEID,strTableName, strFieldList,1, strCondition, "")
+    if (nRet ~= 0) then
+        return 1,"鏌ヨSKU淇℃伅澶辫触!"..strRetInfo
+    end
+    local sku_info = json.decode(strRetInfo)
+    if not sku_info or #sku_info == 0 then
+        return 1,"SKU淇℃伅涓嶅瓨鍦�..detail.item_code
+    end
+    inbound_detail.udf01 = sku_info[1].S_UDF01
+    inbound_detail.udf19=detail.sn
+    inbound_detail.udf20=detail.cntr_code
+
+    nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, inbound_detail)
+    if (nRet==nil or nRet ~= 0 ) then
+        return 1, "鍒涘缓绯荤粺鍏ュ簱鍗曟槑缁嗗け璐ワ紒"..strRetInfo.."no= "..detail.io_no
+    end
+    return 0, ""
+end 
+
+local function gk_create_inbound_detail(strLuaDEID,inboundData, inboundItem,index)
+    local nRet, strRetInfo
+
+    local inbound_detail = m3.AllocObject( strLuaDEID,"GK_IN_TASK_Detail")
+    inbound_detail.row_no=index
+    inbound_detail.io_no=inboundData.taskId
+    inbound_detail.storer=inboundData.storerId
+    inbound_detail.owner=inboundData.ownerId
+    inbound_detail.bs_row_no=inboundItem.orderItemId
+    inbound_detail.item_code=inboundItem.skuId
+    inbound_detail.item_name=inboundItem.skuId
+    inbound_detail.item_state=inboundItem.skuStatus
+    inbound_detail.qty=lua.Get_NumAttrValue(inboundItem.qty)
+    inbound_detail.wms_bn=inboundItem.batchNo
+    inbound_detail.batch_no=inboundItem.produceCode
+    inbound_detail.prd_date=inboundItem.productDate
+    inbound_detail.exp_date=inboundItem.expiryDate
+    inbound_detail.register_no=inboundItem.registerNo
+    inbound_detail.cntr_code=inboundItem.cid
+    inbound_detail.cell_no=inboundItem.boxCode
+    inbound_detail.sn=inboundItem.sn
+
+    nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, inbound_detail)
+    if (nRet==nil or nRet ~= 0 ) then
+        return 1, "鍒涘缓鍏ュ簱鍗曟槑缁嗗け璐ワ紒"..strRetInfo.."no= "..inboundData.taskId
+    end
+
+    if inboundItem.boxCode==nil or inboundItem.boxCode=="" then
+         nRet, strRetInfo=create_inbound_detail(strLuaDEID,inbound_detail)
+        if (nRet==nil or nRet ~= 0 ) then
+            return 1, "鍒涘缓绯荤粺鍏ュ簱鍗曟槑缁嗗け璐ワ紒"..strRetInfo.."no= "..inboundData.taskId
+        end
+    end
+   
+    return 0, ""
+end 
+
+local function create_inbound(strLuaDEID, gk_inbound)
+   local nRet, strRetInfo
+
+   local inbound = m3.AllocObject( strLuaDEID,"Inbound_Order")
+   inbound.no=gk_inbound.no
+   inbound.b_state=0
+   inbound.factory=gk_inbound.factory
+   inbound.wh_code=gk_inbound.wh_code
+   inbound.bs_type=gk_inbound.bs_type
+   inbound.bs_no=gk_inbound.bs_no
+   inbound.asn_no=gk_inbound.asn_no
+   inbound.op_date=gk_inbound.op_date
+   inbound.priority=gk_inbound.priority
+   inbound.note=gk_inbound.note
+   
+    nRet, strRetInfo = m3.CreateDataObj(strLuaDEID, inbound)
+   if (nRet==nil or nRet ~= 0 ) then
+       return 1,  "鍒涘缓绯荤粺鍏ュ簱鍗曞け璐ワ紒"..strRetInfo.."no= "..gk_inbound.no
+   end
+
+    return 0,""
+end
+
+local function gk_create_inbound(strLuaDEID, inboundData,emptyCellCount)
+   local nRet, strRetInfo
+
+   local inbound = m3.AllocObject( strLuaDEID,"GK_IN_TASK")
+   inbound.no=inboundData.taskId
+   inbound.b_state=0
+   nRet, strRetInfo = wms.wms_GetConst("WMS_Default_Factory")
+    if (nRet ~= 0) then
+         return 1, "鑾峰彇榛樿宸ュ巶澶辫触锛�..strRetInfo
+    end
+   inbound.factory=strRetInfo
+   nRet, strRetInfo = wms.wms_GetConst("WMS_Default_Warehouse")
+   if (nRet ~= 0) then
+        return 1, "鑾峰彇榛樿浠撳簱澶辫触锛�..strRetInfo
+   end
+   inbound.wh_code=strRetInfo
+   inbound.bs_type=inboundData.taskType
+   inbound.bs_no=inboundData.orderNo
+   inbound.asn_no=inboundData.asnNo
+   inbound.op_date=inboundData.orderDate
+   inbound.priority=inboundData.priority
+   inbound.source_no=inboundData.sourceBillNo
+   inbound.note=inboundData.memo
+   
+   local detailItems = inboundData.TaskCreation_TB_ITEM
+   local items={}
+   if detailItems==nil then
+       return 1, "鍏ュ簱鍗曟槑缁嗕负绌�
+   end
+   if detailItems[1]==nil then
+        items={detailItems}
+   else
+        items=detailItems
+   end
+   if items==nil or items[1]==nil then
+       return 1, "鍏ュ簱鍗曟槑缁嗕负绌�
+    else
+        local index=1
+        for index, item in ipairs(items) do
+            --鍒涘缓鍏ュ簱鍗曟槑缁�+            item.row_no=index
+             nRet, strRetInfo = gk_create_inbound_detail(strLuaDEID,inboundData,item,index)
+             if (nRet==nil or nRet ~= 0 ) then
+                return 1, "鍒涘缓鍏ュ簱鍗曟槑缁嗗け璐ワ紒"..strRetInfo.."no= "..inboundData.taskId
+             end
+        end
+    end
+
+    inbound.good_type_num=goods_count(items)
+    inbound.total_qty=sku_count(items)
+    nRet, inbound = m3.CreateDataObj(strLuaDEID, inbound)
+   if (nRet==nil or nRet ~= 0 ) then
+       return 1,  "鍒涘缓鍏ュ簱鍗曞け璐ワ紒"..inbound.."no= "..inboundData.taskId
+   end
+
+    --鍒涘缓绯荤粺鍏ュ簱鍗�+    if emptyCellCount>0 then
+         nRet, strRetInfo =create_inbound(strLuaDEID,inbound)
+        if (nRet==nil or nRet ~= 0 ) then
+            return 1, "鍒涘缓绯荤粺鍏ュ簱鍗曞け璐ワ紒"..strRetInfo.."no= "..inboundData.taskId
+        end
+    end
+
+    --鍒涘缓鍏ュ簱鍗曠爜鐩�+    nRet, strRetInfo =create_inbound_pallet(strLuaDEID,inboundData,items)
+    if (nRet==nil or nRet ~= 0 ) then
+        return 1, "鍒涘缓鐮佺洏鏄庣粏澶辫触锛�..strRetInfo.."no= "..inboundData.taskId
+    end
+    
+    --鍒涘缓瀹瑰櫒鏂欐牸淇℃伅
+    nRet, strRetInfo = create_container(strLuaDEID,inboundData,items)
+    if (nRet==nil or nRet ~= 0 ) then
+        return 1, "鍒涘缓瀹瑰櫒澶辫触锛�..strRetInfo.."no= "..inboundData.taskId
+    end
+
+    return 0,""
+end
+
+function Inbound_Sync(strLuaDEID)
+    local nRet, strRetInfo
+    local err_msg
+    
+    --m3.PrintLuaDEInfo(strLuaDEID)
+
+    local soap_xml
+    nRet,soap_xml=mobox.getCurEditDataPacket(strLuaDEID)
+    if ( nRet ~=0 ) then 
+        return_value(strLuaDEID, false,  "鏃犳硶鑾峰彇鏁版嵁鍖�!"..soap_xml)
+        return
+    end
+    local parsed_data
+    nRet, parsed_data = xml.parse(soap_xml)
+    if ( nRet ~= 0 ) then
+        return_value(strLuaDEID, false, "鎺ュ彛杈撳叆鐨刋ML鏍煎紡闈炴硶!")
+        return
+    end
+    
+    local inboundItems=parsed_data.Envelope.Body.InTaskCreationReq.TaskCreation_Input.InputParameters.TaskCreation_TB
+    local inboundSet={}
+    if inboundItems==nil then
+        return_value(strLuaDEID, false, "鎺ュ彛杈撳叆鐨刋ML鏍煎紡闈炴硶!")
+        return
+    end
+    if inboundItems[1]==nil then
+        inboundSet={inboundItems}
+    else
+        inboundSet=inboundItems
+    end
+
+    for i, inboundData in ipairs(inboundSet) do
+         if inboundData.TaskCreation_TB_ITEM==nil then
+            err_msg = "鍏ュ簱鏄庣粏涓虹┖"
+            return_value(strLuaDEID, false, err_msg)
+            return
+        end
+
+          --鍒ゆ柇InBound鏄惁瀛樺湪,鍙栨秷鐘舵�鍚庨潰鑰冭檻
+        local id
+        local strCondition =string.format("S_NO='%s' AND N_B_STATE<>91",inboundData.taskId)
+        nRet,id,strRetInfo=mobox.getDataObjAttrByKeyAttr(strLuaDEID,"GK_IN_TASK",strCondition)
+        if nRet==0 then
+            err_msg = "鍏ュ簱鍗曞彿宸插瓨鍦紒"..inboundData.taskId
+            return_value(strLuaDEID, true, err_msg)
+            return
+        end
+
+        --鍒ゆ柇鏂欑鏄惁瀛樺湪锛屼笉瀛樺湪鎷掔粷
+        local detailItems = inboundData.TaskCreation_TB_ITEM
+        local items={}
+        if detailItems==nil then
+            return 1, "鍏ュ簱鍗曟槑缁嗕负绌�
+        end
+        if detailItems[1]==nil then
+            items={detailItems}
+        else
+            items=detailItems
+        end
+        local by_pallet=group_by(items,"cid")
+        local emptyCellCount=0
+        for cid, group in pairs(by_pallet) do
+            for _,cell in ipairs(group) do
+                if cell.boxCode==nil or cell.boxCode=="" then
+                    emptyCellCount=emptyCellCount+1
+                end
+            end
+            if cid~=nil and cid~="" then
+                --鍒ゆ柇鏂欑鏄惁瀛樺湪
+                local strCondition =string.format("S_CODE='%s'",cid)
+                nRet,strRetInfo=mobox.existThisData(strLuaDEID,"Container",strCondition)
+                if nRet~=0 then
+                    err_msg = "鏌ヨ鏁版嵁鍑洪敊锛�..cid
+                    return_value(strLuaDEID, false, err_msg)
+                    return
+                end
+                if strRetInfo=="no" then
+                    err_msg = "鏂欑涓嶅瓨鍦紒"..cid
+                    return_value(strLuaDEID, false, err_msg)
+                    return
+                end
+                --鍒ゆ柇鏂欑鏄惁瀹屾垚鍏ュ簱
+                 local strCondition =string.format("S_CNTR_CODE='%s' AND N_B_STATE NOT IN(30,40)",cid)
+                nRet,strRetInfo=mobox.existThisData(strLuaDEID,"Inbound_Palletization",strCondition)
+                if nRet~=0 then
+                    err_msg = "鏌ヨ鏁版嵁鍑洪敊锛�..cid
+                    return_value(strLuaDEID, false, err_msg)
+                    return
+                end
+                if strRetInfo=="yes" then
+                    err_msg = "璇ユ枡绠辩爜鐩樻暟鎹湭瀹屾垚锛�..cid
+                    return_value(strLuaDEID, false, err_msg)
+                    return
+                end
+                --鍒ゆ柇鏂欑鏄惁瀛樺湪搴撳瓨
+                strCondition=string.format("S_CNTR_CODE='%s' AND F_QTY>0",cid)
+                nRet,strRetInfo=mobox.existThisData(strLuaDEID,"INV_Detail",strCondition)
+                if nRet~=0 then
+                    err_msg = "鏌ヨ鏁版嵁鍑洪敊锛�..cid
+                    return_value(strLuaDEID, false, err_msg..strRetInfo)
+                    return
+                end
+                if strRetInfo=="yes" then
+                    lua.DebugEx(strLuaDEID, "鏂欑瀛樺湪搴撳瓨")
+                    err_msg = "鏂欑瀛樺湪搴撳瓨"..cid
+                    return_value(strLuaDEID, false, err_msg..strRetInfo)
+                    return
+                end
+            end
+        end
+
+        nRet,err_msg= gk_create_inbound(strLuaDEID, inboundData,emptyCellCount)
+        if (nRet==nil or nRet~=0) then
+            return_value(strLuaDEID, false, err_msg)
+        else
+            return_value(strLuaDEID, true, "")
+        end
+    end
+end
\ No newline at end of file
diff --git a/lua_code/Lua/GK-API-06-Outbound_Sync.lua b/lua_code/Lua/GK-API-06-Outbound_Sync.lua
new file mode 100644
index 0000000..f888ff2
--- /dev/null
+++ b/lua_code/Lua/GK-API-06-Outbound_Sync.lua
@@ -0,0 +1,187 @@
+--[[ 
+    缂栫爜: GK-API-06
+    鍚嶇О: 鍑哄簱鍗曞垱寤烘帴鍙�+    浣滆�: yuanfeng
+    鏃ユ湡: 2025-7-24
+
+    鍏ュ彛鍑芥暟锛�Outbound_Sync
+    鍔熻兘璇存槑:
+        1. 鎺ユ敹涓婃父绯荤粺鐨勫叆搴撲换鍔ML鏁版嵁
+        2. 妫�煡鍏ュ簱鍗曟槸鍚﹀凡瀛樺湪
+        3. 鍒涘缓Outbound_Order涓昏〃鍜孫utbound_Detail瀛愯〃璁板綍
+        4. 杩斿洖澶勭悊缁撴灉
+    鏇存柊
+        2025-07-12 V1.1 鏂板鍑哄簱鍗曚富琛紝state 榛樿涓�"瀹氱増"
+        
+    杈撳叆XML绀轰緥:
+--]] wms_base = require("wms_base")
+xml = require("oi_base_xml")
+xml2lua = require("xml2lua")
+
+-- 鍒涘缓鍑哄簱鍗曚富琛ㄨ褰�+local function create_outbound_order(strLuaDEID, order_data)
+
+    local nRet1, CONST_FACTORY = wms_base.Get_sConst2("WMS_Default_Factory")
+    -- 榛樿宸ュ巶鏍囪瘑
+    local nRet2, CONST_WH = wms_base.Get_sConst2("WMS_Default_Warehouse")
+    if nRet1 ~= 0 or nRet2 ~= 0 then
+        return 1, "鑾峰彇宸ュ巶鎴栦粨搴撳父閲忓け璐�
+    end
+
+    local order = m3.AllocObject(strLuaDEID, "Outbound_Order")
+    order.no = order_data.taskId
+    order.bs_type = order_data.taskType
+    order.bs_no = order_data.orderNo
+    order.wave_no = order_data.waveId
+    order.op_date = order_data.orderDate
+    order.priority = order_data.priority
+    order.note = order_data.memo or ""
+    order.wh_code = CONST_WH
+    order.area_code = ""
+    order.factory = CONST_FACTORY
+    -- 鏂板鍑哄簱鍗曚富琛ㄧ姸鎬佸瓧娈�+    order.state = "瀹氱増"
+    -- 鏂板璐т富缂栫爜
+    order.storer = order_data.storerId
+    -- 鏂板婧愬崟鍙�+    order.source_no = order_data.sourceBillNo
+    -- lua.DebugEx(strLuaDEID, "棰勫垱寤哄嚭搴撳崟涓昏〃", order)
+    local nRet, result = m3.CreateDataObj(strLuaDEID, order)
+    return nRet, result
+end
+
+-- 鍒涘缓鍑哄簱鍗曟槑缁嗚褰�+-- @param:item_date 鏄紶鍏ョ殑鐗╂枡鏄庣粏瀹炰綋鏁版嵁
+-- @param:order_data 浼犲叆鍑哄簱鍗曚富琛ㄥ疄浣撴暟鎹�+local function create_outbound_detail(strLuaDEID, order_no, item_data, order_data)
+    local detail = m3.AllocObject(strLuaDEID, "Outbound_Detail")
+    -- 鏄庣粏琛ㄥ瓧娈垫槧灏�+    detail.oo_no = order_no
+    detail.storer = order_data.storerId
+    detail.owner = order_data.ownerId
+    detail.bs_row_no = item_data.orderItemId -- 璁㈠崟琛屽彿
+    detail.item_code = item_data.skuId
+    detail.item_state = item_data.skuStatus
+    detail.qty = lua.Get_NumAttrValue(item_data.qty)
+    detail.batch_no = item_data.produceCode
+    detail.wms_bn = item_data.batchNo
+    detail.prd_date = item_data.productDate
+    detail.exp_date = item_data.expiryDate
+    detail.udf01 = item_data.registerNo or ""
+    detail.udf02 = item_data.cid or ""
+    -- lua.DebugEx(strLuaDEID, "棰勫垱寤哄嚭搴撳崟鏄庣粏", detail)
+    local nRet, result = m3.CreateDataObj(strLuaDEID, detail)
+    return nRet, result
+end
+function Outbound_Sync(strLuaDEID)
+    local nRet, strRetInfo, err_msg
+    local soap_xml, parsed_data, task_data, input_params, task_tb, order_no
+    local strCondition, id, task_items
+    local isStop = 0
+    local err = {}
+    local items = {}
+
+    m3.PrintLuaDEInfo(strLuaDEID)
+    local result = {
+        flag = "success",
+        code = "0",
+        message = "鎴愬姛"
+    }
+    -- lua.Debug(strLuaDEID, debug.getinfo(1), "鍑哄簱鍗曟暟鎹�", result)
+
+    -- 1. 鑾峰彇鎺ュ彛杈撳叆鏁版嵁
+
+    nRet, soap_xml = mobox.getCurEditDataPacket(strLuaDEID)
+    if nRet ~= 0 then
+        -- lua.Stop(strLuaDEID, "鏃犳硶鑾峰彇鏁版嵁鍖� " .. soap_xml)
+        result.flag = "failure"
+        result.code = "1"
+        result.message = "鏃犳硶鑾峰彇鏁版嵁鍖� "
+        goto api_call_return
+
+        -- return
+    end
+
+    -- 2. 瑙f瀽XML
+
+    nRet, parsed_data = xml.parse(soap_xml)
+    if nRet ~= 0 then
+        -- lua.Stop(strLuaDEID, "鎺ュ彛杈撳叆鐨刋ML鏍煎紡闈炴硶!")
+        result.flag = "failure"
+        result.code = "2"
+        result.message = "鎺ュ彛杈撳叆鐨刋ML鏍煎紡闈炴硶: "
+        goto api_call_return
+        -- return
+    end
+
+    -- 3. 鎻愬彇浠诲姟鏁版嵁
+    task_data = parsed_data.Envelope.Body.InTaskCreationReq.TaskCreation_Input
+    input_params = task_data.InputParameters
+    task_tb = input_params.TaskCreation_TB
+
+    -- 4. 妫�煡鍑哄簱鍗曟槸鍚﹀凡瀛樺湪
+    order_no = task_tb.taskId
+    strCondition = string.format("S_NO = '%s'", order_no)
+    nRet, id, strRetInfo = mobox.getDataObjAttrByKeyAttr(strLuaDEID, "Outbound_Order", strCondition)
+    -- lua.Debug(strLuaDEID, debug.getinfo(1), "鏌ヨ鍑烘潵鐨勫嚭搴撳崟鏁版嵁:", strRetInfo)
+
+    if nRet > 1 then
+        result.flag = "failure"
+        result.code = "3"
+        result.message = "妫�煡鍑哄簱鍗曟槸鍚﹀瓨鍦ㄦ椂鍑洪敊: " .. strRetInfo
+        goto api_call_return
+    elseif nRet == 0 then
+        result.flag = "failure"
+        result.code = "4"
+        result.message = "鍑哄簱鍗曞凡瀛樺湪 "
+        goto api_call_return
+    end
+    -- 5. 鍒涘缓鍑哄簱鍗曚富琛�+    nRet, strRetInfo = create_outbound_order(strLuaDEID, task_tb)
+    if nRet ~= 0 then
+        -- lua.Stop(strLuaDEID, "鍒涘缓鍑哄簱鍗曚富琛ㄥけ璐�" .. strRetInfo)
+        result.flag = "failure"
+        result.code = "5"
+        result.message = "鍒涘缓鍑哄簱鍗曚富琛ㄥけ璐�" .. strRetInfo
+        isStop = 3
+        goto api_call_return
+        -- return
+    end
+
+    -- 6. 澶勭悊鏄庣粏鏁版嵁
+    task_items = task_tb.TaskCreation_TB_ITEM
+
+    -- 鎯呭喌2锛氬鏉℃槑缁嗭紙鏁扮粍褰㈠紡锛�+    if task_items[1] ~= nil then
+        items = task_items
+        -- 鎯呭喌3锛氬崟鏉℃槑缁嗭紙闈炴暟缁勫舰寮忥級
+    else
+        items = {task_items}
+    end
+
+    for i, item in ipairs(items) do
+        nRet, strRetInfo = create_outbound_detail(strLuaDEID, order_no, item, task_tb)
+        if nRet ~= 0 then
+            err_msg = string.format("鍒涘缓鍑哄簱鍗曟槑缁嗗け璐�琛屽彿:%d): %s", item.orderItemId, strRetInfo)
+            result.flag = "failure"
+            result.code = "5"
+            result.message = err_msg
+            isStop = 3
+            goto api_call_return
+        end
+    end
+    ::api_call_return::
+    -- 7. 杩斿洖澶勭悊缁撴灉
+    -- local result = {
+    -- flag = nErr > 0 and "failure" or "success", 
+    -- code = nErr,
+    -- message = nErr > 0 and table.concat(err, "; ") or "鎴愬姛", 
+    -- }
+    local xml_result = xml.json_to_xml(result, "response")
+
+    mobox.returnValue(strLuaDEID, 0, xml_result, isStop)
+
+    -- m3.EPI_Return(strLuaDEID, result)
+    -- ApiReturn(strLuaDEID, 0, result, isStop)
+
+end
diff --git a/lua_code/Lua/GK-API-07.lua b/lua_code/Lua/GK-API-07-Order_Cancel.lua
similarity index 98%
rename from lua_code/Lua/GK-API-07.lua
rename to lua_code/Lua/GK-API-07-Order_Cancel.lua
index 6f1913f..8fcde56 100644
--- a/lua_code/Lua/GK-API-07.lua
+++ b/lua_code/Lua/GK-API-07-Order_Cancel.lua
@@ -1,25 +1,17 @@
----
---- Created by wsz.
---- DateTime: 2025/5/15 涓嬪崍3:31
----
-
 --[[
  缂栫爜: GK-API-07
  鍚嶇О: 璁㈠崟鍙栨秷鎺ュ彛
  浣滆�: wsz
  鍏ュ彛鍑芥暟锛歄rder_Sync
- 鍔熻兘璇存槑: 鎺ユ敹鎶ユ枃鍒涘缓 Order_Hold 瀹炰綋  锛屽浜庡凡瀛樺湪鐨勬暟鎹棤鏉′欢鏇存柊锛岃繑鍥炴姤鏃犻渶鍒涘缓杩樿揣鍗�锛涙柊澧炵殑鏁版嵁璁剧疆闇�鍒涘缓杩樿揣鍗�+ 鍔熻兘璇存槑: 鎺ユ敹鎶ユ枃鍒涘缓 Order_Hold 瀹炰綋锛屽浜庡凡瀛樺湪鐨勬暟鎹棤鏉′欢鏇存柊锛岃繑鍥炴姤鏃犻渶鍒涘缓杩樿揣鍗�锛涙柊澧炵殑鏁版嵁璁剧疆闇�鍒涘缓杩樿揣鍗�  鍙樻洿鍘嗗彶:v0.0.1
-
 娉ㄦ剰锛�     1銆佹寜鐓ф鎶ユ枃褰㈠紡,杩欏簲鏄崟鏉″彂閫�     2銆佹姤鏂囪В鏋愰」灏戜簡鏉ユ簮鍗曞彿銆佹嫤鎴被鍨嬨�锛氬瓨鍌ㄦ椂 鏉ユ簮鍗曞彿涓嶅~锛屾嫤鎴被鍨嬪~Interface
     3銆乶eedReturnOrder 浠�鏍规嵁鍑哄簱鍗曠殑鐘舵�浼氭秹鍙婂埌
-
    璁㈠崟绫诲瀷锛�asn 鍏ュ簱璁㈠崟 so鍑哄簱璁㈠崟 inventory 鐩樼偣鍗�    涓夎�鍗曟嵁鐨勪富閿畁o-涓庢姤鏂囩殑taskId 瀵瑰簲
    鍏ュ簱鍗曞拰鐩樼偣鍗曞凡鎵ц涓嶅厑璁稿彇娑堬紝鍑哄簱鍗曡鍗曟湭瀹屾垚閮藉厑璁稿彇娑堬紝鍏佽鍙栨秷鎵嶆彃鍏rder_Hold
-
 -----------------------------------------
 
 鍏ュ簱鍗�Inbound_Order   no | b_state
diff --git a/lua_code/Lua/GK-API-08-Outbound_Priority_Chg.lua b/lua_code/Lua/GK-API-08-Outbound_Priority_Chg.lua
new file mode 100644
index 0000000..0b5f33b
--- /dev/null
+++ b/lua_code/Lua/GK-API-08-Outbound_Priority_Chg.lua
@@ -0,0 +1,334 @@
+--- Created by w1832.
+--- DateTime: 2025/5/20 涓婂崍8:57
+---
+
+--[[
+ 缂栫爜: GK-API-08
+ 鍚嶇О: Outbound_Priority_Change
+ 浣滆�:wsz
+ 鍏ュ彛鍑芥暟锛歄utbound_Priority_Change
+ 鍔熻兘璇存槑:鏇存柊鍙戣揣鍗�Shipping_Order 浼樺厛绾э紝宸插垎閰嶅悗涓嶅厑璁告洿鏂�+ 鍙樻洿鍘嗗彶:
+v0.0.1 鍒濆
+
+v0.0.2  CLSID 涓哄嚭搴撳崟 Outbound_Order锛岄潪Shipping_Order鍙戣揣鍗�+ 娉ㄦ剰锛�+ 1銆佹鎶ユ枃缁撴瀯搴旀槸鍗曟潯鎺ㄩ�
+ 2銆丼_BS_NO鏌ュ埌鐨勬暟鎹笉涓�畾鍞竴锛屽悓S_BS_NO鏁版嵁鐨凬_B_STATE鐘舵�涔熶笉涓�畾鍏ㄩ儴婊¤冻瑕佹眰锛屼粎澶勭悊婊¤冻鏉′欢鐨勬暟鎹�+
+v0.0.3 淇敼鏄犲皠瀛楁 S_BS_NO -> S_NO
+
+v0.0.4 閲嶅洖鏄犲皠瀛楁 S_NO -> S_BS_NO 鐜伴�杈戜繚鎸佸湪v0.0.2涓哄噯
+
+ --]]
+
+
+ json = require("json")
+ mobox = require("OILua_JavelinExt")
+ m3 = require("oi_base_mobox")
+
+ xml = require("oi_base_xml")
+
+--- 瀹炰綋鏍囪瘑-鍑哄簱璁㈠崟浼樺厛绾ц皟鏁存帴鍙�+local CLSID_OutboundOrder = "Outbound_Order"
+-- 琛ㄥ悕
+local TB_NAME_OutboundOrder = "TN_Outbound_Order"
+
+local CLSID_OutboundOrder_desc = "鍑哄簱璁㈠崟浼樺厛绾ц皟鏁存帴鍙�
+
+local luaDEID
+
+
+
+--鏍规爣绛�+local RootTag =  "response"
+
+
+
+
+-- 绠�寲 debug.info璁板綍
+local function DebugInfo(desc, param)
+    if param == nil then
+        param = ""
+    end
+    lua.Debug(luaDEID, debug.getinfo(1), desc, param)
+end
+
+
+--[[
+-- 鎵ц鎴愬姛
+]]
+local function result_success(strLuaDEID)
+
+    local result = {}
+    result.flag = "success" -- success|failure
+    result.code = 0
+    result.message = ""
+
+    do
+        local nRet = mobox.returnValue(strLuaDEID, 1, xml.json_to_xml(result,RootTag), result.code)
+        if nRet ~= 0 then
+            lua.Error(strLuaDEID, debug.getinfo(1), 'result_success-鎵цmobox.returnValue澶辫触 ' .. nRet)
+        end
+    end
+end
+
+--[[
+-- 浜嬪姟鍥炴粴-杩斿洖淇℃伅鍚庣粓姝㈡墽琛�+]]
+local function result_transaction_back(strLuaDEID, msg)
+
+    -- 鍥炴粴褰撴澶勭悊
+    lua.Stop(strLuaDEID, msg)
+    --
+    --local result = {}
+    --result.flag = "failure" -- success|failure
+    --result.code = 5
+    --result.message = msg
+    --
+    --local xmlstr = xml.json_to_xml(result)
+    --
+    --do
+    --    local nRet = mobox.returnValue(strLuaDEID, 1, xmlstr, result.code)
+    --    if nRet ~= 0 then
+    --        lua.Error(strLuaDEID, debug.getinfo(1), 'result_transaction_back-鎵цmobox.returnValue澶辫触 ' .. nRet)
+    --    end
+    --end
+    error(msg, 0)
+    -- lua.Error(strLuaDEID, debug.getinfo(1), xmlstr)
+end
+
+
+--[[
+param
+    CLSID:鐩爣瀹炰緥calssid
+    id鐩爣鏁版嵁鐨凷_ID
+    temp:寰呮洿鏂板瓧娈靛璞★紝lua灞炴�table
+
+
+--]]
+local function butchUpdateData(strLuaDEID,CLSID,id,temp)
+
+    local nRet, str_data_attrset = mobox.luaJsonToObjAttrs(CLSID_OutboundOrder, json.encode(temp))
+    if nRet ~= 0 then
+        result_transaction_back(strLuaDEID, "luaJsonToObjAttrs 鍑芥暟 杞寲鏍煎紡澶辫触" .. nRet .. str_data_attrset)
+    end
+    -- 鍙嶅簭鍒楀寲涓虹洰鏍囨牸寮�+    local attrValueObj = json.decode(str_data_attrset)
+
+    -- 缁勮鎵归噺鏇存柊鐨勬暟鎹牸寮�+    local updateObj = {}
+
+    local updateObj_item = {}
+    updateObj_item.id = id
+    updateObj_item.attrs = attrValueObj
+    table.insert(updateObj, updateObj_item)
+
+    local updateStrDataJson = lua.table2str(updateObj)
+    lua.Debug(strLuaDEID, debug.getinfo(1), CLSID .. "update鍑嗗瑕嗙洊宸叉湁鏁版嵁", updateStrDataJson)
+    local nRet, strRetInfo = mobox.updateDataObj(strLuaDEID, CLSID, updateStrDataJson)
+    if (nRet ~= 0) then
+        result_transaction_back(strLuaDEID, string.format(CLSID.."鏇存柊鎿嶄綔澶辫触锛乧ode锛�s锛宮sg锛�s", nRet, strRetInfo))
+    end
+
+end
+
+
+--[[
+涓氬姟鏁版嵁澶勭悊
+1銆佹煡璇� orderNo锛歋_BS_NO 璁板綍  鏉ユ簮鍗曞彿闈炰富閿紝鍙兘瀛樺湪澶氭潯鏁版嵁
+2.鍒ゆ柇 N_B_STATE 鐘舵�  鏇存柊鍑哄簱鍗�Outbound_Order 浼樺厛绾э紝宸插垎閰嶅悗涓嶅厑璁告洿鏂�N_B_STATE>=25 AND N_B_STATE<=55)
+
+]]
+local function bussHandle(strLuaDEID, dataSet)
+
+    local strCondition
+    do
+        local filters = {}
+        table.insert(filters, string.format([[ %s = '%s' ]], "S_BS_NO", lua.Get_StrAttrValue(dataSet.orderNo)))
+        strCondition = table.concat(filters, " and ")
+        lua.Debug(strLuaDEID, debug.getinfo(1), "filters-缁勮鐨凷hipping_Order鐨剋here鏉′欢", strCondition)
+    end
+
+
+    -- 鏌ユ壘鎬绘暟閲�+    local nRetCount
+    do
+        local nRet, nCount = mobox.getDataObjCount(strLuaDEID, CLSID_OutboundOrder, strCondition)
+        if nRet == 0 then
+            nRetCount = nCount
+            DebugInfo(string.format("%s-鏌ヨ鎬绘暟閲忎负%s", CLSID_OutboundOrder, nCount))
+        else
+            result_transaction_back(strLuaDEID, string.format("鏌ヨ鐩爣鏁版嵁澶辫触锛宑ode锛�s锛宮sg锛�s", nRet, nCount))
+        end
+
+        if nCount == "0" then
+            result_transaction_back(strLuaDEID, dataSet.orderNo .. "鏌ユ壘涓嶅埌鎶ユ枃瀵瑰簲鐨勫嚭搴撳崟鏁版嵁锛�)
+        end
+    end
+
+
+    -- 鏌ヨ鐩爣鏁版嵁, 瀛樺偍lua鏁扮粍锛屽唴閮ㄤ负鏁版嵁搴撳瓧娈垫牸寮忓璞�+    local datas = {}
+    do
+        local strFieldList = { "S_ID", "S_NO", "S_BS_NO", "N_PRIORITY", "S_NOTE", "N_PRIORITY" }
+        -- 杩斿洖 json鍨�str锛屾牸寮�[ { "attr1": "xxx", "attr2": "xxx1", 鈥�}, 鈥�+        local nRet, strRetInfo = mobox.queryTable(strLuaDEID, TB_NAME_OutboundOrder, json.encode(strFieldList), nRetCount, strCondition)
+        if nRet == 0 then
+            DebugInfo(string.format("%s-queryTable鍑芥暟杩斿洖", CLSID_OutboundOrder), strRetInfo)
+            local tableData = json.decode(strRetInfo)
+            DebugInfo("tableData", tableData)
+
+            datas = tableData
+
+            --for n = 1, #tableData do
+            --    -- local nRet1, strObjJson = mobox.objAttrToObjJson(CLSID_ShippingOrder, tableData[n])
+            --    -- local nRet1, strObjJson = mobox.objJsonToLuaJson(CLSID_ShippingOrder, tableData[n])
+            --
+            --    if nRet1 == 0 then
+            --        table.insert(datas, strObjJson)
+            --    else
+            --        result_transaction_back(strLuaDEID, string.format("queryTable-objAttrToObjJson杞寲澶辫触锛宑ode锛�s锛宮sg锛�s", nRet1, strObjJson))
+            --    end
+            --end
+        else
+            result_transaction_back(strLuaDEID, string.format("queryTable鏌ヨ鐩爣鏁版嵁澶辫触锛宑ode锛�s锛宮sg锛�s", nRet, strRetInfo))
+        end
+    end
+
+    DebugInfo(string.format("%s-queryTable-鍙栧緱datas鏁版嵁", CLSID_OutboundOrder), datas)
+
+    -- 杩唬鏇存柊婊¤冻鏉′欢鐨勬暟鎹�+    for n = 1, #datas do
+
+        local b_state = lua.Get_NumAttrValue(datas[n].N_B_STATE)
+        local id = datas[n].S_ID
+        local flag = b_state >= 25 and b_state <= 55
+        DebugInfo("b_state", b_state)
+        DebugInfo("id", id)
+        DebugInfo("flag", flag)
+
+        if not flag then
+            -- 鎵ц鏇存柊
+            local temp = {}
+            temp.priority = dataSet.priority --浼樺厛绾�+            temp.note = dataSet.memo -- 澶囨敞
+
+            butchUpdateData(strLuaDEID, CLSID_OutboundOrder,id,temp)
+
+            --local nRet, str_data_attrset = mobox.luaJsonToObjAttrs(CLSID_ShippingOrder, json.encode(temp))
+            --if nRet ~= 0 then
+            --    result_transaction_back(strLuaDEID, "luaJsonToObjAttrs 鍑芥暟 杞寲鏍煎紡澶辫触" .. nRet .. str_data_attrset)
+            --end
+            ---- 鍙嶅簭鍒楀寲涓虹洰鏍囨牸寮�+            --local attrValueObj = json.decode(str_data_attrset)
+            --
+            ---- 缁勮鎵归噺鏇存柊鐨勬暟鎹牸寮�+            --local updateObj = {}
+            --
+            --local updateObj_item = {}
+            --updateObj_item.id = id
+            --updateObj_item.attrs = attrValueObj
+            --table.insert(updateObj, updateObj_item)
+            --
+            --local updateStrDataJson = lua.table2str(updateObj)
+            --lua.Debug(strLuaDEID, debug.getinfo(1), CLSID_ShippingOrder .. "update鍑嗗瑕嗙洊宸叉湁鏁版嵁", updateStrDataJson)
+            --local nRet, strRetInfo = mobox.updateDataObj(strLuaDEID, CLSID_ShippingOrder, updateStrDataJson)
+            --if (nRet ~= 0) then
+            --    result_transaction_back(strLuaDEID, string.format("鍙戣揣鍗曟洿鏂版搷浣滃け璐ワ紒code锛�s锛宮sg锛�s", nRet, strRetInfo))
+            --end
+        end
+
+    end
+
+end
+
+
+
+local function Outbound_Priority_Change_main(strLuaDEID)
+    -- 1.1 getxml
+    local soap_xml
+    do
+        local nRet, data = mobox.getCurEditDataPacket(strLuaDEID)
+        if (nRet ~= 0) then
+            result_transaction_back(strLuaDEID, "鏃犳硶鑾峰彇鏁版嵁鍖�datajson !" .. data)
+        end
+        soap_xml = data
+        lua.Debug(strLuaDEID, debug.getinfo(1), "GK-API-08xml鎶ユ枃", soap_xml)
+    end
+
+    -- 1.2 xml->luaobj
+    local parsed_data
+    do
+        local nRet, data = xml.parse(soap_xml)
+        if (nRet ~= 0) then
+            result_transaction_back(strLuaDEID, "鎺ュ彛杈撳叆鐨刋ML鏍煎紡闈炴硶!")
+        end
+        parsed_data = data
+    end
+
+    -- 1.3 鍙栧緱鍟嗗搧鎵规琛╥tem鐨則ableObj
+    local dataSet = parsed_data["Envelope"]["Body"]
+    ["OrderAdjustmentsReq"]
+    ["OrderAdjustments_Input"]
+    ["InputParameters"]
+    ["OrderAdjustments_TB"]
+
+    if nil == dataSet then
+        -- wms_base.Warning(strLuaDEID, 2, 201, CLSID_OutboundOrder_desc .. "-鏈В鏋愬埌soap鐩爣鑺傜偣!", json.encode(dataSet), "", CLSID_OutboundOrder_desc .. "-dataSet")
+        result_transaction_back(strLuaDEID, CLSID_OutboundOrder_desc .. "-鏈В鏋愬埌soap鐩爣鑺傜偣!")
+    elseif #dataSet == 0 then
+        -- 浠呭崟鏉℃暟鎹�+        lua.Debug(strLuaDEID, debug.getinfo(1), "鍗曟潯", dataSet)
+        bussHandle(strLuaDEID, dataSet)
+    else
+        for i = 1, #dataSet do
+            lua.Debug(strLuaDEID, debug.getinfo(1), "澶氭潯", "")
+            bussHandle(strLuaDEID, dataSet[i])
+        end
+    end
+
+    result_success(strLuaDEID)
+end
+
+
+--[[
+鍥哄畾-閿欒鎹曡幏澶勭悊
+]]
+local ERR
+local function errorHandler(err)
+    ERR = err
+    lua.Debug(luaDEID, debug.getinfo(1), "err-璁板綍", err)
+    return err
+end
+
+--[[ 鍏ュ彛鍑芥暟 ]]
+function Outbound_Priority_Change(strLuaDEID)
+
+    m3.PrintLuaDEInfo(strLuaDEID)
+
+    luaDEID = strLuaDEID
+    --Outbound_Priority_Change_main(strLuaDEID)
+    local success, result = xpcall(Outbound_Priority_Change_main, errorHandler, strLuaDEID)
+
+    if not success then
+
+
+        local result = {}
+        result.flag = "failure" -- success|failure
+        result.code = 5
+        result.message = ERR
+
+        local xmlstr = xml.json_to_xml(result,RootTag)
+
+        do
+            local nRet = mobox.returnValue(strLuaDEID, 1, xmlstr, result.code)
+            if nRet ~= 0 then
+                lua.Error(strLuaDEID, debug.getinfo(1), 'result_transaction_back-鎵цmobox.returnValue澶辫触 ' .. nRet)
+            end
+        end
+
+        -- lua.Error(strLuaDEID, debug.getinfo(1), ERR)
+    end
+
+end
\ No newline at end of file
diff --git a/lua_code/Lua/GK-API-09-Count_Pan_Sync.lua b/lua_code/Lua/GK-API-09-Count_Pan_Sync.lua
new file mode 100644
index 0000000..13961de
--- /dev/null
+++ b/lua_code/Lua/GK-API-09-Count_Pan_Sync.lua
@@ -0,0 +1,297 @@
+--[[
+ 缂栫爜: GK-API-09
+ 鍚嶇О: 鐩樼偣璁″垝鍚屾鎺ュ彛
+ 浣滆�: 琚佸嘲
+ 鍏ュ彛鍑芥暟锛欳ount_Pan_Sync
+ 鍔熻兘璇存槑: 璇ユ帴鍙f槸鍚屾鎺ュ彛锛�+    涓婃父绯荤粺璋冪敤璇ユ帴鍙e悗锛學ES鐨勫搷搴旀姤鏂噑uccess璇存槑WES宸茬粡灏嗚鎶ユ枃鎺ユ敹鎴愬姛;
+    闇�鍚屾鐩樼偣浠诲姟琛ㄥ拰鐩樼偣浠诲姟鏄庣粏琛▁ml缁撴瀯銆�+ 鍙樻洿鍘嗗彶:
+
+<soapenv:Envelope
+    xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
+    xmlns:v1="http://www.gkht.com/Inventory/INV/Ebs/Schemas/InventoryTasks/V1.0">
+    <soapenv:Header/>
+    <soapenv:Body>
+        <v1:InventoryTasksReq>
+            <v1:InventoryTasks_Input>
+                <v1:RESTHeader>
+                    <v1:NLSLanguage>SIMPLIFIED CHINESE</v1:NLSLanguage>
+                    <v1:Org_Id>0</v1:Org_Id>
+                </v1:RESTHeader>
+                <v1:InputParameters>
+                    <!-- 绗竴涓洏鐐逛换鍔�-->
+                    <v1:InventoryTasks_TB>
+                        <v1:taskId>TASK30000100</v1:taskId>
+                        <v1:inventoryMode>01</v1:inventoryMode>
+                        <v1:workMode>Manual</v1:workMode>
+                        <v1:MaintenanceNumber>10</v1:MaintenanceNumber>
+                        <v1:inventoryType>YH</v1:inventoryType>
+                        <v1:orderNo>YH100001</v1:orderNo>
+                        <v1:storerId>CGKHTY</v1:storerId>
+                        <v1:ownerId>CGKHTY</v1:ownerId>
+                        <v1:mtBeginDate>2025-05-06</v1:mtBeginDate>
+                        <v1:mtEndDate>2025-05-06</v1:mtEndDate>
+                        <!-- 绗竴涓换鍔$殑鏄庣粏鏁版嵁 -->
+                        <v1:InventoryTasks_TB_ITEM>
+                            <v1:orderItemId>100</v1:orderItemId>
+                            <v1:skuId>XR33201-2L080B</v1:skuId>
+                            <v1:qty>2</v1:qty>
+                            <v1:batchNo>PHI00000000000001309</v1:batchNo>
+                        </v1:InventoryTasks_TB_ITEM>
+                    </v1:InventoryTasks_TB>
+
+                    <!-- 绗簩涓洏鐐逛换鍔�-->
+                    <v1:InventoryTasks_TB>
+                        <v1:taskId>TASK300000101</v1:taskId>
+                        <v1:inventoryMode>02</v1:inventoryMode>
+                        <v1:workMode>Auto</v1:workMode>
+                        <v1:MaintenanceNumber>5</v1:MaintenanceNumber>
+                        <v1:inventoryType>PD</v1:inventoryType>
+                        <v1:orderNo>PD200001</v1:orderNo>
+                        <v1:storerId>GKHT</v1:storerId>
+                        <v1:ownerId>GKHT</v1:ownerId>
+                        <v1:mtBeginDate>2025-05-07</v1:mtBeginDate>
+                        <v1:mtEndDate>2025-05-07</v1:mtEndDate>
+                        <!-- 绗簩涓换鍔$殑鏄庣粏鏁版嵁 -->
+                        <v1:InventoryTasks_TB_ITEM>
+                            <v1:orderItemId>110</v1:orderItemId>
+                            <v1:skuId>ABC123</v1:skuId>
+                            <v1:qty>10</v1:qty>
+                            <v1:batchNo>BATCH2025001</v1:batchNo>
+                        </v1:InventoryTasks_TB_ITEM>
+                        <v1:InventoryTasks_TB_ITEM>
+                            <v1:orderItemId>111</v1:orderItemId>
+                            <v1:skuId>XYZ456</v1:skuId>
+                            <v1:qty>3</v1:qty>
+                            <v1:batchNo>BATCH2025002</v1:batchNo>
+                        </v1:InventoryTasks_TB_ITEM>
+                    </v1:InventoryTasks_TB>
+                </v1:InputParameters>
+            </v1:InventoryTasks_Input>
+        </v1:InventoryTasksReq>
+    </soapenv:Body>
+</soapenv:Envelope>
+
+鍝嶅簲绀轰緥锛�+<response>
+    <flag>success</flag>
+    <code>0</code>
+    <message>鎴愬姛</message>
+</response>
+]] --
+wms_base = require("wms_base")
+xml = require("oi_base_xml")
+mobox = require("OILua_JavelinExt")
+m3 = require("oi_base_mobox")
+wms = require("OILua_WMS")
+
+local filedMapping = {
+    ["璐у搧鐩樼偣"] = 1,
+    ["瀹瑰櫒鐩樼偣"] = 2,
+    ["璐т綅鐩樼偣"] = 3,
+    ["OVERALL鍏ㄧ洏"] = 4,
+    ["MT鍔ㄧ鐩樼偣"] = 5,
+    ["SPECIAL鎶界洏"] = 6,
+    ["YH"] = 7
+}
+
+-- 鍒涘缓缁熶竴杩斿洖缁撴灉(璋冩暣涓�涓弬鏁�
+function Create_result(flag, code, msg)
+    return {
+        flag = flag or "success",
+        code = code or "0",
+        message = msg or ""
+    }
+end
+
+function GK_Count_Pan_Sync(strLuaDEID)
+    -- 鍒濆鍖栨渶缁堢粨鏋�+    local FinalRes = Create_result()
+
+    -- 1. 鑾峰彇 xml 鏁版嵁鍖�+    local nRet, soap_xml = mobox.getCurEditDataPacket(strLuaDEID)
+    if nRet ~= 0 then
+        FinalRes = Create_result("failure", "201", "鏃犳硶鑾峰彇鏁版嵁鍖� " .. soap_xml)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "鑾峰彇鏁版嵁鍖呭け璐�, soap_xml)
+        return
+    end
+
+    lua.DebugEx(strLuaDEID, "鑾峰彇鍒扮殑鏁版嵁鍖�, soap_xml)
+
+    -- 2. 瑙f瀽 xml
+    local nRet, parsed_data = xml.parse(soap_xml)
+    if nRet ~= 0 then
+        FinalRes = Create_result("failure", "202", "xml 鏍煎紡闈炴硶: " .. parsed_data)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "xml鏍煎紡闈炴硶", parsed_data)
+        return
+    end
+
+    -- 3. 鎻愬彇涓昏〃鏁版嵁
+    local receipt_data = parsed_data.Envelope.Body.InventoryTasksReq.InventoryTasks_Input
+    local input_params = receipt_data.InputParameters
+
+    -- 妫�煡鏄惁瀛樺湪 InventoryTasks_TB
+    if not input_params or not input_params.InventoryTasks_TB then
+        FinalRes = Create_result("failure", "203", "xml 鏁版嵁鏍煎紡閿欒锛岀己灏�InventoryTasks_TB")
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "xml 鏁版嵁鏍煎紡閿欒", xml_result)
+        return
+    end
+
+    -- 4. 缁熶竴澶勭悊锛氱‘淇�mainTables 鏄暟缁勶紙鍗充娇鍙湁涓�釜涓昏〃锛�+    local mainTables = input_params.InventoryTasks_TB
+    if mainTables[1] == nil then
+        mainTables = {mainTables}
+    end
+
+    -- 5. 鑾峰彇绯荤粺甯搁噺
+    local RetWH_COE, CONST_WH = wms_base.Get_sConst2("WMS_Default_Factory")
+    if RetWH_COE ~= 0 then
+        FinalRes = Create_result("failure", "204", "鑾峰彇浠撳簱甯搁噺澶辫触: " .. CONST_WH)
+        local xml_result = xml.json_to_xml(FinalRes, "response")
+        mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+        lua.Stop(strLuaDEID, "鑾峰彇绯荤粺甯搁噺澶辫触", xml_result)
+        return
+    end
+
+    -- 6. 閬嶅巻鎵�湁鐩樼偣浠诲姟
+    for i = 1, #mainTables do
+        local mainData = mainTables[i]
+
+        -- 妫�煡鐩樼偣浠诲姟鏄惁宸插瓨鍦�+        local strCondition = string.format("S_CP_NO = '%s'", mainData.taskId)
+        lua.DebugEx(strLuaDEID, "鏌ヨ鐩樼偣浠诲姟鏉′欢", strCondition)
+        local nRet, retCountPlan = m3.GetDataObjByCondition(strLuaDEID, "Count_Plan", strCondition)
+        lua.DebugEx(strLuaDEID, "鏌ヨ缁撴灉", retCountPlan)
+        if nRet == 0 then
+            -- 鏌ヨ鎴愬姛涓旀壘鍒拌褰曪紝璇存槑鐩樼偣浠诲姟宸插瓨鍦�+            FinalRes = Create_result("failure", "1", "鐩樼偣浠诲姟[" .. mainData.taskId .. "]宸插瓨鍦�)
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "鐩樼偣浠诲姟宸插瓨鍦�, retCountPlan)
+            return
+        elseif nRet ~= 1 then
+            -- 鏌ヨ鍑洪敊
+            FinalRes = Create_result("failure", "206", "妫�煡鐩樼偣浠诲姟[" .. mainData.taskId ..
+                "]鏄惁瀛樺湪鏃跺嚭閿� " .. retCountPlan)
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "妫�煡鐩樼偣浠诲姟鏄惁瀛樺湪鏃跺嚭閿�, xml_result)
+            return
+        end
+
+        -- 鍒涘缓涓昏〃鏁版嵁
+        local count_plan = m3.AllocObject(strLuaDEID, "Count_Plan")
+        count_plan.cp_no = mainData.taskId
+        count_plan.inventory_mode = mainData.inventoryMode
+        count_plan.work_mode = mainData.workMode
+        count_plan.count_limit = mainData.MaintenanceNumber
+
+        -- 鏍规嵁inventoryType璁剧疆type鍜宼ype_desc
+        local panTypeValue = mainData.inventoryType or ""
+        local foundType = false
+        local typeValue = 0
+
+        -- 閬嶅巻瀛楀吀鏌ユ壘鍖归厤椤�+        for k, v in pairs(filedMapping) do
+            if string.find(panTypeValue, k) then
+                typeValue = v
+                foundType = true
+                break
+            end
+        end
+
+        -- 濡傛灉娌℃湁鎵惧埌鍖归厤椤癸紝浣跨敤榛樿鍊�+        if not foundType then
+            -- typeValue = 0
+            -- typeDesc = "鏈煡绫诲瀷"
+            -- lua.DebugEx(strLuaDEID, "璀﹀憡锛氭湭鎵惧埌鍖归厤鐨勭洏鐐圭被鍨�, panTypeValue)
+            FinalRes = Create_result("failure", "1", "鐩樼偣绫诲瀷[" .. panTypeValue .. "]涓嶅瓨鍦�)
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "鐩樼偣绫诲瀷涓嶅瓨鍦�, panTypeValue)
+        end
+
+        count_plan.type = typeValue
+
+        lua.DebugEx(strLuaDEID, "瀹瑰櫒绫诲瀷鏁板�锛�, count_plan.type)
+
+        count_plan.bs_no = mainData.orderNo
+        -- count_plan.storer = mainData.storerId
+        -- count_plan.owner = mainData.ownerId
+        count_plan.begin_time = mainData.mtBeginDate
+        count_plan.end_time = mainData.mtEndDate
+        count_plan.wh_code = CONST_WH
+        count_plan.plan_total = 0
+        count_plan.b_state = 0
+        count_plan.acc_finish = 0
+
+        lua.DebugEx(strLuaDEID, "鑾峰彇鍒涘缓鏁版嵁锛�, count_plan)
+
+        -- 妫�煡鏄惁宸插瓨鍦ㄧ浉鍚屽叧閿瓧鐨勮褰�+        local nRet, ret_info = m3.CreateDataObj(strLuaDEID, count_plan)
+        lua.DebugEx(strLuaDEID, "鍒涘缓缁撴灉", ret_info)
+        if nRet ~= 0 then
+            -- 鍐嶆妫�煡鏄惁鐪熺殑瀛樺湪
+            local nRetCheck, retCountPlanCheck = m3.GetDataObjByCondition(strLuaDEID, "Count_Plan", strCondition)
+            lua.DebugEx(strLuaDEID, "鍐嶆鏌ヨ缁撴灉", retCountPlanCheck)
+            if nRetCheck == 0 then
+                FinalRes = Create_result("failure", "205", "鐩樼偣浠诲姟[" .. mainData.taskId .. "]宸插瓨鍦�)
+            else
+                FinalRes = Create_result("failure", "207",
+                    "鐩樼偣浠诲姟[" .. mainData.taskId .. "]鍒涘缓澶辫触: " .. ret_info)
+            end
+            local xml_result = xml.json_to_xml(FinalRes, "response")
+            mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+            lua.Stop(strLuaDEID, "鍒涘缓鐩樼偣浠诲姟涓昏〃澶辫触", ret_info)
+            return
+        end
+
+        -- 妫�煡鏄庣粏鏁版嵁鏄惁瀛樺湪
+        if mainData.InventoryTasks_TB_ITEM == nil then
+            lua.DebugEx(strLuaDEID, "璀﹀憡锛氱洏鐐逛换鍔�" .. mainData.taskId .. " 鏃犳槑缁嗘暟鎹�)
+        else
+            -- 7. 閬嶅巻褰撳墠鐩樼偣浠诲姟鐨勬墍鏈夋槑缁嗘暟鎹�+            local details = mainData.InventoryTasks_TB_ITEM
+            -- 纭繚 details 鏄暟缁勶紙鍗充娇鍙湁涓�釜鏄庣粏锛�+            if details[1] == nil then
+                details = {details}
+            end
+
+            for j = 1, #details do
+                local item = details[j]
+
+                -- 鍒涘缓鏄庣粏鏁版嵁
+                local count_plan_item = m3.AllocObject(strLuaDEID, "Count_Plan_Detail")
+                count_plan_item.cp_no = mainData.taskId
+                count_plan_item.row_no = item.orderItemId
+                count_plan_item.qty = lua.Get_NumAttrValue(item.qty) or 0
+                count_plan_item.wms_bn = item.batchNo
+                count_plan_item.batch_no = item.produceCode or ""
+                count_plan_item.prd_date = item.productDate or ""
+                count_plan_item.exp_date = item.expiryDate or ""
+                count_plan_item.reg_no = item.registerNo or ""
+                count_plan_item.storer = mainData.storerId
+                count_plan_item.owner = mainData.ownerId
+                local nRet, ret_info = m3.CreateDataObj(strLuaDEID, count_plan_item)
+                if nRet ~= 0 then
+                    FinalRes = Create_result("failure", "208", "鍒涘缓鐩樼偣鏄庣粏澶辫触: " .. ret_info)
+                    local xml_result = xml.json_to_xml(FinalRes, "response")
+                    mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+                    lua.Stop(strLuaDEID, "鍒涘缓鐩樼偣鏄庣粏澶辫触", ret_info)
+                    return
+                end
+            end
+        end
+    end
+    -- 8. 杩斿洖鎴愬姛
+    FinalRes = Create_result("success", "0", "鐩樼偣浠诲姟鍒涘缓鎴愬姛")
+    local xml_result = xml.json_to_xml(FinalRes, "response")
+    mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+end
diff --git a/lua_code/Lua/GK-API-11-StockQuery.lua b/lua_code/Lua/GK-API-11-StockQuery.lua
new file mode 100644
index 0000000..2181640
--- /dev/null
+++ b/lua_code/Lua/GK-API-11-StockQuery.lua
@@ -0,0 +1,251 @@
+wms_base = require("wms_base")
+xml = require("oi_base_xml")
+mobox = require("OILua_JavelinExt")
+m3 = require("oi_base_mobox")
+
+-- XML鐗规畩瀛楃杞箟鍑芥暟
+local function xml_escape(str)
+    if not str then
+        return ""
+    end
+    return tostring(str):gsub("&", "&amp;"):gsub("<", "&lt;"):gsub(">", "&gt;"):gsub("\"", "&quot;"):gsub("'", "&apos;")
+end
+
+-- 纭紪鐮乆ML鐢熸垚鍣�+local function generate_raw_xml(result)
+    local xml = [[<?xml version="1.0" encoding="UTF-8"?>
+<response>
+    <flag>]] .. xml_escape(result.flag) .. [[</flag>
+    <code>]] .. xml_escape(result.code) .. [[</code>
+    <message>]] .. xml_escape(result.message) .. [[</message>]]
+
+    if result.data and #result.data > 0 then
+        xml = xml .. [[
+    <data>]]
+        for _, item in ipairs(result.data) do
+            xml = xml .. [[
+        <item>
+            <productLine>]] .. xml_escape(item.productLine) .. [[</productLine>
+            <storerId>]] .. xml_escape(item.storerId) .. [[</storerId>
+            <cid>]] .. xml_escape(item.cid) .. [[</cid>
+            <ownerId>]] .. xml_escape(item.ownerId) .. [[</ownerId>
+            <skuId>]] .. xml_escape(item.skuId) .. [[</skuId>
+            <boxCode>]] .. xml_escape(item.boxCode) .. [[</boxCode>
+            <qty>]] .. xml_escape(item.qty) .. [[</qty>
+            <registerNo>]] .. xml_escape(item.registerNo) .. [[</registerNo>
+            <skuStatus>]] .. xml_escape(item.skuStatus) .. [[</skuStatus>
+            <expiryDate>]] .. xml_escape(item.expiryDate) .. [[</expiryDate>
+            <batchNo>]] .. xml_escape(item.batchNo) .. [[</batchNo>
+            <productDate>]] .. xml_escape(item.productDate) .. [[</productDate>
+            <produceCode>]] .. xml_escape(item.produceCode) .. [[</produceCode>
+            <locationId>]] .. xml_escape(item.locationId) .. [[</locationId>
+        </item>]]
+        end
+        xml = xml .. [[
+    </data>]]
+    else
+        xml = xml .. [[
+    <data/>]]
+    end
+    xml = xml .. [[
+</response>]]
+    return xml
+end
+
+-- 鍒涘缓缁熶竴杩斿洖缁撴灉
+local function Create_result(flag, code, msg, data)
+    return {
+        flag = flag or "success",
+        code = code or "0",
+        message = msg or "",
+        data = data or {}
+    }
+end
+
+-- 娣卞害閬嶅巻鏌ユ壘XML鑺傜偣锛堟渶绋冲畾鐨勬柟娉曪級
+local function deep_find_xml_node(data, node_names)
+    if type(data) ~= "table" then
+        return nil
+    end
+
+    -- 鍏堝皾璇曠洿鎺ヨ矾寰勬煡鎵�+    local current = data
+    for _, name in ipairs(node_names) do
+        if type(current) ~= "table" then
+            break
+        end
+
+        -- 灏濊瘯甯1鍛藉悕绌洪棿鍜屼笉甯﹀懡鍚嶇┖闂寸殑鑺傜偣
+        current = current["v1:" .. name] or current[name]
+        if not current then
+            break
+        end
+    end
+    if current then
+        return current
+    end
+
+    -- 娣卞害閬嶅巻鏁翠釜XML鏍戞煡鎵�+    local function deep_search(t, names, index)
+        if index > #names then
+            return t
+        end
+        local current_name = names[index]
+
+        for k, v in pairs(t) do
+            if (k == current_name or k == "v1:" .. current_name) and type(v) == "table" then
+                local result = deep_search(v, names, index + 1)
+                if result then
+                    return result
+                end
+            elseif type(v) == "table" then
+                local result = deep_search(v, names, index)
+                if result then
+                    return result
+                end
+            end
+        end
+        return nil
+    end
+
+    return deep_search(data, node_names, 1)
+end
+
+-- 鏌ヨ搴撳瓨鏄庣粏
+local function query_inventory_detail(strLuaDEID, query_params)
+    local strCondition = string.format(" S_STORER = '%s' AND S_OWNER = '%s' AND S_ITEM_CODE = '%s'",
+        query_params.storerId, query_params.ownerId, query_params.skuId)
+
+    if query_params.locationId and query_params.locationId ~= "" then
+        strCondition = strCondition .. string.format(" AND S_LOC_CODE = '%s'", query_params.locationId)
+    end
+
+    if query_params.produceCode and query_params.produceCode ~= "" then
+        strCondition = strCondition .. string.format(" AND S_BATCH_NO = '%s'", query_params.produceCode)
+    end
+
+    local nRet, data_objects = m3.QueryDataObject(strLuaDEID, "INV_Detail", strCondition)
+    if nRet ~= 0 then
+        return nRet, data_objects
+    end
+
+    local formatted_result = {}
+    for n = 1, #data_objects do
+        local obj_attrs = m3.KeyValueAttrsToObjAttr(data_objects[n].attrs)
+        local stock = {
+            storerId = obj_attrs.S_STORER or "",
+            ownerId = obj_attrs.S_OWNER or "",
+            skuId = obj_attrs.S_ITEM_CODE or "",
+            skuStatus = obj_attrs.S_ITEM_STATE or "",
+            qty = lua.Get_NumAttrValue(obj_attrs.F_QTY) or 0,
+            locationId = obj_attrs.S_LOC_CODE or "",
+            cid = obj_attrs.S_CNTR_CODE or "",
+            boxCode = obj_attrs.S_CELL_NO or "",
+            batchNo = obj_attrs.S_WMS_BN or "",
+            produceCode = obj_attrs.S_BATCH_NO or "",
+            productDate = obj_attrs.D_PRD_DATE or "",
+            expiryDate = obj_attrs.D_EXP_DATE or "",
+            productLine = obj_attrs.S_UDF01 or "",
+            registerNo = obj_attrs.S_PROD_LINE or ""
+        }
+        table.insert(formatted_result, stock)
+    end
+
+    return 0, formatted_result
+end
+
+-- Main鍑芥暟
+function Stock_Query(strLuaDEID)
+    m3.PrintLuaDEInfo(strLuaDEID)
+    local FinalRes = Create_result()
+    local xml_result = ""
+
+    -- 浣跨敤pcall鎹曡幏鎵�湁鍙兘鐨勯敊璇�+    local status, err = pcall(function()
+        -- 1. 鑾峰彇xml鏁版嵁鍖�+        local nRet, soap_xml = mobox.getCurEditDataPacket(strLuaDEID)
+        if nRet ~= 0 then
+            FinalRes = Create_result("failure", "201", "鏃犳硶鑾峰彇鏁版嵁鍖� " .. tostring(soap_xml))
+            error(FinalRes.message)
+        end
+
+        -- 2. 瑙f瀽xml
+        local nRet, parsed_data = xml.parse(soap_xml)
+        if nRet ~= 0 then
+            FinalRes = Create_result("failure", "202", "xml鏍煎紡闈炴硶")
+            error(FinalRes.message)
+        end
+
+        -- 3. 浣跨敤娣卞害閬嶅巻鏌ユ壘鍏抽敭鑺傜偣
+        local inventory_input = deep_find_xml_node(parsed_data, {"Envelope", "Body", "InventoryReq", "Inventory_Input"})
+        if not inventory_input then
+            FinalRes = Create_result("failure", "206", "XML缁撴瀯閿欒: 缂哄皯Inventory_Input鑺傜偣")
+            error(FinalRes.message)
+        end
+
+        local input_params = deep_find_xml_node(inventory_input, {"InputParameters"})
+        if not input_params then
+            FinalRes = Create_result("failure", "207", "XML缁撴瀯閿欒: 缂哄皯InputParameters鑺傜偣")
+            error(FinalRes.message)
+        end
+
+        local inventory_tb = deep_find_xml_node(input_params, {"Inventory_TB"})
+        if not inventory_tb then
+            FinalRes = Create_result("failure", "208", "XML缁撴瀯閿欒: 缂哄皯Inventory_TB鑺傜偣")
+            error(FinalRes.message)
+        end
+
+        -- 4. 鎻愬彇鏌ヨ鍙傛暟
+        local query_params = {
+            storerId = deep_find_xml_node(inventory_tb, {"storerId"}) or "",
+            ownerId = deep_find_xml_node(inventory_tb, {"ownerId"}) or "",
+            skuId = deep_find_xml_node(inventory_tb, {"skuId"}) or "",
+            productLine = deep_find_xml_node(inventory_tb, {"productLine"}) or "",
+            locationId = deep_find_xml_node(inventory_tb, {"locationId"}) or "",
+            produceCode = deep_find_xml_node(inventory_tb, {"produceCode"}) or ""
+        }
+
+        -- 5. 鍙傛暟鏍¢獙
+        if query_params.storerId == "" then
+            FinalRes = Create_result("failure", "203", "storerId涓嶈兘涓虹┖")
+            error(FinalRes.message)
+        end
+
+        if query_params.skuId == "" then
+            FinalRes = Create_result("failure", "204", "skuId涓嶈兘涓虹┖")
+            error(FinalRes.message)
+        end
+
+        -- 6. 鏌ヨ搴撳瓨鏄庣粏
+        local nRet, query_result = query_inventory_detail(strLuaDEID, query_params)
+        if nRet ~= 0 then
+            FinalRes = Create_result("failure", "205", "鏌ヨ搴撳瓨鏄庣粏澶辫触: " .. tostring(query_result))
+            error(FinalRes.message)
+        end
+
+        -- 7. 澶勭悊鏌ヨ缁撴灉
+        if not query_result or #query_result == 0 then
+            FinalRes = Create_result("success", "0", "鏈煡璇㈠埌绗﹀悎鏉′欢鐨勫簱瀛樿褰�, {})
+        else
+            FinalRes = Create_result("success", "0", "鏌ヨ鎴愬姛锛�, query_result)
+        end
+    end)
+
+    -- 澶勭悊閿欒鎯呭喌
+    if not status then
+        if FinalRes.code == "0" then
+            FinalRes = Create_result("failure", "299", "绯荤粺鍐呴儴閿欒: " .. tostring(err))
+        end
+    end
+
+    -- 鐢熸垚XML缁撴灉
+    xml_result = generate_raw_xml(FinalRes)
+
+    -- 杩斿洖缁撴灉
+    mobox.returnValue(strLuaDEID, 0, xml_result, 0)
+
+    -- 璁板綍閿欒鏃ュ織
+    if not status then
+        lua.Stop(strLuaDEID, "澶勭悊杩囩▼涓彂鐢熼敊璇�, FinalRes)
+    end
+end

--
Gitblit v1.9.1