<?php
class Service_OrderProcess
{
    private $_order = array();
    private $_ordersCode = '';
    private $_order_weight = 0;
    private $_warehouseId = 0;
    private $_picking = array();
    private $_pickingId = 0;
    private $_pickingCode = '';
    private $_pickerId = '0'; //配货员
    private $_printType = '0'; //下架类型
    private $_lc_code_arr = array();


    public function batchPickupTransaction($pickTypeArray = array(), $warehouseId = '')
    {
        $result = array('state' => 0, 'message' => array(), 'assign' => 0, 'error' => array('Fail.'), 'pick' => array(),'errorCode'=>'','failCount'=>0);
        
        //检测账号是否被冻结
        if(!empty($pickTypeArray['orderCodeArr']) && is_array($pickTypeArray['orderCodeArr'])){
            $frozenCustomerDataArr = array();
            foreach ($pickTypeArray['orderCodeArr'] as $orderCodeRow) {
                if(!empty($orderCodeRow)){
                    $customerOrderData = Service_Orders::getByField($orderCodeRow, 'order_code', array('customer_code'));
                    $customerData = Service_Customer::getByField($customerOrderData['customer_code'], 'customer_code', array('is_frozen', 'frozen_reason'));
                    if($customerData['is_frozen'] == 1){
                        if(!in_array(array($customerOrderData['customer_code'] => $customerData['frozen_reason']), $frozenCustomerDataArr)){
                            $frozenCustomerDataArr[] = array($customerOrderData['customer_code'] => $customerData['frozen_reason']);
                        }
                    }
                }
            }
            if(!empty($frozenCustomerDataArr)){
                foreach ($frozenCustomerDataArr as $frozenCustomerRow) {
                    $result['message'][] = '客户['.key($frozenCustomerRow).']已冻结，冻结原因：'.$frozenCustomerRow[key($frozenCustomerRow)];
                }
                return $result;
            }
        }

        $this->_printType = $pickTypeArray['printType'];
        switch ($pickTypeArray['type']) {
            case 0:
                $orderCodes = array();
                foreach($pickTypeArray['orderCodeArr'] as $val){
                    if($val!="") {
                        if( true === $this->hasRefTrackingNumber($val) ) {
                            $orderCodes[] = $val;
                        } else {
                            $result['message'][] = $val.'参考服务商单号为空';
                        }
                    }
                }

                if( empty( $orderCodes ) ) {
                    return $result;
                }

                ksort($pickTypeArray['data']);
                $pickerArr = $pickTypeArray['data'];
                $this->_pickerId = $pickTypeArray['data'][0];
                $size = count($orderCodes)/count($pickTypeArray['data'])>1?count($orderCodes)/count($pickTypeArray['data']):1;
                $orderCodeArr = array_chunk($orderCodes,$size);
                if(count($orderCodeArr)>count($pickTypeArray['data'])){
                    $orderCodeArr[count($orderCodeArr)-2] = array_merge($orderCodeArr[count($orderCodeArr)-2],$orderCodeArr[count($orderCodeArr)-1]);
                    unset($orderCodeArr[count($orderCodeArr)-1]);
                }
                $ocArr = array();
                $i = 0;
                foreach($pickTypeArray['data'] as $pk=>$pv){
                    if(!isset($orderCodeArr[$i])) continue;
                    $ocArr[$pk]['pick_id'] = $pv;
                    $ocArr[$pk]['orderCodeArr'] = $orderCodeArr[$i];
                    $i++;
                }
                foreach($ocArr as $ok=>$ov){
                    $return = $this->orderArrPickupTransaction($ov['orderCodeArr'], $warehouseId,$ov['pick_id'],1);
                    if (isset($return['success_count']) && $return['pick_code']!='' ){
						$result['state'] = "1";
                        $result['assign'] = 1;
                        $result['pick'][] = array('pickCode' => $return['success_count'] > 0 ? $return['pick_code'] : '', 'message' => 'success');
                    }else{
                        $result['errorCode'] = $return['errorCode'];
                        $result['message'][]= isset($return['errors'][0]) ? $return['errors'][0]['message'] :'没有找到未下架订单';
                        $result['errorArra'] = $return;
                        break;
                    }
                }
                $result['pickType'] = 0;
                return $result;
                break;
            case 1:
                //按份数下架
                $result['assign'] = 0;
                $orderCodes = array();
                foreach($pickTypeArray['orderCodeArr'] as $val){
                    if($val!="") {
                        if( true === $this->hasRefTrackingNumber($val) ) {
                            $orderCodes[] = $val;
                        } else {
                            $result['message'][] = $val.'参考服务商单号为空';
                        }
                    }
                }

                if( empty( $orderCodes ) ) {
                    return $result;
                }

                $qty = $pickTypeArray['data'];
                $this->_pickerId = 0;
                //$size = count($orderCodes)/count($pickTypeArray['data'])>1?count($orderCodes)/count($pickTypeArray['data']):1;
                $arraySize = ceil(count($orderCodes)/$qty);
                $orderCodeArr = array_chunk($orderCodes,$arraySize);
                $ocArr = array();
                $i = 0;
                foreach($orderCodeArr as $pk=>$pv){
                    if(!isset($orderCodeArr[$i])) continue;
                    $ocArr[$pk]['pick_id'] = "";
                    $ocArr[$pk]['orderCodeArr'] = $orderCodeArr[$i];
                    $i++;
                }
                foreach($ocArr as $ok=>$ov){
                    $return = $this->orderArrPickupTransaction($ov['orderCodeArr'], $warehouseId,$ov['pick_id'],2);
                    if (isset($return['success_count']) && $return['pick_code']!='' ){
                        $result['state'] = "1";
                        $result['assign'] = 1;
                        $pickCodeArr[] = $return['pick_code'];
                        $result['pick'][] = array('pickCode' => $return['success_count'] > 0 ? $return['pick_code'] : '', 'message' => 'success');
                    }else{
                        $result['message'][]='没有找到未下架订单';
                        break;
                    }
                }
                $result['pickType'] = 1;
                return $result;
                break;

            default:
                break;
        }
    }

    //批量下架
    public function orderArrPickupTransaction($ordersCodes, $warehouseId,$pickerId="",$picking_type="1")
    {
        $results = array();
        $errors = array();
        $this->_warehouseId = $warehouseId;
        $this->_pickerId = $pickerId;
        $db = Service_QualityControl::getModelInstance()->getAdapter();

        try {
            $pickCode = Common_GetNumbers::getCode('picking', $warehouseId, 'PL'); // 配货号

            $this->_userAuth = new Zend_Session_Namespace('userAuthorization');
            $this->_picking = array(
                'warehouse_id' => $warehouseId,
                'picking_code' => $pickCode,
                'picker_id' => $this->_pickerId,
                'creater_id' => isset($this->_userAuth->userId) ? $this->_userAuth->userId : '0',
                'picking_order_cnt' => '0',
                'picking_lc_cnt' => '0',
                'picking_item_cnt' => '0',
                'picking_status' => '0',
                'is_assign' => $this->_pickerId != '0' ? 1 : 0,
                'picking_type' => $picking_type,
                'picking_add_time' => date("Y-m-d H:i:s"),
                'picking_update_time' => date("Y-m-d H:i:s"),
            );
            if (!$this->_pickingId = Service_Picking::add($this->_picking)) { //配货单主键
                throw new Exception('Inner Error11', 50000);
            }
            $this->_pickingCode = $pickCode;
        } catch (Exception $e) {
            return $e->getMessage();
        }
        $ordersCodes = array_unique($ordersCodes); //去除重复项

        $successCount = $failCount = 0;
        if($this->_printType=='0'){
            $order_pick_type_in=array('0');
        }else{
            $order_pick_type_in=array('1','2');
        }
        //$ordersCodes = Service_Orders::getShipmentByCondition(array('order_status' => 4, 'order_pick_type' => $order_pick_type_in), 'order_code', 200, 1, array('order_id asc'));
        foreach ($ordersCodes as $order_code) {
            $ordersCode = $order_code;
            $result = array('state' => 0, 'message' => '', 'order_code' => $ordersCodes);
            $db->beginTransaction();
            try {
                $this->orderPickup($ordersCode);
                $this->_picking['picking_lc_cnt'] = count($this->_lc_code_arr);

                $db->commit();
                $result['state'] = 1;
                $result['message'] = 'Success';
                $results[] = $result;
                $successCount++;
            } catch (Exception $e) {
                $db->rollback();
                $result['errorCode'] =$e->getCode();
                $result['message'] = $e->getMessage();
                $results[] = $result;
                $errors[] = $result;
                $failCount++;
            }

        }
        try {
            if ($failCount == count($ordersCodes)) { //全部失败，删除配货单
                if (!Service_Picking::delete($this->_pickingId, 'picking_id')) {
                    throw new Exception('Inner Error', 50001);
                }
                $pickCode = '';
            } else {
                if ($this->_picking['picking_order_cnt'] == $this->_picking['picking_item_cnt']) {
                    $this->_picking['picking_type'] = 0;
                }
                if (!Service_Picking::update($this->_picking, $this->_pickingId)) {
                    throw new Exception('Inner Error', 50002);
                }
            }

        } catch (Exception $e) {
            //一般不会发生问题，这个地方应当是写日志的
            Ec::showError($e->getMessage(), 'pack');
        }
        $return = array('pick_code' => $pickCode, 'success_count' => $successCount, 'fail_count' => $failCount, 'errors' => $errors);
        return $return;
    }


    //下架
    public function orderPickup($ordersCode)
    {
        $status = 5;
        $date = date('Y-m-d H:i:s');
        $result = array("state" => 0, "message" => "");
        $userId = Service_User::getUserId();
        if ($this->_ordersCode != $ordersCode) {
            $this->_ordersCode = $ordersCode;
            $this->_setOrder();
        }

        if ($this->_order['order_status'] != 4) {
            throw new Exception("Order status Err", 50003);
        }
        if ($this->_order['warehouse_id'] != $this->_warehouseId) {
            throw new Exception("Order warehouse Err", 50004);
        }
        $smWhite = array('BH-USPS','BH-DPD','Rumall-RU-EP','Rumall-RU-G', '4PX-LYT_GH', '4PX-EU_PACKET', '4PX-RU_POST-LINK_RMAIL', '4PX-HKDHL', '4PX-YX','4PX-SG_ordinary_mail+','PNLG','PNLN','BH-POST-NL','BH-SFEP');
        if(in_array($this->_order['sm_code'] , $smWhite) && $this->_order['ref_tracking_number'] == ''){
            throw new Exception("运输渠道【{$this->_order['sm_code']}】只有取回运单号的订单才允许操作下架！", 50008);            
        }
        $sendInfoSmCode=array('4PX-Singapo_SPack_IMAIR','4PX-OZXBTH');
        if(in_array($this->_order['sm_code'] , $sendInfoSmCode) && $this->_order['sync_status'] != '1'){
            throw new Exception("运输渠道【{$this->_order['sm_code']}】只有订单的信息推送4px成功才允许操作下架！", 50008);            
        }
        $this->_holdInventory(); //库存冻结'
        $row = array(
            'order_status' => $status, //下架状态更新
            'picker_id' => $this->_pickerId,
            'update_time' => $date
        );
        if (!Service_Orders::update($row, $ordersCode, 'order_code')) {
            throw new Exception("Internal error!Order Pickup Fail.", 50005);
        }

        if (Service_OrderOperationTime::getByField($this->_order['order_id'], 'order_id')) {
            $orderOperationTimeRow = array( //下架时间
                'process_time' => $date,
                'process_user_id' => $userId,
                'update_time' => $date,
            );
            if (!Service_OrderOperationTime::update($orderOperationTimeRow, $this->_order['order_id'], 'order_id')) {
                throw new Exception("Internal error!Order Pickup Fail.", 50006);
            }
        } else {
            $orderOperationTimeRow = array( //下架时间
                'order_id' => $this->_order['order_id'],
                'order_code' => $ordersCode,
                'process_user_id' => $userId,
                'process_time' => $date,
                'update_time' => $date,
            );
            if (!Service_OrderOperationTime::add($orderOperationTimeRow)) {
                throw new Exception("Internal error!Order Pickup Fail.", 50007);
            }
        }

        $orderRow = Service_Orders::getByField($ordersCode,"order_code","*");
        $w = Service_Warehouse::getByField($orderRow['warehouse_id'],'warehouse_id','*');
        $shipOrderTracking = array(
            'order_code'=>$ordersCode,
            'sot_location'=>$w['warehouse_desc'],
            'sot_add_time'=>$date,
            'warehouse_id'=>$orderRow['warehouse_id'],
            'sot_description'=>'备货仓库系统确认订单,并打印拣货单',
            'sot_type'=>'0',
            'sot_time_offset'=>'',
            'tracking_number'=>$ordersCode,
            'ref_tracking_number'=>'',
            'status_desc'=>'已打印',
            'user_id'=>$userId
        );
        Service_ShipOrderTracking::add($shipOrderTracking);


        $logRow = array( //日志
            'order_id' => $this->_order['order_id'],
            'order_code' => $ordersCode,
            'ol_type' => '0',
            'order_status_from' => $this->_order['order_status'],
            'order_status_to' => $status,
            'ol_add_time' => $date,
            'user_id' => $userId,
            'ol_comments' => "Order Pickup " . $this->_pickerId,
            'ol_ip' => Common_Common::getIP(),
        );
        if (!Service_OrderLog::add($logRow)) {
            throw new Exception("Internal error!Order Pickup Fail.", 50008);
        }

        //订单操作节点
        $nodeRow = array(
            'order_id' => $this->_order['order_id'],
            'order_code' => $ordersCode,
            'oot_code' => 'pickup', //操作代码
            'user_id' => $userId,
            'oon_add_time' => $date,

        );
        if (!Service_OrderOperationNode::add($nodeRow)) {
            throw new Exception("Internal error!Order Pickup Fail.", 50009);
        }


    }

    private function _setOrder()
    { //初始化

        $order = Service_Orders::getByField($this->_ordersCode, 'order_code');

        if (empty($order)) {
            throw  new Exception("OrderCode Not Exists-->" . $this->_ordersCode, 50010);
        }
        $addressRow = Service_OrderAddressBook::getByField($this->_ordersCode, 'order_code');
        if (empty($addressRow)) {
            throw  new Exception("Internal Error!Address Data Miss -->" . $this->_ordersCode, 50011);
        }
        $address = array();
        foreach ($addressRow as $key => $adr) {
            $k = preg_replace('/^oab_/', '', $key);
            $address[$k] = $adr;
        }
        $order = array_merge($address, $order);
        $con = array('order_code' => $this->_ordersCode);
//         $orderProducts = Service_OrderProduct::getByCondition($con);

        $orderProducts = $this->getOrderProductUnique($this->_ordersCode);
        $this->_order_weight = 0; //订单重量
        foreach ($orderProducts as $p) {
            $product = Service_Product::getByField($p['product_id'], 'product_id');
            if (empty($product)) {
                throw new Exception('Inner Error,Product Data Miss[' . $p['product_id'] . ']');
            }
            $this->_order_weight += $p['op_quantity'] * $product['product_weight'];
        }
        $order['order_product'] = $orderProducts;
        $this->_order = $order;
    }

    //提取订单中的所有产品，主要是提取组合产品中的普通产品
    public function getOrderProductUnique($ordersCode)
    {
        $orderProduct = Service_OrderProduct::getByCondition(array("order_code" => $ordersCode));

        $orderProducts = array();
        foreach ($orderProduct as $v) { //提取所有产品（判断有无组合产品）
            $product = Service_Product::getByField($v['product_id'], 'product_id');

            if ($product['product_type'] == 1) { //组合产品
                $con = array('product_id' => $product['product_id']);
                $productCombine = Service_ProductCombineRelation::getByCondition($con, "*");
                foreach ($productCombine as $sub) {
                    $subProduct = Service_Product::getByField($sub['pcr_product_id'], 'product_id');

                    if (isset($orderProducts[$sub['pcr_product_id']])) {
                        $orderProducts[$sub['pcr_product_id']]['op_quantity'] += $sub['pcr_quantity'] * $v['op_quantity'];
                    } else {
                        $orderProducts[$sub['pcr_product_id']] = array(
                            'order_code' => $ordersCode,
                            'op_id' => $v['op_id'],
                            'product_id' => $subProduct['product_id'],
                            'product_sku' => $subProduct['product_sku'],
                            'product_barcode' => $subProduct['product_barcode'],
                            'customer_id' => $subProduct['customer_id'],
                            'op_quantity' => $sub['pcr_quantity'] * $v['op_quantity'],
                            'op_weight' => $subProduct['product_weight'],
                            'op_unit_price' => $subProduct['product_declared_value'],
                            'goods_id'=> $subProduct['goods_id'],
                            'hs_code'=> $subProduct['hs_code'],
                        );
                    }
                }

            } else {
                if (isset($orderProducts[$v['product_id']])) {
                    $orderProducts[$v['product_id']]['op_quantity'] += $v['op_quantity'];
                } else {
                    $orderProducts[$v['product_id']] = array(
                        'order_code' => $ordersCode,
                        'op_id' => $v['op_id'],
                        'product_id' => $product['product_id'],
                        'product_sku' => $product['product_sku'],
                        'product_barcode' => $product['product_barcode'],
                        'customer_id' => $product['customer_id'],
                        'op_quantity' => $v['op_quantity'],
                        'op_weight' => $product['product_weight'],
                        'op_unit_price' => $product['product_declared_value'],
                        'goods_id'=> $product['goods_id'],
                        'hs_code'=> $product['hs_code'],
                    );
                }
            }
        }

        // 	    print_r($orderProducts);exit;
        return $orderProducts;
    }

    private function _holdInventory()
    { //冻结库存
        $orderProductCount = 0; //订单后产品数量
        foreach ($this->_order['order_product'] as $p) {

            $orderProductCount += $p['op_quantity'];
            $con = array(
                'product_id' => $p['product_id'],
                'warehouse_id' => $this->_order['warehouse_id'],
                'ib_status' => '1',
                'ib_hold_status' => '0',
            );
            $batchs = Service_InventoryBatch::getByCondition($con, '*', 0, 0, 'ib_id asc'); //先进先出
            if (empty($batchs)) {
                throw new Exception('[' . $p['product_barcode'] . 'insufficient stock 001',50019);
            }

            foreach ($batchs as $batch) {
                $this->_lc_code_arr[$batch['lc_code']] = $batch['lc_code'];
                $con1 = array(
                    'ib_id' => $batch['ib_id'], //一个货架多个产品无法用货架号去判断，用id吧
                );
                $sumQty = Service_InventoryBatchOutbound::getByCondition($con1, 'sum(ibo_quantity) as sum_qty'); //??
                if (empty($sumQty)) {
                    $sumQty = 0;
                } else {
                    $sumQty = $sumQty[0]['sum_qty'];
                }
                if (!$batch['ib_status'] || $batch['ib_hold_status'] != '0') {
                    continue;
                }
                $batch['ib_quantity'] -= $sumQty; //批次可用数

                if ($p['op_quantity'] <= $batch['ib_quantity']) { // 订单产品数量小于等于批次可用数
                    $qty = $p['op_quantity'];
                    // 插入一条产品出库核销记录
                    $boundRow = array(
                        'lc_code' => $batch['lc_code'],
                        'warehouse_id' => $this->_order['warehouse_id'],
                        'reference_no' => $this->_order['order_code'],
                        'application_code' => 'pickup',
                        'ibo_quantity' => $qty,
                        'ib_id' => $batch['ib_id'],
                        'ibo_add_time' => date('Y-m-d H:i:s')
                    );
                    if (!$ibo_id = Service_InventoryBatchOutbound::add($boundRow)) {
                        throw new Exception('Inner Error', 50011);
                    }
                    $boundLogRow = array(
                        'lc_code' => $batch['lc_code'],
                        'ibo_id' => $ibo_id,
                        'ib_id' => $batch['ib_id'],
                        'reference_no' => $this->_order['order_code'],
                        'application_code' => 'pickup',
                        'ibol_quantity' => $qty,
                        'user_id' => '0',
                        'ibol_ip' => Common_Common::getIP(),
                        'ibol_add_time' => date('Y-m-d H:i:s'),
                        'ibol_note' => $batch['product_barcode']
                    );
                    if (!Service_InventoryBatchOutboundLog::add($boundLogRow)) {
                        throw new Exception('Inner Error', 50012);
                    }
                    $batchLog = array(
                        'lc_code' => $batch['lc_code'],
                        'product_id' => $p['product_id'],
                        'product_barcode' => $p['product_barcode'],
                        'supplier_id' => '',
                        'warehouse_id' => $this->_order['warehouse_id'],
                        'ib_id' => $batch['ib_id'],
                        'receiving_code' => '',
                        'reference_no' => $this->_order['order_code'],
                        'application_code' => '',
                        'ibl_note' => $batch['product_barcode'],
                        'ibl_quantity_before' => $batch['ib_quantity'],
                        'ibl_quantity_after' => $batch['ib_quantity'],
                        'user_id' => '0',
                        'ibl_ip' => Common_Common::getIP(),
                        'ibl_add_time' => date('Y-m-d H:i:s')
                    );

                    if (!Service_InventoryBatchLog::add($batchLog)) { //批次日志 ? 好像此时没动到批次哦
                        throw new Exception('Inner Error', 50013);
                    }

                    $pickingDetailRow = array(
                        'picking_id' => $this->_pickingId,
                        'picking_code' => $this->_pickingCode,
                        'order_id' => $this->_order['order_id'],
                        'order_code' => $this->_order['order_code'],
                        'pd_status' => '0',
                        'op_id' => $p['op_id'],
                        'pd_quantity' => $qty,
                        'ibo_id' => $ibo_id,
                        'product_id' => $p['product_id'],
                        'product_barcode' => $p['product_barcode'],
                        'ib_id' => $batch['ib_id'],
                        'lc_code' => $batch['lc_code'],
                        'pd_add_time' => date('Y-m-d H:i:s')
                    );
                    if (!$pd_id = Service_PickingDetail::add($pickingDetailRow)) { //配货明细
                        throw new Exception('Inner Error', 50014);
                    }
                    if(substr($batch['receiving_code'],0,3)=="SWO"){
                        $this->dealSerial($con1,$batch,$qty,$p,$this->_order['order_code']);
                    }else{
                        $OrderGoods = array(
                            'order_code'=>$this->_order['order_code'],
                            'product_id'=>$p['product_id'],
                            'goods_id'=>$p['goods_id'],
                            'good_quantity'=>$qty,
                            'from_product_id'=>$p['product_id'],
                            'hs_serial_no'=>$batch['hs_serial_no'],
                            'batch_goods_id'=>$batch['batch_goods_id'],
                            'hs_code'=>$p['hs_code'],
                        );
                        Service_OrderGoods::add($OrderGoods);
                    }

                    $p['op_quantity'] = 0;
                    break;
                } else {
                    $qty = $batch['ib_quantity'];
                    if ($qty <= 0) {
                        continue;
                    }
                    // 插入一条产品出库核销记录
                    $boundRow = array(
                        'lc_code' => $batch['lc_code'],
                        'warehouse_id' => $this->_order['warehouse_id'],
                        'reference_no' => $this->_order['order_code'],
                        'application_code' => 'pickup',
                        'ibo_quantity' => $qty,
                        'ib_id' => $batch['ib_id'],
                        'ibo_add_time' => date('Y-m-d H:i:s')
                    );
                    if (!$ibo_id = Service_InventoryBatchOutbound::add($boundRow)) {
                        throw new Exception('Inner Error', 50015);
                    }

                    $boundLogRow = array(
                        'lc_code' => $batch['lc_code'],
                        'ibo_id' => $ibo_id,
                        'ib_id' => $batch['ib_id'],
                        'reference_no' => $this->_order['order_code'],
                        'application_code' => 'pickup',
                        'ibol_quantity' => $qty,
                        'user_id' => '0',
                        'ibol_ip' => Common_Common::getIP(),
                        'ibol_add_time' => date('Y-m-d H:i:s'),
                        'ibol_note' => $batch['product_barcode']
                    );
                    if (!Service_InventoryBatchOutboundLog::add($boundLogRow)) {
                        throw new Exception('Inner Error', 50016);
                    }
                    $batchLog = array(
                        'lc_code' => $batch['lc_code'],
                        'product_id' => $p['product_id'],
                        'product_barcode' => $p['product_barcode'],
                        'supplier_id' => '',
                        'warehouse_id' => $this->_order['warehouse_id'],
                        'ib_id' => $batch['ib_id'],
                        'receiving_code' => '',
                        'reference_no' => $this->_order['order_code'],
                        'application_code' => 'pickup',
                        'ibl_note' => $batch['product_barcode'],
                        'ibl_quantity_before' => $batch['ib_quantity'],
                        'ibl_quantity_after' => $batch['ib_quantity'],
                        'user_id' => '0',
                        'ibl_ip' => Common_Common::getIP(),
                        'ibl_add_time' => date('Y-m-d H:i:s')
                    );
                    if (!Service_InventoryBatchLog::add($batchLog)) {
                        throw new Exception('Inner Error', 50017);
                    }

                    $pickingDetailRow = array(
                        'picking_id' => $this->_pickingId,
                        'picking_code' => $this->_pickingCode,
                        'order_id' => $this->_order['order_id'],
                        'order_code' => $this->_order['order_code'],
                        'pd_status' => '0',
                        'op_id' => $p['op_id'],
                        'pd_quantity' => $qty,
                        'ibo_id' => $ibo_id,
                        'product_id' => $p['product_id'],
                        'product_barcode' => $p['product_barcode'],
                        'ib_id' => $batch['ib_id'],
                        'lc_code' => $batch['lc_code'],
                        'pd_add_time' => date('Y-m-d H:i:s')
                    );
                    if (!$pd_id = Service_PickingDetail::add($pickingDetailRow)) { //配货明细
                        throw new Exception('Inner Error', 50018);
                    }
                    if(substr($batch['receiving_code'],0,3)=="SWO"){
                        $this->dealSerial($con1,$batch,$qty,$p,$this->_order['order_code']);
                    }else{
                        $OrderGoods = array(
                            'order_code'=>$this->_order['order_code'],
                            'product_id'=>$p['product_id'],
                            'goods_id'=>$p['goods_id'],
                            'good_quantity'=>$qty,
                            'from_product_id'=>$p['product_id'],
                            'hs_serial_no'=>$batch['hs_serial_no'],
                            'batch_goods_id'=>$batch['batch_goods_id'],
                            'hs_code'=>$p['hs_code'],
                        );
                        Service_OrderGoods::add($OrderGoods);
                    }

                    $p['op_quantity'] -= $batch['ib_quantity']; //扣除已经处理的
                }
            }

            if ($p['op_quantity'] > 0) {
                throw new Exception('[' . $p['product_barcode'] . 'insufficient stock 002',50020);
            }
        }
        $this->_picking['picking_order_cnt']++;
        $this->_picking['picking_item_cnt'] += $orderProductCount;
    }
  public static function splitOrderCode($orderCode, $delimiter = '|') {
    $orderCode = str_replace(array("\r", "\n"), '', $orderCode);
    $orderCode = trim($orderCode);

    if ('' === $orderCode) {
      return '请提供订单号/交易订单号';
    }

    $orderCode  = explode($delimiter, $orderCode);
    $filterCode = array();

    foreach ($orderCode as $key => $value) {
      if ('' === trim($value)) {
        unset($orderCode[$key]);
      }
      elseif (!isset($filterCode[$value])) {
        $orderCode[$key]    = trim($value);
        $filterCode[$value] = 1;
      }
      else {
        unset($orderCode[$key]);
      }
    }

    $total = count($orderCode);

    if ($total > 0 && $total <= 10) {
      return $orderCode;
    }

    return ($total > 10) ? '最多只接收10个单号' : '请提供订单号/交易订单号';
  }
  public static function getQueryOrder($orderCodeArray,$type,$pageSize=0,$page=1, $order = ""){
      $data=array();
      $result=  Service_Orders::getInnerJionShiporderCondition(array('o_or_r_code'=>$orderCodeArray), $type,$pageSize,$page,$order);
      if($type=='count(*)'){
          $data['total']=$result;
          return $data;
      }
      if(!empty($result)){
        
          foreach($result as $r){
              $stauts=Service_Orders::getStatusText($r['order_status']);
              $contryInfo=Service_Country::getByField($r['oab_country_id']);
              $r['so_weight']=empty($r['so_weight'])?'0':$r['so_weight'];
              $r['so_vol_weight']=empty($r['so_vol_weight'])?'0':$r['so_vol_weight'];
              $r['so_fee_weight']=empty($r['so_fee_weight'])?'0':$r['so_fee_weight'];
              $shipOrderDetail=Service_ShipOrderDetail::getByCondition( array('order_code' =>$r['order_code']));
                $sod='';
              foreach ($shipOrderDetail as $key => $value) {
                  $sod.=$value['sod_length'].'*'.$value['sod_width'].'*'.$value['sod_height'].'<br/>';
              }
              /*$r['sod_length']=is_null($shipOrderDetail[0]['sod_length'])?'0':$r['sod_length'];
              $r['sod_width']=is_null($shipOrderDetail[0]['sod_width'])?'0':$r['sod_width'];
              $r['sod_height']=is_null($shipOrderDetail[0]['sod_height'])?'0':$r['sod_height'];*/
              if(empty($r['process_time'])||$r['process_time']=='0000-00-00 00:00:00'){
                  $r['process_time']='';
              }
              if(empty($r['pack_time'])||$r['pack_time']=='0000-00-00 00:00:00'){
                  $r['pack_time']='';
              }
               if(empty($r['ship_time'])||$r['ship_time']=='0000-00-00 00:00:00'){
                  $r['ship_time']='';
              }
              $data[]=array(
                  'order_id'=>$r['order_id'],
                  'order_code'=>$r['order_code'],
                  'ref_tracking_number'=>$r['tracking_number']?$r['tracking_number']:$r['ref_tracking_number'],
                  'customer_code'=>$r['customer_code'],
                  'sm_code'=>$r['sm_code'],
                  'country'=>$contryInfo['country_name'],
                  'weight'=>$r['so_weight'],
                  'status'=>$stauts,
                  'add_time'=>$r['add_time'],
                  'print_time'=>$r['process_time'],
                  'pack_time'=>$r['pack_time'],
                  'ship_time'=>$r['ship_time'],
                  'so_vol_weight'=>$r['so_vol_weight'],
                  'so_fee_weight'=>$r['so_fee_weight'],
                  'sod'=>$sod,
              );
          }
      }  
      
      return $data;
  }
  public static function getCacheDir() {
    return str_replace('\\', '/', realpath(APPLICATION_PATH . '/../data/cache')) . '/';
  }
   public static function buildCache($file) {
    $response = array('status' => 0, 'message' => '');

    if (!is_file($file)) { // 判断文件是否存在
      $response['message'] = '缓存文件【' . $file . '】不存在';

      return $response;
    }

    $ext = strtolower(pathinfo($file, PATHINFO_EXTENSION)); // 文件扩展名

    if (!in_array($ext, array('xls', 'xlsx'), TRUE)) { // 允许的文件类型
      $response['message'] = '文件类型【' . $ext . '】错误，仅支持xls或xlsx类型文件';
      @unlink($file); // 删除文件

      return $response;
    }

    require_once APPLICATION_PATH . '/../libs/PHPExcel.php';
    require_once APPLICATION_PATH . '/../libs/PHPExcel/IOFactory.php';

    set_time_limit(0); // 不限制执行时间
    ini_set('memory_limit', '2048M'); // 2G内存限制

    $loaderObj = PHPExcel_IOFactory::load($file); // 加载Excel文件

    if (!$loaderObj) {
      $response['message'] = '文件解析失败，请确保所上传的文件类型为xls或xlsx';
      @unlink($file); // 删除文件

      return $response;
    }

    $sheetObj = $loaderObj->getSheet(0); // 获取第一个工作表
    $maxCols  = PHPExcel_Cell::columnIndexFromString($sheetObj->getHighestColumn()); // 最大列数
    $maxRows  = $sheetObj->getHighestRow(); // 最大行数
    $cacheDir = self::getCacheDir();
    $data     = array();
    $repeat   = array(); // 缓存订单号，排查重复单号

    for ($i = 2; $i <= $maxRows; ++$i) { // 排除表头，从第2行开始读取
      $orderCode = trim($sheetObj->getCell('A' . $i)->getValue());

      if ('' !== $orderCode) {
        if (isset($repeat[$orderCode])) {
          continue ;
        }

        $repeat[$orderCode] = $orderCode;
      }
    }
$total=0;
$startIndex=0;
$data=array();
while($pieceOrder=array_slice($repeat, $startIndex,50,true)){
    $result=self::getQueryOrder(array('o_or_r_code'=>$pieceOrder), $type = '*');
    if(!empty($result)){
        $data=  array_merge($data,$result);
        $total+=count($result);
    }
    $startIndex+=50;
}
if (!empty($data)) {
    $data['total']=$total;
      $tmp   = date('YmdHis-') . md5('RETURN-BATCHSEARCH-' . microtime(TRUE)) . '.php'; // 临时文件名
      $cache = '<?php return ' . var_export($data, TRUE) . '; ?>'; // 缓存内容
  
      if (FALSE === file_put_contents($cacheDir . $tmp, $cache)) { // 生成缓存文件
        $response['message'] = '生成缓存文件时发生异常';
      }
      else {
        $response = array('status' => 1, 'message' => $tmp);
      }
    }
    else {
      $response['message'] = '没有找到相匹配的数据';
    }

    unset($data);
    unset($repeat);
    @unlink($file); // 删除文件

    return $response;
  }
  public static function batchExport($orderIdArr){
         set_time_limit(0);
        $condition['order_id_array']=$orderIdArr;
        @ini_set('memory_limit','1024M');
        $csvTitle = array();
        $csvTitle[0] =   array(
        '订单模式','订单状态','订单号','客户代码','是否换单','服务商单号','仓库','订单类型',
        '收件人国家','收件人国家（英文名称）','国家简码','提交时间','国内海关总申报价值',
        '目的海关申报总价','运输方式','交易订单号','收件人姓名','收件人公司名','收件人州\区域',
        '收件人城市','收件人邮编','收件人地址1','收件人地址2','收件人电话','收件人电子邮件',
        '成交币种','成交总价','派送地址','出货时间','体积重','长*宽*高','出货重量','计费总量',
        '件数','产品总数','备注','创建人');
          //头部获取
        $maxCountProduct = Service_OrderProduct::getMaxCountPorduct();       
        for($i=1;$i<=$maxCountProduct;$i++){
            $csvTitle[0][]   =   '产品名称'. $i;
            $csvTitle[0][]   =   'sku'. $i;
            $csvTitle[0][]   =   '入库时间'. $i;
            $csvTitle[0][]   =   '英文品名'. $i;
            $csvTitle[0][]   =   '申报单价'. $i .'(USD)';
            $csvTitle[0][]   =   '目的海关申报单价'. $i . '(USD)';
            $csvTitle[0][]   =   '数量'. $i;
            $csvTitle[0][]   =   '海关品名'. $i;
            $csvTitle[0][]   =   '料件号'. $i;
            $csvTitle[0][]   =   '海关编码'. $i;                
        }  

        echo Common_Export::exportCsvForNotKey($csvTitle);
        unset($csvTitle);
           $index = 1;
            $serviceClass=new Service_Orders();
        $count = $serviceClass->getOrderInnerJoinProductByCondition($condition, 'count(*)');
        if($count>0){
            $statusArr = Common_Status::orderStatus();
            $pageSize = 100;
            $totalPage = ceil($count/$pageSize);
            for($page=1;$page<=$totalPage;$page++){
                $csvData = array();
                $rows = $serviceClass->getOrderInnerJoinProductByCondition($condition,'order_code', $pageSize, $page, array('orders.order_id desc'));
                foreach ($rows as $key => $val) {
                    $orderRow = Service_Orders::getByField($val['order_code'],"order_code","*");
                    //订单模式
                    if($orderRow['order_mode_type']=="1"){
                        $csvData[$index][0]  = '集货模式';                   
                    }else{
                        $csvData[$index][0]  = '备货模式';
                    }
                    //客户代码
                    $customerRow = Service_Customer::getByField($orderRow['customer_code'],"customer_code","*");
                    //服务商单号
                    $shipOrder = Service_ShipOrder::getByField($orderRow['order_code'],"order_code","*");
                    $trackingNumber = isset($shipOrder['tracking_number'])?$shipOrder['tracking_number']:"";
                    //仓库
                    $warehouse = Service_Warehouse::getByField($orderRow['warehouse_id'],"warehouse_id","*");
                    //收件人国家
                    $osa = Service_OrderAddressBook::getByCondition(array('order_code'=>$orderRow['order_code'],'oab_type'=>'0'),"*");
                    $orderSendAddress = $osa[0];
                    $country = Service_Country::getByField($orderSendAddress['oab_country_id'],"country_id","*");
                    // 提交时间
                    $opt = Service_OrderOperationTime::getByField($orderRow['order_code'],'order_code',"*");
                    $csvData[$index][1]  = $statusArr[$orderRow['order_status']];
                    $csvData[$index][2]  = $orderRow['order_code'];
                    $csvData[$index][3] = $customerRow['customer_company_name'];
                    
                    if($orderRow['change_order']=="1"){
                        $csvData[$index][4]  = '是';
                    }else{
                        $csvData[$index][4]  = '否';
                    }               
                    $csvData[$index][5]  = $trackingNumber;
                    $csvData[$index][6]  = $warehouse['warehouse_code'];

                    
                    if($orderRow['order_type']=="2"){
                        $csvData[$index][7]  = '退货';                    
                    }elseif($orderRow['order_type']=="1"){
                        $csvData[$index][7]  = '转仓';                    
                    }else{
                        $csvData[$index][7]  = '普通';
                    }

                    $csvData[$index][8]  =   $country['country_name'];
                    $csvData[$index][9]  =   $country['country_name_en'];
                    $csvData[$index][10]  =   $country['country_code'];                
                    $csvData[$index][11]  =   $opt['submit_time'];

                    $csvData[$index][14]  =   $orderRow['sm_code'];
                    $csvData[$index][15]  =   $orderRow['reference_no'];
                    $csvData[$index][16]  =   $orderSendAddress['oab_firstname'];

                    $csvData[$index][17]  =   $orderSendAddress['oab_company'];
                    $csvData[$index][18]  =   $orderSendAddress['oab_state'];
                    $csvData[$index][19]  =   $orderSendAddress['oab_city'];
                    $csvData[$index][20]  =   $orderSendAddress['oab_postcode'];
                    $csvData[$index][21]  =   $orderSendAddress['oab_street_address1'];
                    $csvData[$index][22]  =   $orderSendAddress['oab_street_address2'];
                    $csvData[$index][23]  =   $orderSendAddress['oab_phone'];
                    $csvData[$index][24]  =   $orderSendAddress['oab_email'];
                    $csvData[$index][25]  =   $orderRow['currency_code'];
                    //aa
                    $csvData[$index][26]  =   $orderRow['charge'];
                    $csvData[$index][27]  =   $orderRow['delivery_address'];
                    $csvData[$index][28]  =   $opt['ship_time'];           
                                
                    //体积重
                    $volWeight = 0;
                    $shipOrderDetail = Service_ShipOrderDetail::getByCondition(array('order_code'=>$orderRow['order_code']),"*");
                    $smRow = Service_ShippingMethod::getByField($orderRow['sm_code'],"sm_code","*");
                    $LWH = "";
                    // HKDHL的长宽高取ship_order_detail表的长宽高，体积重根据长宽高另外计算
                    // 非HKDHL得长宽高、体积重取ship_order表的长宽高、体积重
                    if ('1' == $smRow['sm_is_volume'] && !empty($shipOrderDetail)) {
                      foreach($shipOrderDetail as $sodK=>$sodV){
                        if($smRow['sm_vol_rate']!="0"&&$smRow['sm_vol_rate']!="")
                        $volWeight = $volWeight +$sodV['sod_length']*$sodV['sod_width']*$sodV['sod_height']/$smRow['sm_vol_rate'];
                        if($sodK=="0"){
                            $LWH.=$sodV["sod_length"]."*".$sodV["sod_width"]."*".$sodV["sod_height"];
                        }else{
                            $LWH.="/".$sodV["sod_length"]."*".$sodV["sod_width"]."*".$sodV["sod_height"];
                        }
                      }
                    }
                    elseif (!empty($shipOrder)) {
                      $volWeight = $shipOrder['so_vol_weight'];
                      $LWH = $shipOrder['so_length'] . '*' . $shipOrder['so_width'] . '*' . $shipOrder['so_height'];
                    }
                    $shipWeight = isset($shipOrder['so_weight'])?$shipOrder['so_weight']:"";
                    $feeWeight = isset($shipOrder['so_fee_weight'])?$shipOrder['so_fee_weight']:"";
                    //ad
                    $csvData[$index][29]  =   $volWeight;   
                    $csvData[$index][30]  =   $LWH;   
                    $csvData[$index][31]  =   $shipWeight;   
                    $csvData[$index][32]  =   $feeWeight;   
                    $Total = 0;
                    if($smRow['sm_is_volume']!="1") {
                        $Total = 1;
                    }else{
                        $sodList = Service_ShipOrderDetail::getByCondition(array('order_code'=>$orderRow['order_code']),"*");
                        if($smRow['sm_code']=="HKDHL"){
                            $Total = count($sodList);
                        }else{
                            foreach($sodList as $sodRow){
                                if($sodRow['sub_tracking_number']!="") $Total++;
                            }
                        }
                    }
                    if($Total<1) $Total = 1;
                    $csvData[$index][33]  =   $Total; 
                    $csvData[$index][35]  =   $orderRow['remark']; 

               
                    $creater = "";
                    if(isset($opt['creater_id'])&&$opt['creater_id']!="0"){
                        $account = Service_Account::getByField($opt['creater_id'],'account_id',"*");
                        if(empty($account)){
                            $creater = $orderRow['customer_code'];
                        }else{
                            $creater = $account['account_name'];
                        }
                    }else{
                        $creater = $orderRow['customer_code'];
                    }
                    $csvData[$index][36]  =   $creater;                 
                    $orderProduct = Service_OrderProduct::getByCondition(array('order_code'=>$orderRow['order_code']),"*");

                    $totalProduct = 0;
                    $op_declared_value = 0;
                    $op_purpose_declared_value = 0;
                    $columnCount = 37;
                    foreach($orderProduct as $k=>$v){
                        $totalProduct +=$v['op_quantity'];
                        $op_declared_value +=$v['op_quantity']*$v['op_declared_value'];
                        $op_purpose_declared_value +=$v['op_quantity']*$v['op_purpose_declared_value'];
                        $p = Service_Product::getByField($v['product_id'],"product_id","*");

                        $pickingDetail = Service_PickingDetail::getByCondition(array('order_code'=>$v['order_code'],'product_id'=>$v['product_id']),"*");
                        
                        $ib_fifo_time = "";
                        if(!empty($pickingDetail)){
                            $inventoryBatchLog = Service_InventoryBatchLog::getByCondition(array('ib_id'=>$pickingDetail[0]['ib_id'],'application_code'=>'Putaway','ibl_quantity_before'=>'0'),"*",0,0,'ibl_id asc');
                            if(!empty($inventoryBatchLog))
                            $ib_fifo_time = $inventoryBatchLog[0]['ibl_add_time'];
                        }

                        $csvData[$index][$columnCount++]  =   $p['product_title'];     
                        $csvData[$index][$columnCount++]  =   $p['product_sku'];     
                        $csvData[$index][$columnCount++]  =   $ib_fifo_time;  
                        $csvData[$index][$columnCount++]  =   $v['product_title_en'];  
                        $csvData[$index][$columnCount++]  =   $v['op_declared_value'];     

                        $csvData[$index][$columnCount++]  =   $v['op_purpose_declared_value'];     
                        $csvData[$index][$columnCount++]  =   $v['op_quantity'];
                        $csvData[$index][$columnCount++]  =   $p['hs_goods_name']; 
                        $csvData[$index][$columnCount++]  =   $p['goods_id']; 
                        $csvData[$index][$columnCount++]  =   $p['hs_code']; 
                    }
                    $csvData[$index][12]  =   $op_declared_value; 
                    $csvData[$index][13]  =   $op_purpose_declared_value; 
                    $csvData[$index][34]  =   $totalProduct;    
                    ksort($csvData[$index]);  
                    $index++;
                }
                echo Common_Export::exportCsvForNotKey($csvData);
                $csvData = array();
            }  
                     
        }
        header('Content-Type: application/vnd.ms-excel;charset=gbk');
        header("Content-Disposition: attachment;filename=orderlist".date("YmdHis").".csv");
        header('Cache-Control: max-age=0');

        die();
  }
   public static function getPrintNo(){
        $table= new Table_Orders();
        $condition=array(
             'application_code' =>'HJTW_SEQUESE',
        );
         $application = Service_Application::getByCondition($condition, '*');
         if(empty($application)){
             $addRow=array( 
                 'application_code' =>'HJTW_SEQUESE',
                 'application_name'=>'TWPG与TWPP面单序列号',
                 'current_number'=>'0',
                 'rule'=>1,
                 'app_add_time'=>date('Y-m-d H:i:s'),
                 );
                     
             Service_Application::add($addRow);
             $application[0]=$addRow;
         }
          $start=  $application[0]['current_number'];
          $loopNumber=1;
          $endLoop='2';//正式2
          $startMax=99;//正式99
          $dayMax=1500;//正式1500
          $twoweekMax=5000;//正式5000
        do{
            $printNo=  '100561-0016'.str_pad($start,'2','0',STR_PAD_LEFT);
           
    
            $printCondition=array(
                    'sm_code_in'=>array('TWPG','TWPP'),
                    'confirmDateFor'=>date('Y-m-d').' 00:00:00',
                    'confirmDateTo'=>date('Y-m-d').' 23:59:59',
                    'print_no'=>$printNo,
            );
            $count=  $table->getLeftJoinAllByCondition($printCondition,'count(*)');
            
            $twoWeekCountCondition=array(
                     'sm_code_in'=>array('TWPG','TWPP'),
                    'confirmDateFor'=>date('Y-m-d',  strtotime('-15 days',strtotime(date('Y-m-d')))).' 00:00:00',
                    'confirmDateTo'=>date('Y-m-d').' 23:59:59',
                    'print_no'=>$printNo,
            );
            $twoWeekCount=  $table->getLeftJoinAllByCondition($twoWeekCountCondition,'count(*)');   
            
            if($count<$dayMax&&$twoWeekCount<$twoweekMax){
                $updateRow=array(
                    'current_number'=>$start,
                    'app_update_time'=>date('Y-m-d H:i:s'),
                );
                Service_Application::update($updateRow, $application[0]['application_id']);
                return $printNo;
            }
            if($start==$startMax){
                 $updateRow=array(
                    'current_number'=>0,
                     'app_update_time'=>date('Y-m-d H:i:s'),
                );
                Service_Application::update($updateRow, $application[0]['application_id']);
                $start=-1;//
                $loopNumber+=1;
            }
            $start++;
        }while($loopNumber<$endLoop);
       return '';
                    
                
    }
    public function checkPrintNo($printNo){
              $table= new Table_Orders();
            $printCondition=array(
                    'sm_code_in'=>array('TWPG','TWPP'),
                    'confirmDateFor'=>date('Y-m-d').' 00:00:00',
                    'confirmDateTo'=>date('Y-m-d').' 23:59:59',
                    'print_no'=>$printNo,
            );
            $count=  $table->getLeftJoinAllByCondition($printCondition,'count(*)');
  
            $twoWeekCountCondition=array(
                     'sm_code_in'=>array('TWPG','TWPP'),
                    'confirmDateFor'=>date('Y-m-d',  strtotime('-15 days',strtotime(date('Y-m-d')))).' 00:00:00',
                    'confirmDateTo'=>date('Y-m-d').' 23:59:59',
                    'print_no'=>$printNo,
            );
            $twoWeekCount=  $table->getLeftJoinAllByCondition($twoWeekCountCondition,'count(*)');  
             if($count>1500||$twoWeekCount>5000){
                return false;
            }
            return true;
   }
    //检查是否有跟踪号
    protected function hasRefTrackingNumber( $orderCode ) {
        $orderRow = Service_Orders::getByField( $orderCode, 'order_code');
        if( empty( $orderRow ) ) {
            return false;
        } else {
            $warehouse = Common_DataCache::getWarehouse(0,$orderRow['warehouse_id']);
            if( $orderRow['customer_code'] == 'E0693'
                &&  $warehouse['warehouse_code'] = 'SZ01'
                && in_array( $orderRow['sm_code'], array('HKDHL','BH-HKDHL') )
                && empty( $orderRow['ref_tracking_number'] ) )
                return false;
        }
        return true;
    }

    public static function getPlateForm() {
        return array(
            0 => 'OMS系统',
            1 => '分销平台',
            //2 => '环球平台'
        );
    }

    public function dealSerial($con1,$batch,$qty,$p,$order_code){
        $inventoryBatchSerialList = Service_InventoryBatchSerial::getByCondition($con1, '*',0,0,'ib_id asc');
        if(!empty($inventoryBatchSerialList)){
            $forUseQty = $qty;
            foreach($inventoryBatchSerialList as $ibsl){
                $sumIbslBount = Service_InventoryBatchSerialOutbound::getByCondition(array('ibs_id'=>$ibsl['ibs_id']),"sum(ibso_quantity) as sumIbslBount");
                if (empty($sumIbslBount)) {
                    $haveUseQty = 0;
                } else {
                    $haveUseQty = $sumIbslBount[0]['sumIbslBount'];
                }
                $ibsl['ibs_quantity']-=$haveUseQty;
                if($forUseQty<=$ibsl['ibs_quantity']){
                    //$forUseQuantity = $qty;
                    $IbsLBoundRow = array(
                        'reference_no' => $order_code,
                        'application_code' => 'pickup',
                        'ibso_quantity' => $forUseQty,
                        'ibs_id' => $ibsl['ibs_id'],
                        'ibso_add_time' => date('Y-m-d H:i:s')
                    );
                    Service_InventoryBatchSerialOutbound::add($IbsLBoundRow);
                    $searCon = array(
                        'order_code'=>$order_code,
                        'product_id'=>$p['product_id'],
                        'goods_id'=>$p['goods_id'],
                        'from_product_id'=>$batch['from_product_id'],
                        'hs_serial_no'=>$ibsl['hs_serial_no'],
                        'batch_goods_id'=>$ibsl['batch_goods_id'],
                    );
                    $existOg = Service_OrderGoods::getByCondition($searCon,"*");
                    if(empty($existOg)){
                        $OrderGoods = array(
                            'order_code'=>$order_code,
                            'product_id'=>$p['product_id'],
                            'goods_id'=>$p['goods_id'],
                            'good_quantity'=>$forUseQty,
                            'from_product_id'=>$batch['from_product_id'],
                            'hs_serial_no'=>$ibsl['hs_serial_no'],
                            'batch_goods_id'=>$ibsl['batch_goods_id'],
                            'hs_code'=>$p['hs_code'],
                        );
                        Service_OrderGoods::add($OrderGoods);
                    }else{
                        $updateOg = array(
                            'good_quantity'=>$existOg[0]['good_quantity']+$forUseQty
                        );
                        Service_OrderGoods::update($updateOg,$existOg[0]['og_id'],'og_id');
                    }
                    $forUseQty = 0;
                    break;
                }else{
                    //$toUseQty = $ibsl['ibs_quantity'];
                    if ($ibsl['ibs_quantity'] <= 0) {
                        continue;
                    }
                    $IbsLBoundRow = array(
                        'reference_no' => $order_code,
                        'application_code' => 'pickup',
                        'ibso_quantity' => $ibsl['ibs_quantity'],
                        'ibs_id' => $ibsl['ibs_id'],
                        'ibso_add_time' => date('Y-m-d H:i:s')
                    );
                    Service_InventoryBatchSerialOutbound::add($IbsLBoundRow);
                    $searCon = array(
                        'order_code'=>$order_code,
                        'product_id'=>$p['product_id'],
                        'goods_id'=>$p['goods_id'],
                        'from_product_id'=>$batch['from_product_id'],
                        'hs_serial_no'=>$ibsl['hs_serial_no'],
                        'batch_goods_id'=>$ibsl['batch_goods_id'],
                    );
                    $existOg = Service_OrderGoods::getByCondition($searCon,"*");
                    if(empty($existOg)){
                        $OrderGoods = array(
                            'order_code'=>$order_code,
                            'product_id'=>$p['product_id'],
                            'goods_id'=>$p['goods_id'],
                            'good_quantity'=>$ibsl['ibs_quantity'],
                            'from_product_id'=>$batch['from_product_id'],
                            'hs_serial_no'=>$ibsl['hs_serial_no'],
                            'batch_goods_id'=>$ibsl['batch_goods_id'],
                            'hs_code'=>$p['hs_code'],
                        );
                        Service_OrderGoods::add($OrderGoods);
                    }else{
                        $updateOg = array(
                            'good_quantity'=>$existOg[0]['good_quantity']+$ibsl['ibs_quantity']
                        );
                        Service_OrderGoods::update($updateOg,$existOg[0]['og_id'],'og_id');
                    }
                    $forUseQty -= $ibsl['ibs_quantity']; //扣除已经处理的
                }
            }
            if($forUseQty>0){
                throw new Exception('[' . $p['product_barcode'] . '] batch_serial not enough',10086);
            }
        }else{
            if($batch['from_product_id']>0){
                $fromProduct = Service_Product::getByField($batch['from_product_id'],'product_id');
            }else{
                $fromProduct = Service_Product::getByField($batch['product_id'],'product_id');
            }
            $OrderGoods = array(
                'order_code'=>$order_code,
                'product_id'=>$p['product_id'],
                'goods_id'=>$fromProduct['goods_id'],
                'good_quantity'=>$qty,
                'from_product_id'=>$fromProduct['product_id'],
                'hs_serial_no'=>$batch['hs_serial_no'],
                'batch_goods_id'=>$batch['batch_goods_id'],
                'hs_code'=>$p['hs_code'],
            );
            Service_OrderGoods::add($OrderGoods);
        }
        return true;
    }
}
