统计功能常见实现方法:

(1)直接连表查询后展示(无需建表,直接查询单据的数据进行展示)

优点:

a. 实现简单

缺点:

a. 不适合大量数据的场景,不适合复杂查询的场景,不适合对性能要求较高的场景

b. 满足不了统计需求改变,或者未来的统计需求,即扩展是性能会大大降低

(2)使用定时任务构建数据到统计表(创建新的统计用的数据表,每天晚上定时任务同步单据的数据到统计表)

优点:

a. 适合大量数据的场景,适合复杂查询的场景,适合对性能要求较高的场景

b. 能满足任何的统计需求

缺点:

a. 开发周期较长,实现复杂

使用定时任务构建数据到统计表的实现方法如下:

主要使用贪心的思想,并使用了面向对象的思想,及使用了迭代器模式,装饰器模式

以下为程序流程图:

数据仓库统计开发最佳实践-LMLPHP

实现代码如下:

WmsStatisticsBase.php

主要完成统计基本表的业务逻辑

<?php

namespace core\models;

use Yii;
use \yii\helpers\Console;

class WmsStatisticsBase extends \common\models\WmsStatisticsBase
{

    const HANDLE_IN = 'handleIn';//处理确认入库
    const HANDLE_IN_DELETE = 'handleInDelete';//处理入库单作废
    const HANDLE_OUT = 'handleOut';//处理确认出库
    const HANDLE_OUT_DELETE = 'handleOutDelete';//处理出库单作废

    const RUN_STATUS_NOT = 0;//从未运行过
    const RUN_STATUS_RUNNING = 1;//运行中
    const RUN_STATUS_FINISH = 2;//运行完成
    const RUN_STATUS_EXCEPTION = 3;//异常

    public $wms_statistics_date_begin;//生成统计数据开始日期
    public $wms_statistics_date_end;//生成统计数据截止日期
    public $handle_type;//处理类型
    public $show_output;//是否显示输出打印流

    protected $decorator = [];//这是装饰器列表

    /**
     * @return array
     * 重写行为自动更新记录时间
     */
    public function behaviors()
    {
        return [
            [
                'class' => \yii\behaviors\TimestampBehavior::className(),
                'createdAtAttribute' => 'created_at',
                'updatedAtAttribute' => 'updated_at',
            ],
        ];
    }

    /**
     * @return array
     * 验证规则
     */
    public function rules()
    {
        return array_merge(parent::rules(), [
            [['wms_statistics_date_begin', 'wms_statistics_date_end'], 'integer'],
            [['handle_type'], 'string']
        ]);
    }


    /**
     * @param $decorator
     * 增加装饰器
     */
    public function addDecorator($decorator)
    {
        $this->decorator[] = $decorator;
    }

    /**
     * @param bool $runValidation
     * @param null $attributeNames
     * @return bool
     * 重写save方法,若为新记录则插入;若已经有该记录则返回false
     */
    public function save($runValidation = true, $attributeNames = null)
    {
        if ($this->getIsNewRecord()) {
            return $this->insert($runValidation, $attributeNames);
        } else {
            return false;
        }
    }

    /**
     * @param $relativeSheetNumber
     * @return false|null|string
     * 根据第三方单号获取
     */
    public static function getProduceOutSheetNumberByRelativeSheetNumber($relativeSheetNumber){
        return self::find()->select(['out_sheet_number'])->where(['and', ['relative_sheet_number'=>$relativeSheetNumber], ['>', 'total_weight_sub', 0]])->scalar();
    }

    /**
     * @param $inSheetNumber
     * @return string
     * 根据生产加工入库单号获取生产领料单号
     */
    public static function getProduceOutSheetNumberByInSheetNumberFromWmsSheet($inSheetNumber){
        if (strpos($inSheetNumber, 'YLRK') !== false){
            //原料入库不可能是生产加工入库
            $produceSheetNumber = '';
        }elseif (strpos($inSheetNumber, 'BCPRK') !== false){
            $produceSheetNumber = \core\models\WmsPartiallyProductInSheet::findOne(['wms_partially_product_in_sheet_number'=>$inSheetNumber])->produce_record_sheet_number;
        }elseif (strpos($inSheetNumber, 'CPRK') !== false){
            $produceSheetNumber = \core\models\WmsProductInSheet::findOne(['wms_product_in_sheet_number'=>$inSheetNumber])->produce_record_sheet_number;
        }else{
            //暂无其他入库类型
            $produceSheetNumber = '';
        }
        if (!empty($produceSheetNumber)){
            $outSheetNumber = \core\models\ProduceRecordSheet::findOne(['produce_record_sheet_code'=>$produceSheetNumber])->wms_material_out_sheet_number;
        }else{
            $outSheetNumber = '';
        }
        return $outSheetNumber;
    }

    /**
     * 根据出入库类型重新设置第三方单号
     */
    public function resetRelativeSheetNumber(){
        if ($this->in_and_out_type_name == '生产加工'){
            if ($this->total_weight_add >0 && empty($this->total_weight_sub)){
                if (!empty($outSheetNumber = self::getProduceOutSheetNumberByInSheetNumberFromWmsSheet($this->in_sheet_number))){
                    $this->relative_sheet_number = $outSheetNumber;
                }
            }
            if (empty($this->total_weight_add) && $this->total_weight_sub > 0){
                $this->relative_sheet_number = $this->out_sheet_number;
            }
        }
    }

    public function beforeHandleInReal(){

    }

    /**
     * @return bool
     * 处理入库
     */
    public function handleInReal(){
        $this->beforeHandleInReal();
        $saveResult = $this->save(false);
        if($saveResult){
            $this->afterHandleInReal();
        }
        return $saveResult;
    }

    public function afterHandleInReal(){
        foreach ($this->decorator as $decorator){
            $decorator->handleIn($this);
        }
    }


    public function beforeHandleInDeleteReal(){

    }

    /**
     * @return false|int
     * 处理入库作废
     */
    public function handleInDeleteReal(){
        $this->beforeHandleInDeleteReal();
        $deleteResult = $this->delete();
        if($deleteResult){
            $this->afterHandleInDeleteReal();
        }
        return $deleteResult;
    }

    public function afterHandleInDeleteReal(){
        foreach ($this->decorator as $decorator){
            $decorator->handleInDelete($this);
        }
    }


    public function beforeHandleOutReal(){

    }

    /**
     * @return bool
     * 处理出库
     */
    public function handleOutReal(){
        $this->beforeHandleOutReal();
        $saveResult = $this->save(false);
        if ($saveResult){
            $this->afterHandleOutReal();
        }
        return $saveResult;
    }

    public function afterHandleOutReal(){
        foreach ($this->decorator as $decorator){
            $decorator->handleOut($this);
        }
    }

    public function beforeHandleOutDeleteReal(){

    }

    /**
     * @return false|int
     * 处理出库作废
     */
    public function handleOutDeleteReal(){
        $this->beforeHandleOutDeleteReal();
        $deleteResult = $this->delete();
        if ($deleteResult){
            $this->afterHandleOutDeleteReal();
        }
        return $deleteResult;
    }

    public function afterHandleOutDeleteReal(){
        foreach ($this->decorator as $decorator){
            $decorator->handleOutDelete($this);
        }
    }

    /**
     * WmsStatisticsBase constructor.
     * @param array $wms_statistics_date_begin
     * @param $wms_statistics_date_end
     * 构造方法
     */
    public function __construct($wms_statistics_date_begin, $wms_statistics_date_end)
    {
        $this->wms_statistics_date_begin = $wms_statistics_date_begin;
        $this->wms_statistics_date_end = $wms_statistics_date_end;
    }

    /**
     * @param $wms_statistics_date_begin
     * 设置运行开始日期
     */
    public function setWmsStatisticsDateBegin($wms_statistics_date_begin){
        $this->wms_statistics_date_begin = $wms_statistics_date_begin;
    }

    /**
     * @param $wms_statistics_date_end
     * 设置运行结束日期
     */
    public function setWmsStatisticsDateEnd($wms_statistics_date_end){
        $this->wms_statistics_date_end = $wms_statistics_date_end;
    }

    /**
     * @param $show_output
     * 设置是否显示输出流
     */
    public function setShowOutput($show_output){
        $this->show_output = $show_output;
    }

    /**
     * @return mixed
     * 获取是否显示输出流
     */
    public function getShowOutput(){
        return $this->show_output;
    }

    /**
     * @param $content
     * @param $color
     * 屏幕打印流
     */
    public function output($content, $color, $tty){
        if($this->getShowOutput()){
            \core\components\OutputHelper::output($content, $color, $tty);
        }
    }

    /**
     * @param $sheetNumber
     * @return false|int
     * 根据单号获取出入库时间
     */
    public function getInOutAtBySheetNumber($sheetNumber){
        $sheetNumberPieces = explode('-', $sheetNumber);
        $atStrTemp = '20'.$sheetNumberPieces[2];
        $atStr = substr($atStrTemp, 0, 4).'-'.substr($atStrTemp, 4, 2).'-'.substr($atStrTemp, 6, 2);
        return strtotime($atStr);
    }

    /**
     * @param $inSheetNumber
     * @return bool
     * 判断是否有此入库单的信息
     */
    public function hasInSheetNumber($inSheetNumber){
        return self::find()->where(['and', ['in_sheet_number'=>$inSheetNumber], ['>', 'total_weight_add', 0]])->exists();
    }

    /**
     * @param $inSheetNumber
     * @return array|null|\yii\db\ActiveRecord
     * 根据入库单获取统计信息
     */
    public function getModelByInSheetNumber($inSheetNumber){
        return self::find()->where(['and', ['in_sheet_number'=>$inSheetNumber], ['>', 'total_weight_add', 0]])->one();
    }

    /**
     * @param $inSheetNumber
     * @return array|\yii\db\ActiveRecord[]
     * 根据入库单号获取所有的出入库记录
     */
    public function getAllModelsByInSheetNumber($inSheetNumber){
        return self::find()->where(['in_sheet_number'=>$inSheetNumber])->orderBy(['wms_statistics_date'=>SORT_ASC])->all();
    }

    /**
     * @param $relativeSheetNumber
     * @return array|\yii\db\ActiveRecord[]
     * 根据第三方单号获取所有的出入库记录
     */
    public function getAllModelsByRelativeSheetNumber($relativeSheetNumber){
        return self::find()->where(['relative_sheet_number'=>$relativeSheetNumber])->all();
    }

    /**
     * @param $outSheetNumber
     * @param $outSheetDetailId
     * @return bool
     * 判断是否有此出库单的信息
     */
    public function hasOutSheetNumber($outSheetNumber, $outSheetDetailId){
        return self::find()->where(['out_sheet_number'=>$outSheetNumber, 'out_sheet_detail_id'=>$outSheetDetailId])->exists();
    }

    /**
     * @param $outSheetNumber
     * @param $outSheetDetailId
     * @return array|null|\yii\db\ActiveRecord
     * 根据出库单获取统计信息
     */
    public function getModelByOutSheetNumber($outSheetNumber, $outSheetDetailId){
        return self::find()->where(['out_sheet_number'=>$outSheetNumber, 'out_sheet_detail_id'=>$outSheetDetailId])->one();
    }

    /**
     * @return false|int
     * 获取运行数据截止时间戳
     */
    public static function getLastRunAt(){
        $wmsStatisticsBaseModel = \common\models\WmsStatisticsBase::find()->select(['wms_statistics_date'])->orderBy(['wms_statistics_date'=>SORT_DESC])->one();
        if (empty($wmsStatisticsBaseModel)){
            $lastRunAt = 0;
        }else{
            $lastRunAt = $wmsStatisticsBaseModel->wms_statistics_date;
        }
        return strtotime('+1 day', strtotime(date('Y-m-d', $lastRunAt)));
    }

    /**
     * 获取最新运行时间
     */
    public static function getLastUpdatedAt(){
        $key = 'wms_statistics_base_last_updated_at';
        $value = 0;
        if (\Yii::$app->redis->exists($key)){
            $value = \Yii::$app->redis->get($key);
        }
        return $value;
    }

    /**
     * 设置上一次更新时间
     */
    public static function setLastUpdatedAt(){
        \Yii::$app->redis->set('wms_statistics_base_last_updated_at', time());
    }

    /**
     * @return int
     * 获取运行状态
     */
    public static function getRunStatus(){
        $key = 'wms_statistics_base_run_status';
        $value = \core\models\WmsStatisticsBase::RUN_STATUS_NOT;
        if (\Yii::$app->redis->exists($key)){
            $value = \Yii::$app->redis->get($key);
        }
        return $value;
    }

    /**
     * @param $runStatus
     * 设置运行状态
     */
    public static function setRunStatus($runStatus){
        \Yii::$app->redis->set('wms_statistics_base_run_status', $runStatus);
    }

    /**
     * 能否运行
     */
    public static function canRun(){
        $runStatus = \core\models\WmsStatisticsBase::getRunStatus();
        if (\core\models\WmsStatisticsBase::RUN_STATUS_RUNNING == $runStatus){
            return false;
        }else{
            return true;
        }
    }

    /**
     * @return \Generator|void
     * 迭代器生成统计模型
     */
    public function iteratorGen(){
        //处理原料
        $materialWmsStatisticsBase = new MaterialWmsStatisticsBase();
        $materialWmsStatisticsBase->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
        $materialWmsStatisticsBase->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
        $wmsMaterialInSheetModels = $materialWmsStatisticsBase->getWmsInSheet();

        foreach ($wmsMaterialInSheetModels as $wmsMaterialInSheetModel){
            if (!empty($wmsMaterialInSheetModel->wms_material_in_sheet_status) && empty($wmsMaterialInSheetModel->is_del)) {
                $className = '\core\models\MaterialWmsStatisticsBase';
                $funcName = 'handleIn';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsMaterialInSheetModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsMaterialInSheetModel);
                yield $wmsStatisticsBaseModel;
            }
            elseif (!empty($wmsMaterialInSheetModel->wms_material_in_sheet_status) && !empty($wmsMaterialInSheetModel->is_del)){
                $className = '\core\models\MaterialWmsStatisticsBase';
                $funcName = 'handleInDelete';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsMaterialInSheetModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsMaterialInSheetModel);
                yield $wmsStatisticsBaseModel;
            }
            else{
                unset($wmsMaterialInSheetModel);
                yield null;
            }
        }
        unset($wmsMaterialInSheetModels);

        $wmsMaterialOutSheetDetailModels = $materialWmsStatisticsBase->getWmsOutSheetDetail();
        unset($materialWmsStatisticsBase);
        foreach ($wmsMaterialOutSheetDetailModels as $wmsMaterialOutSheetDetailModel){
            if (!empty($wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->wms_material_out_sheet_status) && empty($wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->is_del)){
                $className = '\core\models\MaterialWmsStatisticsBase';
                $funcName = 'handleOut';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsMaterialOutSheetDetailModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsMaterialOutSheetDetailModel);
                yield $wmsStatisticsBaseModel;
            }elseif (!empty($wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->wms_material_out_sheet_status) && !empty($wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->is_del)){
                $className = '\core\models\MaterialWmsStatisticsBase';
                $funcName = 'handleOutDelete';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsMaterialOutSheetDetailModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsMaterialOutSheetDetailModel);
                yield $wmsStatisticsBaseModel;
            }else{
                unset($wmsMaterialOutSheetDetailModel);
                yield null;
            }
        }
        unset($wmsMaterialOutSheetDetailModels);

        //处理成品
        $productWmsStatisticsBase = new ProductWmsStatisticsBase();
        $productWmsStatisticsBase->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
        $productWmsStatisticsBase->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
        $wmsProductInSheetModels = $productWmsStatisticsBase->getWmsInSheet();
        foreach ($wmsProductInSheetModels as $wmsProductInSheetModel){
            if (!empty($wmsProductInSheetModel->wms_product_in_sheet_status) && empty($wmsProductInSheetModel->is_del)) {
                $className = '\core\models\ProductWmsStatisticsBase';
                $funcName = 'handleIn';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsProductInSheetModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsProductInSheetModel);
                yield $wmsStatisticsBaseModel;
            }
            elseif (!empty($wmsProductInSheetModel->wms_product_in_sheet_status) && !empty($wmsProductInSheetModel->is_del)){
                $className = '\core\models\ProductWmsStatisticsBase';
                $funcName = 'handleInDelete';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsProductInSheetModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsProductInSheetModel);
                yield $wmsStatisticsBaseModel;
            }
            else{
                unset($wmsProductInSheetModel);
                yield null;
            }
        }
        unset($wmsProductInSheetModels);

        $wmsProductOutDetailInfoModels = $productWmsStatisticsBase->getWmsOutSheetDetail();
        unset($productWmsStatisticsBase);
        foreach ($wmsProductOutDetailInfoModels as $wmsProductOutDetailInfoModel){
            if (!empty($wmsProductOutDetailInfoModel->wmsProductOutSheet->wms_product_out_sheet_status) && empty($wmsProductOutDetailInfoModel->wmsProductOutSheet->is_del)){
                $className = '\core\models\ProductWmsStatisticsBase';
                $funcName = 'handleOut';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsProductOutDetailInfoModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsProductOutDetailInfoModel);
                yield $wmsStatisticsBaseModel;
            }elseif (!empty($wmsProductOutDetailInfoModel->wmsProductOutSheet->wms_product_out_sheet_status) && !empty($wmsProductOutDetailInfoModel->wmsProductOutSheet->is_del)){
                $className = '\core\models\ProductWmsStatisticsBase';
                $funcName = 'handleOutDelete';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsProductOutDetailInfoModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsProductOutDetailInfoModel);
                yield $wmsStatisticsBaseModel;
            }else{
                unset($wmsProductOutDetailInfoModel);
                yield null;
            }
        }
        unset($wmsProductOutDetailInfoModels);

        //处理半成品
        $partiallyProductWmsStatisticsBase = new PartiallyProductWmsStatisticsBase();
        $partiallyProductWmsStatisticsBase->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
        $partiallyProductWmsStatisticsBase->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
        $wmsPartiallyProductInSheetModels = $partiallyProductWmsStatisticsBase->getWmsInSheet();
        foreach ($wmsPartiallyProductInSheetModels as $wmsPartiallyProductInSheetModel){
            if (!empty($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_status) && empty($wmsPartiallyProductInSheetModel->is_del)) {
                $className = '\core\models\PartiallyProductWmsStatisticsBase';
                $funcName = 'handleIn';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsPartiallyProductInSheetModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsPartiallyProductInSheetModel);
                yield $wmsStatisticsBaseModel;
            }
            elseif (!empty($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_status) && !empty($wmsPartiallyProductInSheetModel->is_del)){
                $className = '\core\models\PartiallyProductWmsStatisticsBase';
                $funcName = 'handleInDelete';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsPartiallyProductInSheetModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsPartiallyProductInSheetModel);
                yield $wmsStatisticsBaseModel;
            }
            else{
                unset($wmsPartiallyProductInSheetModel);
                yield null;
            }
        }
        unset($wmsPartiallyProductInSheetModels);

        $wmsPartiallyProductOutDetailInfoModels = $partiallyProductWmsStatisticsBase->getWmsOutSheetDetail();
        unset($partiallyProductWmsStatisticsBase);
        foreach ($wmsPartiallyProductOutDetailInfoModels as $wmsPartiallyProductOutDetailInfoModel){
            if (!empty($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->wms_partially_product_out_sheet_status) && empty($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->is_del)){
                $className = '\core\models\PartiallyProductWmsStatisticsBase';
                $funcName = 'handleOut';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsPartiallyProductOutDetailInfoModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsPartiallyProductOutDetailInfoModel);
                yield $wmsStatisticsBaseModel;
            }elseif (!empty($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->wms_partially_product_out_sheet_status) && !empty($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->is_del)){
                $className = '\core\models\PartiallyProductWmsStatisticsBase';
                $funcName = 'handleOutDelete';
                $class = new \ReflectionClass($className);
                $instance = $class->newInstance();
                $funcReflection = $class->getMethod($funcName);
                $wmsStatisticsBaseModel = $funcReflection->invoke($instance, $wmsPartiallyProductOutDetailInfoModel);
                unset($className);
                unset($funcName);
                unset($class);
                unset($instance);
                unset($funcReflection);
                unset($wmsPartiallyProductOutDetailInfoModel);
                yield $wmsStatisticsBaseModel;
            }else{
                unset($wmsPartiallyProductOutDetailInfoModel);
                yield null;
            }
        }
        unset($wmsPartiallyProductOutDetailInfoModels);

        return;
    }

    /**
     * @return int
     * 运行
     */
    public function run($tty=0){
        try {
            $successNum = 0;
            $iteratorGen = $this->iteratorGen();
            foreach ($iteratorGen as $key => $genModel) {
                if (!empty($genModel) && $genModel != null) {
                    $transaction = \Yii::$app->db->beginTransaction();
                    try {
                        $genModel->addDecorator(new WmsStatisticsModel());
                        switch ($genModel->handle_type) {
                            case self::HANDLE_IN:
                                $this->output("[入库]正在处理入库单" . $genModel->in_sheet_number . "确认入库...", Console::FG_YELLOW, $tty);
                                if ($genModel->handleInReal(false)) {
                                    $successNum += 1;
                                    $this->output("[入库]处理入库单" . $genModel->in_sheet_number . "确认入库成功[增加:".$genModel->total_weight_add."减少:".$genModel->total_weight_sub."]", Console::FG_GREEN, $tty);
                                } else {
                                    $this->output("[入库]处理入库单" . $genModel->in_sheet_number . "已经确认入库,无需再次入库", Console::FG_RED, $tty);
                                }
                                break;
                            case self::HANDLE_IN_DELETE:
                                $this->output("[入库作废]正在处理入库单" . $genModel->in_sheet_number . "作废...", Console::FG_YELLOW, $tty);
                                if ($genModel->handleInDeleteReal()) {
                                    $successNum += 1;
                                    $this->output("[入库作废]处理入库单" . $genModel->in_sheet_number . "作废成功", Console::FG_GREEN, $tty);
                                } else {
                                    $this->output("[入库作废]处理入库单" . $genModel->in_sheet_number . "已经作废,无需再次作废", Console::FG_RED, $tty);
                                }
                                break;
                            case self::HANDLE_OUT:
                                $this->output("[出库]正在处理出库单" . $genModel->out_sheet_number . "确认出库...", Console::FG_YELLOW, $tty);
                                if ($genModel->handleOutReal(false)) {
                                    $this->output("[出库]处理出库单" . $genModel->out_sheet_number . "确认出库成功[增加:".$genModel->total_weight_add."减少:".$genModel->total_weight_sub."]", Console::FG_GREEN, $tty);
                                    $successNum += 1;
                                } else {
                                    $this->output("[出库]处理出库单" . $genModel->out_sheet_number . "已经确认出库,无需再次出库",Console::FG_RED, $tty);
                                }
                                break;
                            case self::HANDLE_OUT_DELETE:
                                $this->output("[出库作废]正在处理出库单" . $genModel->out_sheet_number . "作废...", Console::FG_YELLOW, $tty);
                                if ($genModel->handleOutDeleteReal()) {
                                    $this->output("[出库作废]正在处理出库单" . $genModel->out_sheet_number . "作废成功", Console::FG_GREEN, $tty);
                                    $successNum += 1;
                                } else {
                                    $this->output("[出库作废]正在处理出库单" . $genModel->out_sheet_number . "已经作废,无需再次作废", Console::FG_RED, $tty);
                                }
                                break;
                            default:
                                break;
                        }
                        $transaction->commit();
                    } catch (\yii\db\Exception $e) {
                        $transaction->rollBack();
                        $this->output("[异常]".$e->getMessage() . "已经成功回滚", Console::FG_RED, $tty);
                    }
                    unset($genModel);
                }
            }
            unset($iteratorGen);
            //添加再生产处理的行为
            $tourApplication = new \core\models\WmsStatisticsTour();
            $tourApplication->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
            $tourApplication->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
            $tourApplication->setShowOutput(true);
            $tourApplication->run($tty);

            //设置为运行完成
            self::setRunStatus(self::RUN_STATUS_FINISH);
            //添加运行结束标志日志
            $this->output("[运行成功]程序运行完成,自动退出", Console::FG_RED, $tty);

            //设置上一次更新时间
            $this->setLastUpdatedAt();
        }catch (\yii\base\Exception $ex){
            //设置运行状态为异常
            self::setRunStatus(self::RUN_STATUS_EXCEPTION);
            $this->output("[程序终止]".$ex->getMessage(), Console::FG_RED, $tty);
            try{
                $dingtalk_userid_list = ["07065922225593", "056812195221366111"];
                $content = "[库存统计程序终止]".$ex->getMessage();
                foreach ($dingtalk_userid_list as $dingtalk_userid){
                    \core\components\OutputHelper::ding($dingtalk_userid, $content);
                }
            }catch(\yii\base\Exception $except){

            }
        }finally{

        }
        return $successNum;
    }

    /**
     * @return int
     * 运行
     */
    public function templateRun($tty=0){
        //判断能否运行,不能运行则直接退出
        if (!$this->canRun()){
            $this->output("抱歉,另一客户端或线程正在运行此程序,不能运行", Console::FG_RED, $tty);
            exit(0);
        }
        //设置运行状态为正在运行
        $this->setRunStatus(self::RUN_STATUS_RUNNING);

        //调用行为
        $successNum = $this->run($tty);


        return $successNum;
    }

}

MaterialWmsStatisticsBase.php

继承自WmsMaterialBase.php

主要实现了原料相关统计的功能

<?php

namespace core\models;

use Yii;

class MaterialWmsStatisticsBase extends \core\models\WmsStatisticsBase
{
    /**
     * MaterialWmsStatisticsBase constructor.
     * 重写构造方法
     */
    public function __construct(){}

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取入库单列表
     */
    public function getWmsInSheet(){
        $wmsMaterialInSheetModels = \core\models\WmsMaterialInSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsMaterialInSheetModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取指定时间范围内的生产加工成品入库单是确认入库或作废
     */
    public function getWmsInSheetForProduce(){
        $wmsMaterialInSheetModels = \core\models\WmsMaterialInSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
            ['in', 'wms_material_in_sheet_type', ['生产加工']],
            ['or', ['wms_material_in_sheet_status'=>1], ['is_del'=>1]]
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsMaterialInSheetModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取出库详情列表
     */
    public function getWmsOutSheetDetail(){
        //注意:这里不能使用ID升序,应该使用出库日期升序,因为ID升序和出库日期出库不是对应的
        $wmsMaterialOutSheetDetailModels = \core\models\WmsMaterialOutSheetDetail::find()->where(['and',
            ['>=', '{{%wms_material_out_sheet_detail}}.updated_at', $this->wms_statistics_date_begin],
            ['<', '{{%wms_material_out_sheet_detail}}.updated_at', $this->wms_statistics_date_end],
        ])->joinWith(['wmsMaterialOutSheet'=>function($query){
            $query->orderBy(['{{%wms_material_out_sheet}}.wms_material_out_sheet_outgoing_date'=>SORT_ASC]);
        }])->all();
        return $wmsMaterialOutSheetDetailModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取指定时间范围内生产加工成品出库确认出库或出库作废
     */
    public function getWmsOutSheetForProduce(){
        $wmsMaterialOutSheetModels = \core\models\WmsMaterialOutSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
            ['in', 'wms_out_sheet_type', ['0', '生产加工']],
        ])->andWhere(['or', ['wms_material_out_sheet_status'=>1], ['is_del'=>1]])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsMaterialOutSheetModels;
    }

    /**
     * @param $inAndOutTypeInput
     * @return string
     * 清洗入库类型
     */
    public function mapInTypeName($inAndOutTypeInput){
        $inAndOutTypeName = '';
        if (empty($inAndOutTypeInput)){
            $inAndOutTypeName = '采购';
        }else{
            $inAndOutTypeName = $inAndOutTypeInput;
        }
        return $inAndOutTypeName;
    }

    /**
     * @param $inAndOutTypeInput
     * @return string
     * 清洗出库类型
     */
    public function mapOutTypeName($inAndOutTypeInput){
        $inAndOutTypeName = '';
        if (empty($inAndOutTypeInput)){
            $inAndOutTypeName = '生产加工';
        }else{
            $inAndOutTypeName = $inAndOutTypeInput;
        }
        return $inAndOutTypeName;
    }

    /**
     * @param $wmsMaterialInSheetModel
     * @return array|MaterialWmsStatisticsBase|null|\yii\db\ActiveRecord
     * 生成入库记录
     */
    public function handleIn($wmsMaterialInSheetModel){
        if ($this->hasInSheetNumber($wmsMaterialInSheetModel->wms_material_in_sheet_number)){
            $wmsStatisticsBaseModel = $this->getModelByInSheetNumber($wmsMaterialInSheetModel->wms_material_in_sheet_number);
        }else {
            $wmsStatisticsBaseModel = new \core\models\MaterialWmsStatisticsBase();

            $wmsStatisticsBaseModel->common_producer_info_id = $wmsMaterialInSheetModel->common_producer_info_id;
            $wmsStatisticsBaseModel->common_producer_info_name = \core\models\WmsTransfer::getCommonProducerInfoName($wmsMaterialInSheetModel->common_producer_info_id);
            $wmsStatisticsBaseModel->common_producer_herb_info_id = $wmsMaterialInSheetModel->common_producer_herb_info_id;
            $wmsStatisticsBaseModel->common_producer_herb_info_name = $wmsMaterialInSheetModel->common_producer_herb_info_name;
            $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsMaterialInSheetModel->common_producer_herb_grade_info_id;
            $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsMaterialInSheetModel->common_producer_herb_grade_name;

            $wmsStatisticsBaseModel->wms_statistics_date = !empty($wmsMaterialInSheetModel->wms_material_in_sheet_product_in_date) ? $wmsMaterialInSheetModel->wms_material_in_sheet_product_in_date : 0;
            $wmsStatisticsBaseModel->in_sheet_number = $wmsMaterialInSheetModel->wms_material_in_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_number = '';
            $wmsStatisticsBaseModel->out_sheet_detail_id = 0;
            $wmsStatisticsBaseModel->relative_sheet_number = $wmsMaterialInSheetModel->purchase_sheet_number;

            $wmsStatisticsBaseModel->wms_type = \core\models\WmsTransfer::WMS_TYPE_MATERIAL;
            $wmsStatisticsBaseModel->piece_type = $wmsMaterialInSheetModel->piece_type;
            $wmsStatisticsBaseModel->in_and_out_type_name = $this->mapInTypeName($wmsMaterialInSheetModel->wms_material_in_sheet_type);
            $wmsStatisticsBaseModel->weight_per_package = $wmsMaterialInSheetModel->wms_material_in_sheet_weight_per_package;
            $wmsStatisticsBaseModel->wms_statistics_text = $wmsMaterialInSheetModel->wms_material_in_sheet_note;

            $wmsStatisticsBaseModel->standard_package_number_add = $wmsMaterialInSheetModel->standard_package_number;
            $wmsStatisticsBaseModel->off_standard_package_number_add = $wmsMaterialInSheetModel->off_standard_package_number;
            $wmsStatisticsBaseModel->total_package_number_add = $wmsMaterialInSheetModel->wms_material_in_sheet_package_number;
            $wmsStatisticsBaseModel->standard_weight_add = $wmsMaterialInSheetModel->standard_weight;
            $wmsStatisticsBaseModel->off_standard_weight_add = $wmsMaterialInSheetModel->off_standard_weight;
            $wmsStatisticsBaseModel->total_weight_add = $wmsMaterialInSheetModel->wms_material_in_sheet_in_weight;

            $wmsStatisticsBaseModel->standard_package_number_sub = 0;
            $wmsStatisticsBaseModel->off_standard_package_number_sub = 0;
            $wmsStatisticsBaseModel->total_package_number_sub = 0;
            $wmsStatisticsBaseModel->standard_weight_sub = 0;
            $wmsStatisticsBaseModel->off_standard_weight_sub = 0;
            $wmsStatisticsBaseModel->total_weight_sub = 0;
        }
        $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
        //根据出入库类型重新设置第三方单号
        $wmsStatisticsBaseModel->resetRelativeSheetNumber();
        return $wmsStatisticsBaseModel;
    }

    /**
     * @param $wmsMaterialInSheetModel
     * @return array|null|\yii\db\ActiveRecord
     * 处理入库单作废
     */
    public function handleInDelete($wmsMaterialInSheetModel){
        if ($this->hasInSheetNumber($wmsMaterialInSheetModel->wms_material_in_sheet_number)){
            $wmsStatisticsBaseModel = $this->getModelByInSheetNumber($wmsMaterialInSheetModel->wms_material_in_sheet_number);
            $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
            return $wmsStatisticsBaseModel;
        }else{
            return null;
        }
    }

    /**
     * @param $wmsMaterialOutSheetDetailModel
     * @return array|MaterialWmsStatisticsBase|null|\yii\db\ActiveRecord
     * 处理出库
     */
    public function handleOut($wmsMaterialOutSheetDetailModel){
        if ($this->hasOutSheetNumber($wmsMaterialOutSheetDetailModel->wms_material_out_sheet_number, $wmsMaterialOutSheetDetailModel->id)){
            $wmsStatisticsBaseModel = $this->getModelByOutSheetNumber($wmsMaterialOutSheetDetailModel->wms_material_out_sheet_number, $wmsMaterialOutSheetDetailModel->id);
        }else {
            $wmsStatisticsBaseModel = new \core\models\MaterialWmsStatisticsBase();

            $wmsStatisticsBaseModel->common_producer_info_id = $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->common_producer_info_id;
            $wmsStatisticsBaseModel->common_producer_info_name = \core\models\WmsTransfer::getCommonProducerInfoName($wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->common_producer_info_id);
            if (isset($wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_info_id)){
                $wmsStatisticsBaseModel->common_producer_herb_info_id = $wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_info_id;
            }else{
                $wmsStatisticsBaseModel->common_producer_herb_info_id = $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->common_producer_herb_info_id;
            }
            if(isset($wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_info_name)){
                $wmsStatisticsBaseModel->common_producer_herb_info_name = $wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_info_name;
            }else{
                $wmsStatisticsBaseModel->common_producer_herb_info_name = $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->common_producer_herb_info_name;
            }
            if(isset($wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_grade_info_id)){
                $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_grade_info_id;
            }else{
                $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->common_producer_herb_grade_info_id;
            }
            if (isset($wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_grade_name)){
                $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->common_producer_herb_grade_name;
            }else{
                $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->common_producer_herb_grade_name;
            }

            //如果出库时间小于入库时间,则容错处理
            if (isset($wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->wms_material_in_sheet_product_in_date)
                && $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->wms_material_out_sheet_outgoing_date < $wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->wms_material_in_sheet_product_in_date){
                $wmsStatisticsBaseModel->wms_statistics_date = $wmsMaterialOutSheetDetailModel->wmsMaterialInSheet->wms_material_in_sheet_product_in_date;
            }else{
                $wmsStatisticsBaseModel->wms_statistics_date = !empty($wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->wms_material_out_sheet_outgoing_date) ? $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->wms_material_out_sheet_outgoing_date : 0;
            }
            $wmsStatisticsBaseModel->in_sheet_number = $wmsMaterialOutSheetDetailModel->wms_stock_detail_info_relation_good_in_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_number = $wmsMaterialOutSheetDetailModel->wms_material_out_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_detail_id = $wmsMaterialOutSheetDetailModel->id;
            $wmsStatisticsBaseModel->relative_sheet_number = $wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->produce_instruction_number;

            $wmsStatisticsBaseModel->wms_type = \core\models\WmsTransfer::WMS_TYPE_MATERIAL;
            $wmsStatisticsBaseModel->piece_type = $wmsMaterialOutSheetDetailModel->piece_type;
            $wmsStatisticsBaseModel->in_and_out_type_name = $this->mapOutTypeName($wmsMaterialOutSheetDetailModel->wmsMaterialOutSheet->wms_out_sheet_type);
            $wmsStatisticsBaseModel->weight_per_package = 0;
            $wmsStatisticsBaseModel->wms_statistics_text = $wmsMaterialOutSheetDetailModel->wms_material_out_sheet_detail_note;

            $wmsStatisticsBaseModel->standard_package_number_add = 0;
            $wmsStatisticsBaseModel->off_standard_package_number_add = 0;
            $wmsStatisticsBaseModel->total_package_number_add = 0;
            $wmsStatisticsBaseModel->standard_weight_add = 0;
            $wmsStatisticsBaseModel->off_standard_weight_add = 0;
            $wmsStatisticsBaseModel->total_weight_add = 0;

            $wmsStatisticsBaseModel->standard_package_number_sub = $wmsMaterialOutSheetDetailModel->standard_package_number;
            $wmsStatisticsBaseModel->off_standard_package_number_sub = $wmsMaterialOutSheetDetailModel->off_standard_package_number;
            $wmsStatisticsBaseModel->total_package_number_sub = $wmsMaterialOutSheetDetailModel->wms_material_out_sheet_detail_out_number;
            $wmsStatisticsBaseModel->standard_weight_sub = $wmsMaterialOutSheetDetailModel->standard_weight;
            $wmsStatisticsBaseModel->off_standard_weight_sub = $wmsMaterialOutSheetDetailModel->off_standard_weight;
            $wmsStatisticsBaseModel->total_weight_sub = $wmsMaterialOutSheetDetailModel->wms_material_out_sheet_detail_out_weight;
        }
        $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
        //根据出入库类型重新设置第三方单号
        $wmsStatisticsBaseModel->resetRelativeSheetNumber();
        return $wmsStatisticsBaseModel;
    }

    /**
     * @param $wmsMaterialOutSheetDetailModel
     * @return array|null|\yii\db\ActiveRecord
     * 处理出库作废
     */
    public function handleOutDelete($wmsMaterialOutSheetDetailModel){
        if ($this->hasOutSheetNumber($wmsMaterialOutSheetDetailModel->wms_material_out_sheet_number, $wmsMaterialOutSheetDetailModel->id)){
            $wmsStatisticsBaseModel = $this->getModelByOutSheetNumber($wmsMaterialOutSheetDetailModel->wms_material_out_sheet_number, $wmsMaterialOutSheetDetailModel->id);
            $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
            return $wmsStatisticsBaseModel;
        }else{
            return null;
        }
    }
}

ProductWmsStatisticsBase.php

继承自WmsStatisticsBase

主要完成了成品的相关统计的功能

<?php

namespace core\models;

use Yii;

class ProductWmsStatisticsBase extends \core\models\WmsStatisticsBase
{
    /**
     * ProductWmsStatisticsBase constructor.
     * 重写构造方法
     */
    public function __construct(){}

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取成品入库单列表
     */
    public function getWmsInSheet(){
        $wmsProductInSheetModels = \core\models\WmsProductInSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsProductInSheetModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取指定时间范围内的生产加工成品入库单是确认入库或作废
     */
    public function getWmsInSheetForProduce(){
        $out_sheet_number_list = [];
        $wmsProductInSheetModels = \core\models\WmsProductInSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
            ['or', ['wms_product_in_sheet_status'=>1], ['is_del'=>1]],
            ['or', ['stock_origin_type'=>NULL], ['stock_origin_type'=>'生产加工']]
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsProductInSheetModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取成品出库单详情列表
     */
    public function getWmsOutSheetDetail(){
        //注意:这里不能使用ID升序,应该使用出库日期升序,因为ID升序和出库日期出库不是对应的
        $wmsProductOutDetailInfoModels = \core\models\WmsProductOutDetailInfo::find()->where(['and',
            ['>=', '{{%wms_product_out_detail_info}}.updated_at', $this->wms_statistics_date_begin],
            ['<', '{{%wms_product_out_detail_info}}.updated_at', $this->wms_statistics_date_end],
        ])->joinWith(['wmsProductOutSheet'=>function($query){
            $query->orderBy(['{{%wms_product_out_sheet}}.wms_product_out_sheet_product_out_date'=>SORT_ASC]);
        }])->all();
        return $wmsProductOutDetailInfoModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取指定时间范围内生产加工成品出库确认出库或出库作废
     */
    public function getWmsOutSheetForProduce(){
        $wmsProductOutSheetModels = \core\models\WmsProductOutSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
            ['in', 'wms_product_out_sheet_type', [\common\models\ProduceInstruction::OPT_TYPE]],
            ['or', ['wms_product_out_sheet_status'=>1], ['is_del'=>1]]
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsProductOutSheetModels;
    }

    /**
     * @param $inAndOutTypeInput
     * @return string
     * 清洗入库类型
     */
    public function mapInTypeName($inAndOutTypeInput){
        $inAndOutTypeName = '';
        if (empty($inAndOutTypeInput)){
            $inAndOutTypeName = '生产加工';
        }else{
            $inAndOutTypeName = $inAndOutTypeInput;
        }
        return $inAndOutTypeName;
    }

    /**
     * @param $inAndOutTypeInput
     * @return string
     * 清洗出库类型
     */
    public function mapOutTypeName($inAndOutTypeInput){
        $inAndOutTypeName = '';
        if (empty($inAndOutTypeInput)){
            $inAndOutTypeName = '销售';
        }else{
            $inAndOutTypeName = $inAndOutTypeInput;
        }
        return $inAndOutTypeName;
    }

    /**
     * @param $wmsProductInSheetModel
     * @return array|ProductWmsStatisticsBase|null|\yii\db\ActiveRecord
     * 处理生成入库单
     */
    public function handleIn($wmsProductInSheetModel){
        if ($this->hasInSheetNumber($wmsProductInSheetModel->wms_product_in_sheet_number)){
            $wmsStatisticsBaseModel = $this->getModelByInSheetNumber($wmsProductInSheetModel->wms_product_in_sheet_number);
        }else {
            $wmsStatisticsBaseModel = new \core\models\ProductWmsStatisticsBase();

            $wmsStatisticsBaseModel->common_producer_info_id = $wmsProductInSheetModel->common_producer_info_id;
            $wmsStatisticsBaseModel->common_producer_info_name = \core\models\WmsTransfer::getCommonProducerInfoName($wmsProductInSheetModel->common_producer_info_id);
            $wmsStatisticsBaseModel->common_producer_herb_info_id = $wmsProductInSheetModel->common_producer_herb_info_id_product;
            $wmsStatisticsBaseModel->common_producer_herb_info_name = $wmsProductInSheetModel->common_producer_herb_info_name_product;
            $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsProductInSheetModel->common_producer_herb_grade_info_id_product;
            $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsProductInSheetModel->common_producer_herb_grade_name_product;

            $wmsStatisticsBaseModel->wms_statistics_date = !empty($wmsProductInSheetModel->wms_product_in_sheet_product_in_date) ? $wmsProductInSheetModel->wms_product_in_sheet_product_in_date : 0;
            $wmsStatisticsBaseModel->in_sheet_number = $wmsProductInSheetModel->wms_product_in_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_number = '';
            $wmsStatisticsBaseModel->out_sheet_detail_id = 0;
            $wmsStatisticsBaseModel->relative_sheet_number = $wmsProductInSheetModel->wms_product_in_sheet_relative_sheet_number;

            $wmsStatisticsBaseModel->wms_type = \core\models\WmsTransfer::WMS_TYPE_PRODUCT;
            $wmsStatisticsBaseModel->piece_type = $wmsProductInSheetModel->piece_type;
            $wmsStatisticsBaseModel->in_and_out_type_name = $this->mapInTypeName($wmsProductInSheetModel->stock_origin_type);
            $wmsStatisticsBaseModel->weight_per_package = $wmsProductInSheetModel->wms_product_in_sheet_weight_per_package;
            $wmsStatisticsBaseModel->wms_statistics_text = $wmsProductInSheetModel->wms_product_in_sheet_note;

            $wmsStatisticsBaseModel->standard_package_number_add = $wmsProductInSheetModel->standard_package_number;
            $wmsStatisticsBaseModel->off_standard_package_number_add = $wmsProductInSheetModel->off_standard_package_number;
            $wmsStatisticsBaseModel->total_package_number_add = $wmsProductInSheetModel->wms_product_in_sheet_package_number;
            $wmsStatisticsBaseModel->standard_weight_add = $wmsProductInSheetModel->standard_weight;
            $wmsStatisticsBaseModel->off_standard_weight_add = $wmsProductInSheetModel->off_standard_weight;
            $wmsStatisticsBaseModel->total_weight_add = $wmsProductInSheetModel->wms_product_in_sheet_in_weight;

            $wmsStatisticsBaseModel->standard_package_number_sub = 0;
            $wmsStatisticsBaseModel->off_standard_package_number_sub = 0;
            $wmsStatisticsBaseModel->total_package_number_sub = 0;
            $wmsStatisticsBaseModel->standard_weight_sub = 0;
            $wmsStatisticsBaseModel->off_standard_weight_sub = 0;
            $wmsStatisticsBaseModel->total_weight_sub = 0;
        }
        $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
        //根据出入库类型重新设置第三方单号
        $wmsStatisticsBaseModel->resetRelativeSheetNumber();
        return $wmsStatisticsBaseModel;
    }

    /**
     * @param $wmsProductInSheetModel
     * @return array|null|\yii\db\ActiveRecord
     * 处理入库单作废
     */
    public function handleInDelete($wmsProductInSheetModel){
        if ($this->hasInSheetNumber($wmsProductInSheetModel->wms_product_in_sheet_number)){
            $wmsStatisticsBaseModel = $this->getModelByInSheetNumber($wmsProductInSheetModel->wms_product_in_sheet_number);
            $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
            return $wmsStatisticsBaseModel;
        }else{
            return null;
        }
    }

    /**
     * @param $wmsProductOutDetailInfoModel
     * @return array|ProductWmsStatisticsBase|null|\yii\db\ActiveRecord
     * 处理生成出库记录
     */
    public function handleOut($wmsProductOutDetailInfoModel){
        if ($this->hasOutSheetNumber($wmsProductOutDetailInfoModel->wms_product_out_sheet_number, $wmsProductOutDetailInfoModel->id)){
            $wmsStatisticsBaseModel = $this->getModelByOutSheetNumber($wmsProductOutDetailInfoModel->wms_product_out_sheet_number, $wmsProductOutDetailInfoModel->id);
        }else {
            $wmsStatisticsBaseModel = new \core\models\ProductWmsStatisticsBase();

            $wmsStatisticsBaseModel->common_producer_info_id = $wmsProductOutDetailInfoModel->common_producer_info_id;
            $wmsStatisticsBaseModel->common_producer_info_name = \core\models\WmsTransfer::getCommonProducerInfoName($wmsProductOutDetailInfoModel->common_producer_info_id);
            $wmsStatisticsBaseModel->common_producer_herb_info_id = $wmsProductOutDetailInfoModel->common_producer_herb_info_id;
            $wmsStatisticsBaseModel->common_producer_herb_info_name = $wmsProductOutDetailInfoModel->common_producer_herb_info_name;

            if (isset($wmsProductOutDetailInfoModel->wmsProductInSheet)){
                $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsProductOutDetailInfoModel->wmsProductInSheet->common_producer_herb_grade_info_id_product;
                $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsProductOutDetailInfoModel->wmsProductInSheet->common_producer_herb_grade_name_product;
            }else{
                $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsProductOutDetailInfoModel->common_producer_product_grade_info_id;
                $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsProductOutDetailInfoModel->common_producer_product_grade_info_name;
            }

            //如果出库时间小于入库时间,则容错处理
            if (isset($wmsProductOutDetailInfoModel->wmsProductInSheet->wms_product_in_sheet_product_in_date)
                && $wmsProductOutDetailInfoModel->wmsProductOutSheet->wms_product_out_sheet_product_out_date < $wmsProductOutDetailInfoModel->wmsProductInSheet->wms_product_in_sheet_product_in_date){
                $wmsStatisticsBaseModel->wms_statistics_date = $wmsProductOutDetailInfoModel->wmsProductInSheet->wms_product_in_sheet_product_in_date;
            }else{
                $wmsStatisticsBaseModel->wms_statistics_date = !empty($wmsProductOutDetailInfoModel->wmsProductOutSheet->wms_product_out_sheet_product_out_date) ? $wmsProductOutDetailInfoModel->wmsProductOutSheet->wms_product_out_sheet_product_out_date : 0;
            }
            $wmsStatisticsBaseModel->in_sheet_number = $wmsProductOutDetailInfoModel->wms_product_in_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_number = $wmsProductOutDetailInfoModel->wms_product_out_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_detail_id = $wmsProductOutDetailInfoModel->id;
            $wmsStatisticsBaseModel->relative_sheet_number = $wmsProductOutDetailInfoModel->sales_order_code;

            $wmsStatisticsBaseModel->wms_type = \core\models\WmsTransfer::WMS_TYPE_PRODUCT;
            $wmsStatisticsBaseModel->piece_type = $wmsProductOutDetailInfoModel->piece_type;
            $wmsStatisticsBaseModel->in_and_out_type_name = $this->mapOutTypeName($wmsProductOutDetailInfoModel->wmsProductOutSheet->wms_product_out_sheet_type);
            $wmsStatisticsBaseModel->weight_per_package = 0;
            $wmsStatisticsBaseModel->wms_statistics_text = $wmsProductOutDetailInfoModel->wms_product_out_detail_info_note;

            $wmsStatisticsBaseModel->standard_package_number_add = 0;
            $wmsStatisticsBaseModel->off_standard_package_number_add = 0;
            $wmsStatisticsBaseModel->total_package_number_add = 0;
            $wmsStatisticsBaseModel->standard_weight_add = 0;
            $wmsStatisticsBaseModel->off_standard_weight_add = 0;
            $wmsStatisticsBaseModel->total_weight_add = 0;

            $wmsStatisticsBaseModel->standard_package_number_sub = $wmsProductOutDetailInfoModel->standard_package_number;
            $wmsStatisticsBaseModel->off_standard_package_number_sub = $wmsProductOutDetailInfoModel->off_standard_package_number;
            $wmsStatisticsBaseModel->total_package_number_sub = $wmsProductOutDetailInfoModel->wms_product_out_detail_info_out_number;
            $wmsStatisticsBaseModel->standard_weight_sub = $wmsProductOutDetailInfoModel->standard_weight;
            $wmsStatisticsBaseModel->off_standard_weight_sub = $wmsProductOutDetailInfoModel->off_standard_weight;
            $wmsStatisticsBaseModel->total_weight_sub = $wmsProductOutDetailInfoModel->wms_product_out_detail_info_out_weight;
        }
        $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
        //根据出入库类型重新设置第三方单号
        $wmsStatisticsBaseModel->resetRelativeSheetNumber();
        return $wmsStatisticsBaseModel;
    }

    /**
     * @param $wmsProductOutDetailInfoModel
     * @return array|null|\yii\db\ActiveRecord
     * 处理出库作废
     */
    public function handleOutDelete($wmsProductOutDetailInfoModel){
        if ($this->hasOutSheetNumber($wmsProductOutDetailInfoModel->wms_product_out_sheet_number, $wmsProductOutDetailInfoModel->id)){
            $wmsStatisticsBaseModel = $this->getModelByOutSheetNumber($wmsProductOutDetailInfoModel->wms_product_out_sheet_number, $wmsProductOutDetailInfoModel->id);
            $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
            return $wmsStatisticsBaseModel;
        }else{
            return null;
        }

    }
}

PartiallyProductStatisticsBase.php

继承自WmsStatisticsBase.php

主要完成了半成品相关统计功能

<?php

namespace core\models;

use Yii;

class PartiallyProductWmsStatisticsBase extends \core\models\WmsStatisticsBase
{
    /**
     * PartiallyProductWmsStatisticsBase constructor.
     * 重写构造方法
     */
    public function __construct(){}

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取入库单列表
     */
    public function getWmsInSheet(){
        $wmsPartiallyProductInSheetModels = \core\models\WmsPartiallyProductInSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsPartiallyProductInSheetModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取指定时间范围内的生产加工半成品入库单是确认入库或作废
     */
    public function getWmsInSheetForProduce(){
        $wmsPartiallyProductInSheetModels = \core\models\WmsPartiallyProductInSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
            ['in', 'stock_origin_type', ['', 0, '0', '生产加工']],
            ['or', ['wms_partially_product_in_sheet_status'=>1], ['is_del'=>1]]
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsPartiallyProductInSheetModels;
    }


    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取出库详情列表
     */
    public function getWmsOutSheetDetail(){
        //注意:这里不能使用ID升序,应该使用出库日期升序,因为ID升序和出库日期出库不是对应的
        $wmsPartiallyProductOutDetailInfoModels = \core\models\WmsPartiallyProductOutDetailInfo::find()->where(['and',
            ['>=', '{{%wms_partially_product_out_detail_info}}.updated_at', $this->wms_statistics_date_begin],
            ['<', '{{%wms_partially_product_out_detail_info}}.updated_at', $this->wms_statistics_date_end],
        ])->joinWith(['wmsPartiallyProductOutSheet'=>function($query){
            $query->orderBy(['{{%wms_partially_product_out_sheet}}.wms_partially_product_out_sheet_product_out_date'=>SORT_ASC]);
        }])->all();
        return $wmsPartiallyProductOutDetailInfoModels;
    }

    /**
     * @return array|\yii\db\ActiveRecord[]
     * 获取指定时间范围内生产加工成品出库确认出库或出库作废
     */
    public function getWmsOutSheetForProduce(){
        $wmsPartiallyProductOutSheetModels = \core\models\WmsPartiallyProductOutSheet::find()->where(['and',
            ['>=', 'updated_at', $this->wms_statistics_date_begin],
            ['<', 'updated_at', $this->wms_statistics_date_end],
            ['in', 'wms_partially_product_out_sheet_type', ['生产加工']],
            ['or', ['wms_partially_product_out_sheet_status'=>1], ['is_del'=>1]]
        ])->orderBy(['id'=>SORT_ASC])->all();
        return $wmsPartiallyProductOutSheetModels;
    }

    /**
     * @param $inAndOutTypeInput
     * @return string
     * 清洗入库类型
     */
    public function mapInTypeName($inAndOutTypeInput){
        $inAndOutTypeName = '';
        $inAndOutTypeName = $inAndOutTypeInput;
        return $inAndOutTypeName;
    }

    /**
     * @param $inAndOutTypeInput
     * @return string
     * 清洗出库类型
     */
    public function mapOutTypeName($inAndOutTypeInput){
        $inAndOutTypeName = '';
        $inAndOutTypeName = $inAndOutTypeInput;
        return $inAndOutTypeName;
    }

    /**
     * @param $wmsPartiallyProductInSheetModel
     * @return array|ProductWmsStatisticsBase|null|\yii\db\ActiveRecord
     * 处理生成入库记录
     */
    public function handleIn($wmsPartiallyProductInSheetModel){
        if ($this->hasInSheetNumber($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_number)){
            $wmsStatisticsBaseModel = $this->getModelByInSheetNumber($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_number);
        }else {
            $wmsStatisticsBaseModel = new \core\models\ProductWmsStatisticsBase();

            $wmsStatisticsBaseModel->common_producer_info_id = $wmsPartiallyProductInSheetModel->common_producer_info_id;
            $wmsStatisticsBaseModel->common_producer_info_name = \core\models\WmsTransfer::getCommonProducerInfoName($wmsPartiallyProductInSheetModel->common_producer_info_id);
            $wmsStatisticsBaseModel->common_producer_herb_info_id = $wmsPartiallyProductInSheetModel->common_producer_herb_info_id_product;
            $wmsStatisticsBaseModel->common_producer_herb_info_name = $wmsPartiallyProductInSheetModel->common_producer_herb_info_name_product;
            $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsPartiallyProductInSheetModel->common_producer_herb_grade_info_id_product;
            $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsPartiallyProductInSheetModel->common_producer_herb_grade_name_product;

            $wmsStatisticsBaseModel->wms_statistics_date = !empty($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_product_in_date) ? $wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_product_in_date : 0;
            $wmsStatisticsBaseModel->in_sheet_number = $wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_number = '';
            $wmsStatisticsBaseModel->out_sheet_detail_id = 0;
            $wmsStatisticsBaseModel->relative_sheet_number = $wmsPartiallyProductInSheetModel->produce_record_sheet_number;

            $wmsStatisticsBaseModel->wms_type = \core\models\WmsStatisticsModel::WMS_TYPE_PARTIAL;
            $wmsStatisticsBaseModel->piece_type = $wmsPartiallyProductInSheetModel->piece_type;
            $wmsStatisticsBaseModel->in_and_out_type_name = $this->mapInTypeName($wmsPartiallyProductInSheetModel->stock_origin_type);
            $wmsStatisticsBaseModel->weight_per_package = $wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_weight_per_package;
            $wmsStatisticsBaseModel->wms_statistics_text = $wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_note;

            $wmsStatisticsBaseModel->standard_package_number_add = $wmsPartiallyProductInSheetModel->standard_package_number;
            $wmsStatisticsBaseModel->off_standard_package_number_add = $wmsPartiallyProductInSheetModel->off_standard_package_number;
            $wmsStatisticsBaseModel->total_package_number_add = $wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_package_number;
            $wmsStatisticsBaseModel->standard_weight_add = $wmsPartiallyProductInSheetModel->standard_weight;
            $wmsStatisticsBaseModel->off_standard_weight_add = $wmsPartiallyProductInSheetModel->off_standard_weight;
            $wmsStatisticsBaseModel->total_weight_add = $wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_in_weight;

            $wmsStatisticsBaseModel->standard_package_number_sub = 0;
            $wmsStatisticsBaseModel->off_standard_package_number_sub = 0;
            $wmsStatisticsBaseModel->total_package_number_sub = 0;
            $wmsStatisticsBaseModel->standard_weight_sub = 0;
            $wmsStatisticsBaseModel->off_standard_weight_sub = 0;
            $wmsStatisticsBaseModel->total_weight_sub = 0;
        }
        $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
        //根据出入库类型重新设置第三方单号
        $wmsStatisticsBaseModel->resetRelativeSheetNumber();
        return $wmsStatisticsBaseModel;
    }

    /**
     * @param $wmsPartiallyProductInSheetModel
     * @return array|null|\yii\db\ActiveRecord
     * 处理入库单作废
     */
    public function handleInDelete($wmsPartiallyProductInSheetModel){
        if ($this->hasInSheetNumber($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_number)){
            $wmsStatisticsBaseModel = $this->getModelByInSheetNumber($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_number);
            $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
            return $wmsStatisticsBaseModel;
        }else{
            return null;
        }
    }

    /**
     * @param $wmsPartiallyProductOutDetailInfoModel
     * @return array|PartiallyProductWmsStatisticsBase|null|\yii\db\ActiveRecord
     * 处理生成出库单
     */
    public function handleOut($wmsPartiallyProductOutDetailInfoModel){
        if ($this->hasOutSheetNumber($wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_sheet_number, $wmsPartiallyProductOutDetailInfoModel->id)){
            $wmsStatisticsBaseModel = $this->getModelByOutSheetNumber($wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_sheet_number, $wmsPartiallyProductOutDetailInfoModel->id);
        }else {
            $wmsStatisticsBaseModel = new \core\models\PartiallyProductWmsStatisticsBase();

            $wmsStatisticsBaseModel->common_producer_info_id = $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->common_producer_info_id;
            $wmsStatisticsBaseModel->common_producer_info_name = \core\models\WmsTransfer::getCommonProducerInfoName($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->common_producer_info_id);
            $wmsStatisticsBaseModel->common_producer_herb_info_id = $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->common_producer_herb_info_id_product;
            $wmsStatisticsBaseModel->common_producer_herb_info_name = $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->common_producer_herb_info_name_product;
            $wmsStatisticsBaseModel->common_producer_grade_info_id = $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->common_producer_herb_grade_info_id_product;
            $wmsStatisticsBaseModel->common_producer_grade_info_name = $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->common_producer_herb_grade_name_product;

            //如果出库时间小于入库时间,则容错处理
            if (isset($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->wms_partially_product_in_sheet_product_in_date)
                && $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->wms_partially_product_out_sheet_product_out_date < $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->wms_partially_product_in_sheet_product_in_date){
                $wmsStatisticsBaseModel->wms_statistics_date = $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductInSheet->wms_partially_product_in_sheet_product_in_date;
            }else{
                $wmsStatisticsBaseModel->wms_statistics_date = !empty($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->wms_partially_product_out_sheet_product_out_date) ? $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->wms_partially_product_out_sheet_product_out_date : 0;
            }
            $wmsStatisticsBaseModel->in_sheet_number = $wmsPartiallyProductOutDetailInfoModel->wms_partially_product_in_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_number = $wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_sheet_number;
            $wmsStatisticsBaseModel->out_sheet_detail_id = $wmsPartiallyProductOutDetailInfoModel->id;
            $wmsStatisticsBaseModel->relative_sheet_number = $wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->out_sheet_relative_sheet_number;

            $wmsStatisticsBaseModel->wms_type = \core\models\WmsStatisticsModel::WMS_TYPE_PARTIAL;
            $wmsStatisticsBaseModel->piece_type = $wmsPartiallyProductOutDetailInfoModel->piece_type;
            $wmsStatisticsBaseModel->in_and_out_type_name = $this->mapOutTypeName($wmsPartiallyProductOutDetailInfoModel->wmsPartiallyProductOutSheet->wms_partially_product_out_sheet_type);
            $wmsStatisticsBaseModel->weight_per_package = 0;
            $wmsStatisticsBaseModel->wms_statistics_text = $wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_detail_info_note;

            $wmsStatisticsBaseModel->standard_package_number_add = 0;
            $wmsStatisticsBaseModel->off_standard_package_number_add = 0;
            $wmsStatisticsBaseModel->total_package_number_add = 0;
            $wmsStatisticsBaseModel->standard_weight_add = 0;
            $wmsStatisticsBaseModel->off_standard_weight_add = 0;
            $wmsStatisticsBaseModel->total_weight_add = 0;

            $wmsStatisticsBaseModel->standard_package_number_sub = $wmsPartiallyProductOutDetailInfoModel->standard_package_number;
            $wmsStatisticsBaseModel->off_standard_package_number_sub = $wmsPartiallyProductOutDetailInfoModel->off_standard_package_number;
            $wmsStatisticsBaseModel->total_package_number_sub = $wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_detail_info_out_number;
            $wmsStatisticsBaseModel->standard_weight_sub = $wmsPartiallyProductOutDetailInfoModel->standard_weight;
            $wmsStatisticsBaseModel->off_standard_weight_sub = $wmsPartiallyProductOutDetailInfoModel->off_standard_weight;
            $wmsStatisticsBaseModel->total_weight_sub = $wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_detail_info_out_weight;
        }
        $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
        //根据出入库类型重新设置第三方单号
        $wmsStatisticsBaseModel->resetRelativeSheetNumber();
        return $wmsStatisticsBaseModel;
    }

    /**
     * @param $wmsPartiallyProductOutDetailInfoModel
     * @return array|null|\yii\db\ActiveRecord
     * 处理出库单作废
     */
    public function handleOutDelete($wmsPartiallyProductOutDetailInfoModel){
        if ($this->hasOutSheetNumber($wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_sheet_number, $wmsPartiallyProductOutDetailInfoModel->id)){
            $wmsStatisticsBaseModel = $this->getModelByOutSheetNumber($wmsPartiallyProductOutDetailInfoModel->wms_partially_product_out_sheet_number, $wmsPartiallyProductOutDetailInfoModel->id);
            $wmsStatisticsBaseModel->handle_type = __FUNCTION__;
            return $wmsStatisticsBaseModel;
        }else{
            return null;
        }
    }
}

WmsStatisticsModel.php

主要完成了统计表的相关业务逻辑

<?php

namespace core\models;

use Yii;
use yii\db\Query;
use yii\helpers\Console;

class WmsStatisticsModel extends \common\models\WmsStatisticsModel
{
    use WmsStatisticsModelTrait;

    const WMS_TYPE_MATERIAL = 1;//原料
    const WMS_TYPE_PRODUCT = 2;//成品
    const WMS_TYPE_TOUR = 3;//在产品
    const WMS_TYPE_PARTIAL = 4;//半成品

    const IS_OLD_VERSION = '1'; // 是否旧版本
    const DEFAULT_IS_OLD_VERSION = '0'; // 是否旧版默认值

    public $wms_statistics_date_begin;//生成统计数据开始日期
    public $wms_statistics_date_end;//生成统计数据截止日期
    public $show_output;//是否显示输出打印流

    public $total_weight_add_sum;
    public $total_weight_sub_sum;

    /**
     * @return array
     * 重写行为自动更新记录时间
     */
    public function behaviors()
    {
        return [
            [
                'class' => \yii\behaviors\TimestampBehavior::className(),
                'createdAtAttribute' => 'created_at',
                'updatedAtAttribute' => 'updated_at',
            ],
        ];
    }

    /**
     * @return array
     * 验证规则
     */
    public function rules()
    {
        return array_merge(parent::rules(), [
            [['wms_statistics_date_begin', 'wms_statistics_date_end'], 'integer'],
        ]);
    }

    /**
     * WmsStatisticsBase constructor.
     * @param array $wms_statistics_date_begin
     * @param $wms_statistics_date_end
     * 构造方法
     */
    public function __construct(){}

    /**
     * @param $wms_statistics_date_begin
     * 设置运行开始日期
     */
    public function setWmsStatisticsDateBegin($wms_statistics_date_begin){
        $this->wms_statistics_date_begin = $wms_statistics_date_begin;
    }

    /**
     * @param $wms_statistics_date_end
     * 设置运行结束日期
     */
    public function setWmsStatisticsDateEnd($wms_statistics_date_end){
        $this->wms_statistics_date_end = $wms_statistics_date_end;
    }

    /**
     * @param $show_output
     * 设置是否显示输出流
     */
    public function setShowOutput($show_output){
        $this->show_output = $show_output;
    }

    /**
     * @return mixed
     * 获取是否显示输出流
     */
    public function getShowOutput(){
        return $this->show_output;
    }

    /**
     * @param $content
     * @param $color
     * 屏幕打印流
     */
    public function output($content, $color, $tty){
        if($this->getShowOutput()){
            \core\components\OutputHelper::output($content, $color, $tty);
        }
    }

    /**
     * @param $outSheetNumber
     * @return static[]
     * 根据生产领料单号获取所有的生产批记录单
     */
    public static function getProduceRecordSheetModels($outSheetNumber){
        return \core\models\ProduceRecordSheet::find()->where(['wms_material_out_sheet_number'=>$outSheetNumber])->all();
    }

    /**
     * @param $inSheetNumber
     * @return bool
     * 判断是否有此入库单的信息
     */
    public function hasInSheetNumber($inSheetNumber){
        return self::find()->where(['and', ['in_sheet_number'=>$inSheetNumber], ['>', 'total_weight_add', 0]])->exists();
    }

    /**
     * @param $inSheetNumber
     * @return array|null|\yii\db\ActiveRecord
     * 根据入库单获取统计信息
     */
    public function getModelByInSheetNumber($inSheetNumber){
        return self::find()->where(['and', ['in_sheet_number'=>$inSheetNumber], ['>', 'total_weight_add', 0]])->one();
    }

    /**
     * @param $inSheetNumber
     * @return array|\yii\db\ActiveRecord[]
     * 获取所有相关入库单的模型
     */
    public function getAllModelsByInSheetNumber($inSheetNumber){
        return self::find()->where(['in_sheet_number'=>$inSheetNumber])->all();
    }

    /**
     * @param $inSheetNumber
     * @return int
     * 删除此入库单号的所有记录
     */
    public function deleteAllModelsByInSheetNumber($inSheetNumber){
        return self::deleteAll(['in_sheet_number'=>$inSheetNumber]);
    }

    /**
     * @param $inSheetNumber
     * @return array|null|\yii\db\ActiveRecord
     * 根据入库单获取最新的记录
     */
    public function getLastModelByInSheetNumber($inSheetNumber){
        return self::find()->where(['in_sheet_number'=>$inSheetNumber])->orderBy(['id'=>SORT_DESC])->one();
    }

    /**
     * @param $inSheetNumber
     * 判断是否今天已经同入库单号的记录
     */
    public function hasInSheetToday($wmsStatisticsBaseModel){
        $_today_begin_at = strtotime(date('Y-m-d', $wmsStatisticsBaseModel->wms_statistics_date));
        $_today_end_at = strtotime('+1 day', $_today_begin_at);
        return self::find()->where(['in_sheet_number'=>$wmsStatisticsBaseModel->in_sheet_number])
            ->andWhere(['>=', 'wms_statistics_date', $_today_begin_at])
            ->andWhere(['<', 'wms_statistics_date', $_today_end_at])
            ->exists();
    }

    /**
     * @param $wmsStatisticsBaseModel
     * @return bool
     * 获取今天同入库单号的记录
     */
    public function getInSheetToday($wmsStatisticsBaseModel){
        $_today_begin_at = strtotime(date('Y-m-d', $wmsStatisticsBaseModel->wms_statistics_date));
        $_today_end_at = strtotime('+1 day', $_today_begin_at);
        return self::find()->where(['in_sheet_number'=>$wmsStatisticsBaseModel->in_sheet_number])
            ->andWhere(['>=', 'wms_statistics_date', $_today_begin_at])
            ->andWhere(['<', 'wms_statistics_date', $_today_end_at])
            ->orderBy(['id'=>SORT_DESC])
            ->one();
    }

    /**
     * @param $wmsStatisticsBaseModel
     * @return bool
     * 判断统计表中是否已经有了统计日期大于当前统计记录日期的记录
     */
    public function alreadyHasNext($wmsStatisticsBaseModel){
        return self::find()->where(['in_sheet_number'=>$wmsStatisticsBaseModel->in_sheet_number])->andWhere(['>', 'wms_statistics_date', $wmsStatisticsBaseModel->wms_statistics_date])->exists();
    }

    /**
     * @param $wmsStatisticsBaseModel
     * @return bool
     * 处理入库
     */
    public function handleIn($wmsStatisticsBaseModel){

        $wmsStatisticsModel = new \core\models\WmsStatisticsModel();

        $wmsStatisticsModel->common_producer_info_id = $wmsStatisticsBaseModel->common_producer_info_id;
        $wmsStatisticsModel->common_producer_info_name = $wmsStatisticsBaseModel->common_producer_info_name;
        $wmsStatisticsModel->common_producer_herb_info_id = $wmsStatisticsBaseModel->common_producer_herb_info_id;
        $wmsStatisticsModel->common_producer_herb_info_name = $wmsStatisticsBaseModel->common_producer_herb_info_name;
        $wmsStatisticsModel->common_producer_grade_info_id = $wmsStatisticsBaseModel->common_producer_grade_info_id;
        $wmsStatisticsModel->common_producer_grade_info_name = $wmsStatisticsBaseModel->common_producer_grade_info_name;

        $wmsStatisticsModel->wms_statistics_date = $wmsStatisticsBaseModel->wms_statistics_date;
        $wmsStatisticsModel->wms_statistics_day = !empty($wmsStatisticsModel->wms_statistics_date) ? strtotime(date('Y-m-d', $wmsStatisticsBaseModel->wms_statistics_date)) : 0;
        $wmsStatisticsModel->wms_statistics_month = !empty($wmsStatisticsModel->wms_statistics_date) ? strtotime(date('Y-m', $wmsStatisticsBaseModel->wms_statistics_date)) : 0;
        $wmsStatisticsModel->wms_statistics_year = !empty($wmsStatisticsModel->wms_statistics_date) ? strtotime(date('Y', $wmsStatisticsModel->wms_statistics_date).'-01-01') : 0;
        $wmsStatisticsModel->in_sheet_number = $wmsStatisticsBaseModel->in_sheet_number;

        $wmsStatisticsModel->wms_type = $wmsStatisticsBaseModel->wms_type;
        $wmsStatisticsModel->piece_type = $wmsStatisticsBaseModel->piece_type;
        $wmsStatisticsModel->weight_per_package = $wmsStatisticsBaseModel->weight_per_package;
        $wmsStatisticsModel->wms_statistics_text = $wmsStatisticsBaseModel->wms_statistics_text;

        $wmsStatisticsModel->standard_package_number_begin = 0;
        $wmsStatisticsModel->off_standard_package_number_begin = 0;
        $wmsStatisticsModel->total_package_number_begin = 0;
        $wmsStatisticsModel->standard_weight_begin = 0;
        $wmsStatisticsModel->off_standard_weight_begin = 0;
        $wmsStatisticsModel->total_weight_begin = 0;

        $wmsStatisticsModel->standard_package_number_add = $wmsStatisticsBaseModel->standard_package_number_add;
        $wmsStatisticsModel->off_standard_package_number_add = $wmsStatisticsBaseModel->off_standard_package_number_add;
        $wmsStatisticsModel->total_package_number_add = $wmsStatisticsBaseModel->total_package_number_add;
        $wmsStatisticsModel->standard_weight_add = $wmsStatisticsBaseModel->standard_weight_add;
        $wmsStatisticsModel->off_standard_weight_add = $wmsStatisticsBaseModel->off_standard_weight_add;
        $wmsStatisticsModel->total_weight_add = $wmsStatisticsBaseModel->total_weight_add;

        $wmsStatisticsModel->standard_package_number_sub = 0;
        $wmsStatisticsModel->off_standard_package_number_sub = 0;
        $wmsStatisticsModel->total_package_number_sub = 0;
        $wmsStatisticsModel->standard_weight_sub = 0;
        $wmsStatisticsModel->off_standard_weight_sub = 0;
        $wmsStatisticsModel->total_weight_sub = 0;

        $wmsStatisticsModel->standard_package_number_end = $wmsStatisticsBaseModel->standard_package_number_add;
        $wmsStatisticsModel->off_standard_package_number_end = $wmsStatisticsBaseModel->off_standard_package_number_add;
        $wmsStatisticsModel->total_package_number_end = $wmsStatisticsBaseModel->total_package_number_add;
        $wmsStatisticsModel->standard_weight_end = $wmsStatisticsBaseModel->standard_weight_add;
        $wmsStatisticsModel->off_standard_weight_end = $wmsStatisticsBaseModel->off_standard_weight_add;
        $wmsStatisticsModel->total_weight_end = $wmsStatisticsBaseModel->total_weight_add;

        $saveResult = $wmsStatisticsModel->save(false);
        if ($saveResult){
            \core\components\OutputHelper::logFile("[wms_statistics][入库]处理入库单" . $wmsStatisticsModel->in_sheet_number . "确认入库成功[期初:".$wmsStatisticsModel->total_weight_begin."期末:".$wmsStatisticsModel->total_weight_end."增加:".$wmsStatisticsModel->total_weight_add."减少:".$wmsStatisticsModel->total_weight_sub."]");
        }else{
            \core\components\OutputHelper::logFile("[wms_statistics][入库]处理入库单" . $wmsStatisticsModel->in_sheet_number . "确认入库失败[期初:".$wmsStatisticsModel->total_weight_begin."期末:".$wmsStatisticsModel->total_weight_end."增加:".$wmsStatisticsModel->total_weight_add."减少:".$wmsStatisticsModel->total_weight_sub."]");
        }
        unset($wmsStatisticsModel);
        return $saveResult;
    }

    /**
     * @param $wmsStatisticsBaseModel
     * @return bool|false|int
     * 处理入库作废
     */
    public function handleInDelete($wmsStatisticsBaseModel){
        if ($this->hasInSheetNumber($wmsStatisticsBaseModel->in_sheet_number)){
            $wmsStatisticsModel = $this->getModelByInSheetNumber($wmsStatisticsBaseModel->in_sheet_number);
            $deleteResult = $wmsStatisticsModel->delete();
            if ($deleteResult){
                \core\components\OutputHelper::logFile("[wms_statistics][入库作废]处理入库单" . $wmsStatisticsModel->in_sheet_number . "作废成功");
            }else{
                \core\components\OutputHelper::logFile("[wms_statistics][入库作废]处理入库单" . $wmsStatisticsModel->in_sheet_number . "作废失败");
            }
        }else{
            return true;
        }
    }

    /**
     * @param $wmsStatisticsBaseModel
     * @return bool
     * 处理出库
     */
    public function handleOut($wmsStatisticsBaseModel){
        //获取最新一次记录
        $lastModel = $this->getLastModelByInSheetNumber($wmsStatisticsBaseModel->in_sheet_number);
        if (empty($lastModel)){
            throw new \yii\db\Exception('wms_statistics:未找到出库单'.$wmsStatisticsBaseModel->out_sheet_number.'对应的入库单记录'.$wmsStatisticsBaseModel->in_sheet_number);
        }
        if ($this->alreadyHasNext($wmsStatisticsBaseModel)){
            return $this->handleOutDelete($wmsStatisticsBaseModel);
        }else {
            if ($this->hasInSheetToday($wmsStatisticsBaseModel)) {
                $wmsStatisticsModel = $this->getInSheetToday($wmsStatisticsBaseModel);

                $wmsStatisticsModel->off_standard_package_number_sub = bcadd($wmsStatisticsModel->off_standard_package_number_sub, $wmsStatisticsBaseModel->off_standard_package_number_sub, 0);
                $wmsStatisticsModel->total_package_number_sub = bcadd($wmsStatisticsModel->total_package_number_sub, $wmsStatisticsBaseModel->total_package_number_sub, 0);
                $wmsStatisticsModel->standard_weight_sub = bcadd($wmsStatisticsModel->standard_weight_sub, $wmsStatisticsBaseModel->standard_weight_sub, 0);
                $wmsStatisticsModel->off_standard_weight_sub = bcadd($wmsStatisticsModel->off_standard_weight_sub, $wmsStatisticsBaseModel->off_standard_weight_sub, 0);
                $wmsStatisticsModel->total_weight_sub = bcadd($wmsStatisticsModel->total_weight_sub, $wmsStatisticsBaseModel->total_weight_sub, 0);

                $wmsStatisticsModel->standard_package_number_end = bcsub($wmsStatisticsModel->standard_package_number_end, $wmsStatisticsBaseModel->standard_package_number_sub, 0);
                $wmsStatisticsModel->off_standard_package_number_end = bcsub($wmsStatisticsModel->off_standard_package_number_end, $wmsStatisticsBaseModel->off_standard_package_number_sub, 0);
                $wmsStatisticsModel->total_package_number_end = bcsub($wmsStatisticsModel->total_package_number_end, $wmsStatisticsBaseModel->total_package_number_sub, 0);
                $wmsStatisticsModel->standard_weight_end = bcsub($wmsStatisticsModel->standard_weight_end, $wmsStatisticsBaseModel->standard_weight_sub, 0);
                $wmsStatisticsModel->off_standard_weight_end = bcsub($wmsStatisticsModel->off_standard_weight_end, $wmsStatisticsBaseModel->off_standard_weight_sub, 0);
                $wmsStatisticsModel->total_weight_end = bcsub($wmsStatisticsModel->total_weight_end, $wmsStatisticsBaseModel->total_weight_sub, 0);
            } else {
                $wmsStatisticsModel = new \core\models\WmsStatisticsModel();

                $wmsStatisticsModel->common_producer_info_id = $wmsStatisticsBaseModel->common_producer_info_id;
                $wmsStatisticsModel->common_producer_info_name = $wmsStatisticsBaseModel->common_producer_info_name;
                $wmsStatisticsModel->common_producer_herb_info_id = $wmsStatisticsBaseModel->common_producer_herb_info_id;
                $wmsStatisticsModel->common_producer_herb_info_name = $wmsStatisticsBaseModel->common_producer_herb_info_name;
                $wmsStatisticsModel->common_producer_grade_info_id = $wmsStatisticsBaseModel->common_producer_grade_info_id;
                $wmsStatisticsModel->common_producer_grade_info_name = $wmsStatisticsBaseModel->common_producer_grade_info_name;

                $wmsStatisticsModel->wms_statistics_date = $wmsStatisticsBaseModel->wms_statistics_date;
                $wmsStatisticsModel->wms_statistics_day = !empty($wmsStatisticsModel->wms_statistics_date) ? strtotime(date('Y-m-d', $wmsStatisticsBaseModel->wms_statistics_date)) : 0;
                $wmsStatisticsModel->wms_statistics_month = !empty($wmsStatisticsModel->wms_statistics_date) ? strtotime(date('Y-m', $wmsStatisticsBaseModel->wms_statistics_date)) : 0;
                $wmsStatisticsModel->wms_statistics_year = !empty($wmsStatisticsModel->wms_statistics_date) ? strtotime(date('Y', $wmsStatisticsModel->wms_statistics_date) . '-01-01') : 0;
                $wmsStatisticsModel->in_sheet_number = $wmsStatisticsBaseModel->in_sheet_number;

                $wmsStatisticsModel->wms_type = $wmsStatisticsBaseModel->wms_type;
                $wmsStatisticsModel->piece_type = $wmsStatisticsBaseModel->piece_type;
                $wmsStatisticsModel->weight_per_package = $wmsStatisticsBaseModel->weight_per_package;
                $wmsStatisticsModel->wms_statistics_text = $wmsStatisticsBaseModel->wms_statistics_text;

                $wmsStatisticsModel->standard_package_number_begin = $lastModel->standard_package_number_end;
                $wmsStatisticsModel->off_standard_package_number_begin = $lastModel->off_standard_package_number_end;
                $wmsStatisticsModel->total_package_number_begin = $lastModel->total_package_number_end;
                $wmsStatisticsModel->standard_weight_begin = $lastModel->standard_weight_end;
                $wmsStatisticsModel->off_standard_weight_begin = $lastModel->off_standard_weight_end;
                $wmsStatisticsModel->total_weight_begin = $lastModel->total_weight_end;

                $wmsStatisticsModel->standard_package_number_add = 0;
                $wmsStatisticsModel->off_standard_package_number_add = 0;
                $wmsStatisticsModel->total_package_number_add = 0;
                $wmsStatisticsModel->standard_weight_add = 0;
                $wmsStatisticsModel->off_standard_weight_add = 0;
                $wmsStatisticsModel->total_weight_add = 0;

                $wmsStatisticsModel->standard_package_number_sub = $wmsStatisticsBaseModel->standard_package_number_sub;
                $wmsStatisticsModel->off_standard_package_number_sub = $wmsStatisticsBaseModel->off_standard_package_number_sub;
                $wmsStatisticsModel->total_package_number_sub = $wmsStatisticsBaseModel->total_package_number_sub;
                $wmsStatisticsModel->standard_weight_sub = $wmsStatisticsBaseModel->standard_weight_sub;
                $wmsStatisticsModel->off_standard_weight_sub = $wmsStatisticsBaseModel->off_standard_weight_sub;
                $wmsStatisticsModel->total_weight_sub = $wmsStatisticsBaseModel->total_weight_sub;

                $wmsStatisticsModel->standard_package_number_end = bcsub($wmsStatisticsModel->standard_package_number_begin, $wmsStatisticsModel->standard_package_number_sub, 0);
                $wmsStatisticsModel->off_standard_package_number_end = bcsub($wmsStatisticsModel->off_standard_package_number_begin, $wmsStatisticsModel->off_standard_package_number_sub, 0);
                $wmsStatisticsModel->total_package_number_end = bcsub($wmsStatisticsModel->total_package_number_begin, $wmsStatisticsModel->total_package_number_sub, 0);
                $wmsStatisticsModel->standard_weight_end = bcsub($wmsStatisticsModel->standard_weight_begin, $wmsStatisticsModel->standard_weight_sub, 0);
                $wmsStatisticsModel->off_standard_weight_end = bcsub($wmsStatisticsModel->off_standard_weight_begin, $wmsStatisticsModel->off_standard_weight_sub, 0);
                $wmsStatisticsModel->total_weight_end = bcsub($wmsStatisticsModel->total_weight_begin, $wmsStatisticsModel->total_weight_sub, 0);
            }
            $saveResult = $wmsStatisticsModel->save(false);
            if ($saveResult) {
                \core\components\OutputHelper::logFile("[wms_statistics][出库]处理入库单" . $wmsStatisticsModel->in_sheet_number . "出库单" . $wmsStatisticsBaseModel->out_sheet_number . "出库成功[期初:" . $wmsStatisticsModel->total_weight_begin . "期末:" . $wmsStatisticsModel->total_weight_end . "增加:" . $wmsStatisticsModel->total_weight_add . "减少:" . $wmsStatisticsModel->total_weight_sub . "]");
            } else {
                \core\components\OutputHelper::logFile("[wms_statistics][出库]处理入库单" . $wmsStatisticsModel->in_sheet_number . "出库单" . $wmsStatisticsBaseModel->out_sheet_number . "出库失败[期初:" . $wmsStatisticsModel->total_weight_begin . "期末:" . $wmsStatisticsModel->total_weight_end . "增加:" . $wmsStatisticsModel->total_weight_add . "减少:" . $wmsStatisticsModel->total_weight_sub . "]");
            }
            unset($lastModel);
            unset($wmsStatisticsModel);
            return $saveResult;
        }
    }

    /**
     * @param $wmsStatisticsBaseModel
     * 处理出库作废
     */
    public function handleOutDelete($wmsStatisticsBaseModel){
        $deleteNum = $this->deleteAllModelsByInSheetNumber($wmsStatisticsBaseModel->in_sheet_number);
        if ($deleteNum){
            \core\components\OutputHelper::logFile("[wms_statistics][出库作废]处理入库单" . $wmsStatisticsBaseModel->in_sheet_number . "删除所有相关统计单据成功");
        }else{
            \core\components\OutputHelper::logFile("[wms_statistics][出库作废]处理入库单" . $wmsStatisticsBaseModel->in_sheet_number . "删除所有相关统计单据失败");
        }
        $_wmsStatisticsBaseModels = $wmsStatisticsBaseModel->getAllModelsByInSheetNumber($wmsStatisticsBaseModel->in_sheet_number);
        foreach ($_wmsStatisticsBaseModels as $_wmsStatisticsBaseModel){
            if ($_wmsStatisticsBaseModel->total_weight_add > 0){
                $saveResult = $this->handleIn($_wmsStatisticsBaseModel);
                if ($saveResult){
                    \core\components\OutputHelper::logFile("[wms_statistics][出库]处理入库单" . $_wmsStatisticsBaseModel->in_sheet_number . "入库成功");
                }else{
                    \core\components\OutputHelper::logFile("[wms_statistics][出库]处理入库单" . $_wmsStatisticsBaseModel->in_sheet_number . "入库失败");
                }
            }elseif($_wmsStatisticsBaseModel->total_weight_sub > 0){
                $saveResult = $this->handleOut($_wmsStatisticsBaseModel);
                if ($saveResult){
                    \core\components\OutputHelper::logFile("[wms_statistics][出库]处理入库单" . $_wmsStatisticsBaseModel->in_sheet_number . "出库单".$_wmsStatisticsBaseModel->out_sheet_number."出库成功");
                }else{
                    \core\components\OutputHelper::logFile("[wms_statistics][出库]处理入库单" . $_wmsStatisticsBaseModel->in_sheet_number . "出库单".$_wmsStatisticsBaseModel->out_sheet_number."出库失败");
                }
            }else{

            }
            unset($_wmsStatisticsBaseModel);
        }
        unset($_wmsStatisticsBaseModels);
        return $deleteNum;
    }
}

WmsStatisticsTour.php

继承自WmsStatisticsModel

主要完成了在产品相关统计的功能

<?php

namespace core\models;

use core\components\ArrayHelper;
use \core\models\WmsInfoTour;
use \yii\helpers\Console;

class WmsStatisticsTour extends \core\models\WmsStatisticsModel {

    /**
     * WmsStatisticsTour constructor.
     * 重写再生产库存统计
     */
    public function __construct(){}

    /**
     * @param $out_sheet_number
     * @return int
     * 根据出库单获取再生产重量
     */
    public static function getTourWeightByOutSheetNumber($out_sheet_number, $wms_statistics_end_at){
        $wms_statistics_end_at = !empty($wms_statistics_end_at) ? $wms_statistics_end_at : time();
        $tour_weight = 0;
        if (strpos($out_sheet_number, 'YLCK') !== false){
            $material_out_sheet = WmsInfoTour::getMaterialOutSheetByProduceNumberForOther($out_sheet_number);
            $out_weight = $material_out_sheet['weight'];
            $scjl_sheet_list = WmsInfoTour::getSCJLSheetListByOutNumber($out_sheet_number);
            $sum_surplus_weight = 0;
            $scjl_sum_weight = 0;
            $scjl_number_detail = [];
            if (empty($scjl_sheet_list)){
                $sum_surplus_weight = 0;
            }else {
                //所有生产批记录单的总投入数
                $scjl_sum_weight = 0;
                foreach ($scjl_sheet_list as $scjl_sheet) {
                    $info = WmsInfoTour::getSurplusWeightByProduceRecord($scjl_sheet, $out_weight, 0, $wms_statistics_end_at);
                    $surplus_weight = $info['surplus_weight'];
                    $scjl_weight = $info['scjl_weight'];
                    $sum_surplus_weight += $surplus_weight;
                    $scjl_sum_weight += $scjl_weight;
                }
            }
            $tour_weight = $sum_surplus_weight + $out_weight - $scjl_sum_weight;
            $item = $material_out_sheet;
            $item['tour_weight'] = $tour_weight;
        }elseif (strpos($out_sheet_number, 'BCPCK') !== false){
            $partially_product_out_sheet = WmsInfoTour::getPartiallyProductOutSheetByProduceNumberForOther($out_sheet_number);
            $out_weight = $partially_product_out_sheet['weight'];
            $scjl_sheet_list = WmsInfoTour::getSCJLSheetListByOutNumber($out_sheet_number);
            $sum_surplus_weight = 0;
            $scjl_sum_weight = 0;
            $scjl_number_detail = [];
            if (empty($scjl_sheet_list)){
                $sum_surplus_weight = 0;
            }else {
                //所有生产批记录单的总投入数
                $scjl_sum_weight = 0;
                foreach ($scjl_sheet_list as $scjl_sheet) {
                    $info = WmsInfoTour::getSurplusWeightByProduceRecord($scjl_sheet, $out_weight, 0, $wms_statistics_end_at);
                    $surplus_weight = $info['surplus_weight'];
                    $scjl_weight = $info['scjl_weight'];
                    $sum_surplus_weight += $surplus_weight;
                    $scjl_sum_weight += $scjl_weight;
                }
            }
            $tour_weight = $sum_surplus_weight + $out_weight - $scjl_sum_weight;
            $item = $partially_product_out_sheet;
            $item['tour_weight'] = $tour_weight;
        }elseif (strpos($out_sheet_number, 'CPCK') !== false) {
            $product_out_sheet = WmsInfoTour::getProductOutSheetByProduceNumberForOther($out_sheet_number);
            $out_weight = $product_out_sheet['weight'];
            $scjl_sheet_list = WmsInfoTour::getSCJLSheetListByOutNumber($out_sheet_number);
            $sum_surplus_weight = 0;
            $scjl_sum_weight = 0;
            $scjl_number_detail = [];
            if (empty($scjl_sheet_list)) {
                $sum_surplus_weight = 0;
            } else {
                //所有生产批记录单的总投入数
                $scjl_sum_weight = 0;
                foreach ($scjl_sheet_list as $scjl_sheet) {
                    $info = WmsInfoTour::getSurplusWeightByProduceRecord($scjl_sheet, $out_weight, 0, $wms_statistics_end_at);
                    $surplus_weight = $info['surplus_weight'];
                    $scjl_weight = $info['scjl_weight'];
                    $sum_surplus_weight += $surplus_weight;
                    $scjl_sum_weight += $scjl_weight;
                }
            }
            $tour_weight = $sum_surplus_weight + $out_weight - $scjl_sum_weight;
            $item = $product_out_sheet;
            $item['tour_weight'] = $tour_weight;
        }else{
            throw new \yii\db\Exception('在生产计算接口:出库单号'.$out_sheet_number.'异常');
        }
        return $item;
    }

    /**
     * @param $outSheetNumber
     * @return bool
     * 判断是否存在此出库单号
     */
    public function hasOutSheetNumber($outSheetNumber, $time_end){
        return self::find()->where(['in_sheet_number'=>$outSheetNumber])->andWhere(['<', 'wms_statistics_date', $time_end])->exists();
    }

    /**
     * @param $outSheetNumber
     * @return array|null|\yii\db\ActiveRecord
     * 获取此出库单的上一条统计记录
     */
    public function getLastModelByOutSheetNumber($outSheetNumber, $time_end){
        return self::find()->where(['in_sheet_number'=>$outSheetNumber])->andWhere(['<', 'wms_statistics_date', $time_end])->orderBy(['wms_statistics_date'=>SORT_DESC])->one();
    }

    /**
     * @param $outSheetNumber
     * @return bool
     * 判断当天是否存在此出库单号
     */
    public function hasOutSheetNumberToday($outSheetNumber, $time_end){
        $today_begin_at = $time_end % 86400 ? $time_end - 3600*24 : strtotime(date('Y-m-d', $time_end));
        $today_begin_end = $time_end % 86400 ? $time_end : $time_end;
        return self::find()->where(['and',
            ['in_sheet_number'=>$outSheetNumber],
            ['>=', 'wms_statistics_date', $today_begin_at],
            ['<', 'wms_statistics_date', $today_begin_end],
        ])->exists();
    }

    /**
     * @param $outSheetNumber
     * @return bool
     * @throws \yii\db\Exception
     * 处理再生产
     */
    public function handleTour($outSheetNumber, $time_end){
        try{

            //获取再生产的重量
            $item = self::getTourWeightByOutSheetNumber($outSheetNumber, $time_end);
            $tour_weight = $item['tour_weight'];
            //判断当天是否已有记录, 有则直接修改更新; 没有则创建
            if($this->hasOutSheetNumberToday($outSheetNumber, $time_end)){
                $lastModel = $this->getLastModelByOutSheetNumber($outSheetNumber, $time_end);
                $tour_weight_before = $lastModel->total_weight_end;
                if(intval($tour_weight) > intval($tour_weight_before)){
                    $total_weight_begin = $lastModel->total_weight_begin;
                    $total_weight_add = bcadd($lastModel->total_weight_add, bcsub($tour_weight, $tour_weight_before, 0), 0);
                    $total_weight_sub = $lastModel->total_weight_sub;
                    $total_weight_end = $tour_weight;
                }elseif(intval($tour_weight) < intval($tour_weight_before)){
                    $total_weight_begin = $lastModel->total_weight_begin;
                    $total_weight_add = $lastModel->total_weight_add;
                    $total_weight_sub = bcsub($lastModel->total_weight_sub, bcsub($tour_weight_before, $tour_weight, 0), 0);
                    $total_weight_end = $tour_weight;
                }else{
                    $total_weight_begin = $lastModel->total_weight_begin;
                    $total_weight_add = $lastModel->total_weight_add;
                    $total_weight_sub = $lastModel->total_weight_sub;
                    $total_weight_end = $lastModel->total_weight_end;
                }

                $wmsStatisticsModel = $lastModel;

            }elseif($this->hasOutSheetNumber($outSheetNumber, $time_end)){
                $lastModel = $this->getLastModelByOutSheetNumber($outSheetNumber, $time_end);
                $tour_weight_before = $lastModel->total_weight_end;
                if(intval($tour_weight) > intval($tour_weight_before)){
                    $total_weight_begin = $tour_weight_before;
                    $total_weight_add = bcsub($tour_weight, $tour_weight_before, 0);
                    $total_weight_sub = 0;
                    $total_weight_end = $tour_weight;
                }elseif(intval($tour_weight) < intval($tour_weight_before)){
                    $total_weight_begin = $tour_weight_before;
                    $total_weight_add = 0;
                    $total_weight_sub = bcsub($tour_weight_before, $tour_weight, 0);
                    $total_weight_end = $tour_weight;
                }else{
                    $total_weight_begin = $tour_weight_before;
                    $total_weight_add = 0;
                    $total_weight_sub = 0;
                    $total_weight_end = $tour_weight;
                }

                $wmsStatisticsModel = new \core\models\WmsStatisticsTour();

                $wmsStatisticsModel->common_producer_info_id = $lastModel->common_producer_info_id;
                $wmsStatisticsModel->common_producer_info_name = $lastModel->common_producer_info_name;
                $wmsStatisticsModel->common_producer_herb_info_id = $lastModel->common_producer_herb_info_id;
                $wmsStatisticsModel->common_producer_herb_info_name = $lastModel->common_producer_herb_info_name;
                $wmsStatisticsModel->common_producer_grade_info_id = $lastModel->common_producer_grade_info_id;
                $wmsStatisticsModel->common_producer_grade_info_name = $lastModel->common_producer_grade_info_name;

                $wmsStatisticsModel->wms_statistics_date = $time_end - 1;
                $wmsStatisticsModel->wms_statistics_day = strtotime(date('Y-m-d', $wmsStatisticsModel->wms_statistics_date));
                $wmsStatisticsModel->wms_statistics_month = strtotime(date('Y-m', $wmsStatisticsModel->wms_statistics_date));
                $wmsStatisticsModel->wms_statistics_year = strtotime(date('Y', $wmsStatisticsModel->wms_statistics_date).'-01-01');
                $wmsStatisticsModel->in_sheet_number = $lastModel->in_sheet_number;

                $wmsStatisticsModel->wms_type = $lastModel->wms_type;
                $wmsStatisticsModel->piece_type = $lastModel->piece_type;
                $wmsStatisticsModel->weight_per_package = $lastModel->weight_per_package;
                $wmsStatisticsModel->wms_statistics_text = $lastModel->wms_statistics_text;

            }else{
                $tour_weight_before = 0;
                if(intval($tour_weight) > intval($tour_weight_before)){
                    $total_weight_begin = 0;
                    $total_weight_add = bcsub($tour_weight, $tour_weight_before, 0);
                    $total_weight_sub = 0;
                    $total_weight_end = $tour_weight;
                }elseif(intval($tour_weight) < intval($tour_weight_before)){
                    $total_weight_begin = 0;
                    $total_weight_add = 0;
                    $total_weight_sub = bcsub($tour_weight_before, $tour_weight, 0);
                    $total_weight_end = $tour_weight;
                }else{
                    $total_weight_begin = 0;
                    $total_weight_add = 0;
                    $total_weight_sub = 0;
                    $total_weight_end = 0;
                }

                $wmsStatisticsModel = new \core\models\WmsStatisticsTour();

                $wmsStatisticsModel->common_producer_info_id = $item['producer_id'];
                $wmsStatisticsModel->common_producer_info_name = \core\models\WmsTransfer::getCommonProducerInfoName($item['producer_id']);
                $wmsStatisticsModel->common_producer_herb_info_id = $item['info_id'];
                $wmsStatisticsModel->common_producer_herb_info_name = $item['info_name'];
                $wmsStatisticsModel->common_producer_grade_info_id = $item['grade_id'];
                $wmsStatisticsModel->common_producer_grade_info_name = $item['grade_name'];

                $wmsStatisticsModel->wms_statistics_date = $time_end - 1;
                $wmsStatisticsModel->wms_statistics_day = strtotime(date('Y-m-d', $wmsStatisticsModel->wms_statistics_date));
                $wmsStatisticsModel->wms_statistics_month = strtotime(date('Y-m', $wmsStatisticsModel->wms_statistics_date));
                $wmsStatisticsModel->wms_statistics_year = strtotime(date('Y', $wmsStatisticsModel->wms_statistics_date).'-01-01');
                $wmsStatisticsModel->in_sheet_number = $outSheetNumber;

                $wmsStatisticsModel->wms_type = \core\models\WmsStatisticsModel::WMS_TYPE_TOUR;
                $wmsStatisticsModel->piece_type = \core\models\WmsManager::PIECE_TYPE_OFF_STANDARD;
                $wmsStatisticsModel->weight_per_package = 0;
                $wmsStatisticsModel->wms_statistics_text = '';
            }

            $wmsStatisticsModel->standard_package_number_begin = 0;
            $wmsStatisticsModel->off_standard_package_number_begin = 0;
            $wmsStatisticsModel->total_package_number_begin = 0;
            $wmsStatisticsModel->standard_weight_begin = 0;
            $wmsStatisticsModel->off_standard_weight_begin = $total_weight_begin;
            $wmsStatisticsModel->total_weight_begin = $total_weight_begin;

            $wmsStatisticsModel->standard_package_number_add = 0;
            $wmsStatisticsModel->off_standard_package_number_add = 0;
            $wmsStatisticsModel->total_package_number_add = 0;
            $wmsStatisticsModel->standard_weight_add = 0;
            $wmsStatisticsModel->off_standard_weight_add = $total_weight_add;
            $wmsStatisticsModel->total_weight_add = $total_weight_add;

            $wmsStatisticsModel->standard_package_number_sub = 0;
            $wmsStatisticsModel->off_standard_package_number_sub = 0;
            $wmsStatisticsModel->total_package_number_sub = 0;
            $wmsStatisticsModel->standard_weight_sub = 0;
            $wmsStatisticsModel->off_standard_weight_sub = $total_weight_sub;
            $wmsStatisticsModel->total_weight_sub = $total_weight_sub;

            $wmsStatisticsModel->standard_package_number_end = 0;
            $wmsStatisticsModel->off_standard_package_number_end = 0;
            $wmsStatisticsModel->total_package_number_end = 0;
            $wmsStatisticsModel->standard_weight_end = 0;
            $wmsStatisticsModel->off_standard_weight_end = $total_weight_end;
            $wmsStatisticsModel->total_weight_end = $total_weight_end;
            /*
            if (empty($wmsStatisticsModel->total_weight_begin) && empty($wmsStatisticsModel->total_weight_end)){
                throw new \yii\db\Exception('wms_statistics:在生产'.$outSheetNumber.'['.date("Y-m-d", $time_end).']的期初和期末都为0,无需记录在生产统计');
            }elseif ($wmsStatisticsModel->total_weight_begin == $wmsStatisticsModel->total_weight_end){
                throw new \yii\db\Exception('wms_statistics:在生产'.$outSheetNumber.'['.date("Y-m-d", $time_end).']的期初和期末相等,无需记录在生产统计');
            }else
            */
            if(empty($wmsStatisticsModel->total_weight_begin)
            && empty($wmsStatisticsModel->total_weight_add)
            && empty($wmsStatisticsModel->total_weight_sub)
            && empty($wmsStatisticsModel->total_weight_end)){
                throw new \yii\db\Exception('wms_statistics:在生产'.$outSheetNumber.'['.date("Y-m-d", $time_end).']期初增加减少期末均为0,无需记录或更新');
            } elseif($this->hasOutSheetNumber($outSheetNumber, $time_end)
                && ($lastModel = $this->getLastModelByOutSheetNumber($outSheetNumber, $time_end))
                && $lastModel->total_weight_begin == $wmsStatisticsModel->total_weight_begin
                && $lastModel->total_weight_add == $wmsStatisticsModel->total_weight_add
                && $lastModel->total_weight_sub == $wmsStatisticsModel->total_weight_sub
                && $lastModel->total_weight_end == $wmsStatisticsModel->total_weight_end){
                throw new \yii\db\Exception('wms_statistics:在生产'.$outSheetNumber.'['.date("Y-m-d", $time_end).']没有变化,无需重复记录或更新');
            }else{
                $saveResult = $wmsStatisticsModel->save(false);
                unset($total_weight_begin);
                unset($total_weight_end);
                unset($total_weight_add);
                unset($total_weight_sub);
                if ($saveResult){
                    return $wmsStatisticsModel;
                }else{
                    return false;
                }
            }
        }catch (\Exception $e){
            throw new \yii\db\Exception($e->getMessage());
        }
    }

    /**
     * 删除所有的再生产
     */
    private function __deleteAll(){
        return \common\models\WmsStatisticsModel::deleteAll(['wms_type'=>parent::WMS_TYPE_TOUR]);
    }

    /**
     * @return \Generator|void
     * 获取生产加工出库单号生成器
     */
    public function genOutSheet(){
        //这里查询只能指定结束日期,而不能指定开始日期;因为一段时间内可能还没有生成完成,需要在以后的时间段内完成; 所有每次要查询小于结束日期的领料单
        $outSheetList = \common\models\WmsStatisticsBase::find()->select(['out_sheet_number'])
            ->where(['and', ['in_and_out_type_name'=>'生产加工'], ['>', 'total_weight_sub', 0]])
            ->andFilterWhere(['<', 'wms_statistics_date', $this->wms_statistics_date_end])
            ->orderBy(['id'=>SORT_ASC])->all();
        foreach ($outSheetList as $outSheetModel){
            yield $outSheetModel;
        }
        return;
    }

    /**
     * 获取该时间范围内的影响再生产的领料出库单列表
     */
    public function getOutSheetNumberInfoListForProduce(){
        $out_sheet_number_info_list = [];
        //处理原料
        $materialWmsStatisticsBase = new MaterialWmsStatisticsBase();
        $materialWmsStatisticsBase->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
        $materialWmsStatisticsBase->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
        $wmsMaterialInSheetModels = $materialWmsStatisticsBase->getWmsInSheetForProduce();
        $wmsMaterialOutSheetModels = $materialWmsStatisticsBase->getWmsOutSheetForProduce();

        //处理成品
        $productWmsStatisticsBase = new ProductWmsStatisticsBase();
        $productWmsStatisticsBase->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
        $productWmsStatisticsBase->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
        $wmsProductInSheetModels = $productWmsStatisticsBase->getWmsInSheetForProduce();
        $wmsProductOutSheetModels = $productWmsStatisticsBase->getWmsOutSheetForProduce();

        //半成品
        $partiallyProductWmsStatisticsBase = new PartiallyProductWmsStatisticsBase();
        $partiallyProductWmsStatisticsBase->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
        $partiallyProductWmsStatisticsBase->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
        $wmsPartiallyProductInSheetModels = $partiallyProductWmsStatisticsBase->getWmsInSheetForProduce();
        $wmsPartiallyProductOutSheetModels = $partiallyProductWmsStatisticsBase->getWmsOutSheetForProduce();

        //生产批记录单
        $produceRecordWmsStatisticsBase = new ProduceRecordWmsStatisticsBase();
        $produceRecordWmsStatisticsBase->setWmsStatisticsDateBegin($this->wms_statistics_date_begin);
        $produceRecordWmsStatisticsBase->setWmsStatisticsDateEnd($this->wms_statistics_date_end);
        $produceRecordSheetModels = $produceRecordWmsStatisticsBase->getProduceRecordForFinishOrDelete();

        //遍历原料入库单

        //遍历原料出库单
        foreach ($wmsMaterialOutSheetModels as $wmsMaterialOutSheetModel){
            $out_sheet_number = $wmsMaterialOutSheetModel->wms_material_out_sheet_number;
//            $updated_at = $wmsMaterialOutSheetModel->updated_at;
           $updated_at = !empty($wmsMaterialOutSheetModel->wms_material_out_sheet_outgoing_date) ? $wmsMaterialOutSheetModel->wms_material_out_sheet_outgoing_date : $wmsMaterialOutSheetModel->updated_at;
            self::repushOutSheetNumber($out_sheet_number_info_list, $out_sheet_number, $updated_at);
        }
        //遍历成品入库单
        foreach ($wmsProductInSheetModels as $productInSheetModel){
            if (strpos($productInSheetModel->produce_record_sheet_number, 'SCJL') !== false){
                $out_sheet_number = \core\models\ProduceRecordWmsStatisticsBase::getOutSheetNumberByProduceNumber($productInSheetModel->produce_record_sheet_number);
                //                $updated_at = $productInSheetModel->updated_at;
                $updated_at = !empty($productInSheetModel->wms_product_in_sheet_product_in_date) ? $productInSheetModel->wms_product_in_sheet_product_in_date : $productInSheetModel->updated_at;
                self::repushOutSheetNumber($out_sheet_number_info_list, $out_sheet_number, $updated_at);
            }
        }

        //遍历成品出库单
        foreach ($wmsProductOutSheetModels as $wmsProductOutSheetModel){
            $out_sheet_number = $wmsProductOutSheetModel->wms_product_out_sheet_number;
//            $updated_at = $wmsProductOutSheetModel->updated_at;
            $updated_at = !empty($wmsProductOutSheetModel->wms_product_out_sheet_product_out_date) ? $wmsProductOutSheetModel->wms_product_out_sheet_product_out_date : $wmsProductOutSheetModel->updated_at;
            self::repushOutSheetNumber($out_sheet_number_info_list, $out_sheet_number, $updated_at);
        }

        //遍历半成品入库单
        foreach ($wmsPartiallyProductInSheetModels as $wmsPartiallyProductInSheetModel){
            if (strpos($wmsPartiallyProductInSheetModel->produce_record_sheet_number, 'SCJL') !== false){
                $out_sheet_number = \core\models\ProduceRecordWmsStatisticsBase::getOutSheetNumberByProduceNumber($wmsPartiallyProductInSheetModel->produce_record_sheet_number);
//                $updated_at = $wmsPartiallyProductInSheetModel->updated_at;
                $updated_at = !empty($wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_product_in_date) ? $wmsPartiallyProductInSheetModel->wms_partially_product_in_sheet_product_in_date : $wmsPartiallyProductInSheetModel->updated_at;
                self::repushOutSheetNumber($out_sheet_number_info_list, $out_sheet_number, $updated_at);
            }
        }
        //遍历半成品出库单
        foreach ($wmsPartiallyProductOutSheetModels as $wmsPartiallyProductOutSheetModel){
            $out_sheet_number = $wmsPartiallyProductOutSheetModel->wms_partially_product_out_sheet_number;
//            $updated_at = $wmsPartiallyProductOutSheetModel->updated_at;
            $updated_at = !empty($wmsPartiallyProductOutSheetModel->wms_partially_product_out_sheet_outgoing_date) ? $wmsPartiallyProductOutSheetModel->wms_partially_product_out_sheet_outgoing_date : $wmsPartiallyProductOutSheetModel->updated_at;
            self::repushOutSheetNumber($out_sheet_number_info_list, $out_sheet_number, $updated_at);
        }
        //遍历生产批记录单
        foreach ($produceRecordSheetModels as $produceRecordSheetModel){
            $out_sheet_number = \core\models\ProduceRecordWmsStatisticsBase::getOutSheetNumberByProduceNumber($produceRecordSheetModel->produce_record_sheet_code);
            $updated_at = $produceRecordSheetModel->updated_at;
            self::repushOutSheetNumber($out_sheet_number_info_list, $out_sheet_number, $updated_at);
        }
        return $out_sheet_number_info_list;
    }

    /**
     * @param $out_sheet_number_info_list
     * @param $out_sheet_number
     * @param $updated_at
     * @return mixed
     * 更新影响再生产的领料单号队列
     */
    private static function repushOutSheetNumber(&$out_sheet_number_info_list, $out_sheet_number, $updated_at){
        $_updated_at = strtotime(date('Y-m-d', $updated_at)) + 86400;
        if(isset($out_sheet_number_info_list[$out_sheet_number]['updated_at_list']) && !empty($out_sheet_number_info_list[$out_sheet_number]['updated_at_list'])){
            $updated_at_list = array_merge($out_sheet_number_info_list[$out_sheet_number]['updated_at_list'], [$_updated_at]);
            $updated_at_list = array_unique($updated_at_list);
            sort($updated_at_list, SORT_NUMERIC);
        }else{
            $updated_at_list = [$_updated_at];
        }
        $out_sheet_number_info_list[$out_sheet_number]['updated_at_list'] = $updated_at_list;
    }


    public function run($tty){
        $successNum = 0;
        $this->output("正在查询所有生产加工出库单,请稍等...", Console::FG_YELLOW, $tty);
        $out_sheet_number_info_list = $this->getOutSheetNumberInfoListForProduce();
        foreach ($out_sheet_number_info_list as $out_sheet_number=>$out_sheet_number_info){
            $updated_at_list = $out_sheet_number_info['updated_at_list'];

            foreach ($updated_at_list as $day_at){
                $transaction = \Yii::$app->db->beginTransaction();
                try {
                    if($wmsStatisticsTour = $this->handleTour($out_sheet_number, $day_at)){
                        $successNum += 1;
                        $this->output("出库单".$out_sheet_number."[".date('Y-m-d', $day_at)."]"."记录再生产成功[期初:".$wmsStatisticsTour->total_weight_begin."增加:".$wmsStatisticsTour->total_weight_add."减少:".$wmsStatisticsTour->total_weight_sub."期末:".$wmsStatisticsTour->total_weight_end."]", Console::FG_GREEN, $tty);
                    }else{
                        $this->output("出库单".$out_sheet_number."[".date('Y-m-d', $day_at)."]"."记录再生产失败", Console::FG_RED, $tty);
                    }
                    $transaction->commit();
                }catch (\yii\db\Exception $e){
                    $transaction->rollBack();
                    $this->output($e->getMessage()."已经成功回滚", Console::FG_RED, $tty);
                }
            }
        }
        unset($out_sheet_number_info_list);
        return $successNum;
    }
}
03-25 01:52