stationService=null; $this->stationTypeService=null; $this->stationTaskService=null; $this->materialBoxService=null; } function get(array $kvPairs){ ksort($kvPairs); return Cache::remember('stationTaskChild_'.md5(json_encode($kvPairs)), config('cache.expirations.oftenChange'), function ()use($kvPairs) { $query = StationTaskCommodity::query(); foreach ($kvPairs as $column => $value){ if (is_array($value))$query->whereIn($column,$value); else $query->where($column,$value); } return $query->get(); }); } function createByBatches(Collection $batches,Collection $stationTasks_toAttach): Collection { $this->instant($this->stationTaskService,'StationTaskService'); $stationTaskCommodities_lists_ByBatch=new Collection(); $stationTaskCommodities=new Collection(); foreach ($batches as $batch){ $taskCommodities = $this->createByBatch($batch); $stationTaskCommodities= $stationTaskCommodities->merge($taskCommodities); $stationTaskCommodities_lists_ByBatch->push($taskCommodities); } // $stationTaskCommodities=$this->getAndAttachIds($stationTaskCommodities); $this->stationTaskService->registerSubTasks( $stationTasks_toAttach, $stationTaskCommodities_lists_ByBatch); return $stationTaskCommodities; } // function getAndAttachIds($taskCommodities): Collection // { // $md5=is_array($taskCommodities) // ?$md5=md5(json_encode($taskCommodities)):null; // // return Cache::remember( // 'StationTaskCommodity_'.$md5??md5(json_encode($taskCommodities->toArray())) // ,config('cache.expirations.rarelyChange') // ,function()use($taskCommodities){ // $a=data_get($taskCommodities,'*.status'); // $a2=data_get($taskCommodities,'*.station_task_batch_id'); // $a3=data_get($taskCommodities,'*.commodity_id'); // $a4=StationTaskCommodity::query() // ->whereIn('status',data_get($taskCommodities,'*.status')) // ->whereIn('station_task_batch_id',data_get($taskCommodities,'*.station_task_batch_id')) // ->whereIn('commodity_id',data_get($taskCommodities,'*.commodity_id')) // ->get(); // $a5=1; // return StationTaskCommodity::query() // ->whereIn('status',data_get($taskCommodities,'*.status')) // ->whereIn('station_task_batch_id',data_get($taskCommodities,'*.station_task_batch_id')) // ->whereIn('commodity_id',data_get($taskCommodities,'*.commodity_id')) // ->get(); // }); // } function createByBatch(Batch $batch): Collection { $this->instant($this->stationTypeService,'StationTypeService'); $this->instant($this->stationService,'StationService'); $this->instant($this->materialBoxService,'MaterialBoxService'); $this->instant($this->stationTaskBatchService,'StationTaskBatchService'); $stationTaskCommodities_toCreate=new Collection(); $order_ids=data_get($batch['orders'],'*.id'); $orderCommodities=OrderCommodity::query()->with('orderBin')->whereIn('order_id',$order_ids)->get(); $stationTaskBatch=$this->stationTaskBatchService->get(['batch_id'=>$batch['id']])->first(); foreach ($orderCommodities as $orderCommodity){ $stationType=$this->stationTypeService->getForCommodity(); $station=$this->stationService->getStation_byType($stationType['name']); $materialBox=$this->materialBoxService->firstOrCreate(['code' => $orderCommodity['location']]); $stationTaskMaterialBoxId=StationTaskMaterialBox::query()->where('station_task_batch_id',$stationTaskBatch['id'])->where('material_box_id',$materialBox['id'])->get('id')->first()['id']??null; $stationTaskCommodities_toCreate->push( new StationTaskCommodity([ 'station_id'=>$station['id'], // 'material_box_id'=>$materialBox['id'], 'material_box_position'=>$orderCommodity['material_box_position'], 'commodity_id'=>$orderCommodity['commodity_id'], 'amount'=>$orderCommodity['amount'], 'bin_number'=>$orderCommodity['orderBin']['number']??'', 'order_id'=>$orderCommodity['order_id'], 'station_task_batch_id'=>$stationTaskBatch['id'], 'station_task_material_box_id'=>$stationTaskMaterialBoxId, 'status'=>'待处理', ]) ); } return $this->insert($stationTaskCommodities_toCreate->toArray(),true); } function markProcessing($stationTaskCommodity_orCollection) { $stationTaskCommodities = (function()use($stationTaskCommodity_orCollection){ if (get_class($stationTaskCommodity_orCollection)==StationTaskCommodity::class){ return collect([$stationTaskCommodity_orCollection]); } return collect($stationTaskCommodity_orCollection); })(); $stationTaskCommodities_grouped= ($按时间从前往后排出顺序=function ()use(&$stationTaskCommodities){ return $stationTaskCommodities ->sortBy('id') ->groupBy('station_task_batch_id'); })(); $stationTaskCommodities_grouped->each(function(&$groupByBatch){ ($标记本波次内是处理中或处理队列=function()use(&$groupByBatch){ $stationId=$groupByBatch[0]['station_id']; $processingIds=data_get($this->getProcessings_byStationId($stationId),'*.id')??[]; $groupByBatch->each(function(&$stationTaskCommodity)use($processingIds){ if(in_array($stationTaskCommodity['id'],$processingIds)) $stationTaskCommodity['status']='处理中'; else $stationTaskCommodity['status']='处理队列'; }); if(count($processingIds)==0){ foreach($groupByBatch as &$stationTaskCommodity){ if($stationTaskCommodity['station_task_material_box_id']==$groupByBatch[0]['station_task_material_box_id']){ $stationTaskCommodity['status']='处理中'; } } } })(); }); ($持久化处理队列的记录=function()use(&$stationTaskCommodities_grouped){ $toArray = $stationTaskCommodities_grouped->collapse(); $toQueue=$toArray->where('status','处理队列'); $toProcess=$toArray->where('status','处理中'); $ids_toQueue_toUpdate = data_get($toQueue, '*.id'); if(count($ids_toQueue_toUpdate)) StationTaskCommodity::query()->whereIn('id',$ids_toQueue_toUpdate)->update(['status'=>'处理队列']); $ids_toProcess_toUpdate = data_get($toProcess, '*.id'); if(count($ids_toProcess_toUpdate)) StationTaskCommodity::query()->whereIn('id',$ids_toProcess_toUpdate)->update(['status'=>'处理中']); })(); } function getProcessings_byStationId($stationTaskBatch_id) { //这里不好用缓存,因为更新会非常快 return StationTaskCommodity::query() ->where('station_id',$stationTaskBatch_id) ->where('status','处理中') ->get(); } function markProcessed(Collection $stationTaskCommodities){ StationTaskCommodity::query() ->whereIn('id',data_get($stationTaskCommodities,'*.id')??[]) ->update(['status'=>'完成']); $stationTaskMaterialBoxes=StationTaskMaterialBox::query() ->whereIn('id', data_get($stationTaskCommodities, '*.station_task_material_box_id') ?? []) ->get('material_box_id'); $boxes = data_get($stationTaskMaterialBoxes,'*.material_box_id')??[]; $commodities = data_get($stationTaskCommodities,'*.commodity_id')??[]; $map = []; foreach ($stationTaskCommodities as $commodity){ $map[$commodity->material_box_id."-".$commodity->commodity_id] = $commodity->amount; } MaterialBoxCommodity::query()->whereIn('commodity_id',$commodities) ->whereIn('material_box_id',$boxes)->lockForUpdate() ->get()->each(function ($boxC)use($map){ $key = $boxC->material_box_id."-".$boxC->commodity_id; if (!isset($map[$key]))return false; if ($boxC->amount>$map[$key])$boxC->update(["amount"=>DB::raw("amount-{$map[$key]}")]); if ($boxC->amount==$map[$key])$boxC->delete(); return true; }); } }