unidade_almoxarifado_id); $unidadeRequisitante = is_null($request->unidade_id) ? null : Unidade::find($request->unidade_id); $dataInicial = Carbon::create($request->data_inicial)->startOfDay(); $dataFinal = Carbon::create($request->data_final)->endOfDay(); $saidas = DB::table('almoxarifado_saida_item_entrada_item AS saida_item_entrada_item') ->join( 'almoxarifado_entrada_item AS entrada_item', 'entrada_item.id', 'saida_item_entrada_item.entrada_item_id' ) ->join( 'almoxarifado_saida_item AS saida_item', 'saida_item.id', 'saida_item_entrada_item.saida_item_id' ) ->join( 'almoxarifado_saida AS saida', 'saida.id', 'saida_item.saida_id' ) ->join( 'web_service_almoxarifado_cliente_material AS cliente_material', 'cliente_material.conectasus_material_id', 'saida_item.material_id' ) ->leftJoin( 'almoxarifado_saida_requisicao AS saida_requisicao', 'saida_requisicao.saida_id', 'saida.id' ) ->leftJoin( 'almoxarifado_saida_transferencia AS saida_transferencia', 'saida_transferencia.saida_id', 'saida.id' ) ->leftJoin( 'almoxarifado_requisicao_resposta AS requisicao_resposta', 'requisicao_resposta.saida_id', 'saida.id' ) ->leftJoin( 'almoxarifado_requisicao AS requisicao', 'requisicao.id', 'requisicao_resposta.requisicao_id' ) ->leftJoin( 'web_service_almoxarifado_cliente_unidade AS cliente_unidade_requisitante', 'cliente_unidade_requisitante.conectasus_centro_custo_id', DB::raw("COALESCE( saida_requisicao.centro_custo_id, saida_transferencia.centro_custo_id, requisicao.created_centro_custo_id )") ) ->where('saida.finalizada', true) ->where('saida.centro_custo_id', $unidadeAlmoxarifado->conectasus_centro_custo_id) ->whereBetween('saida.created_at', [$dataInicial, $dataFinal]) ->where('saida.tipo_id', '<>', SaidaTipo::ESTORNO) ->when($unidadeRequisitante->conectasus_centro_custo_id ?? null, fn ($q, $id) => $q->where(fn ($q) => $q ->where('saida_requisicao.centro_custo_id', $id) ->orWhere('saida_transferencia.centro_custo_id', $id) ->orWhere('requisicao.created_centro_custo_id', $id) )) ->when(DataUtil::isStringBoolean($request->query('is_estornada')), fn ($q) => $q ->when(DataUtil::isStringTrue($request->query('is_estornada')), fn ($q) => $q->whereNotNull('saida_item.estornado_em'), fn ($q) => $q->whereNull('saida_item.estornado_em') ) ) ->select([ DB::raw("CAST(saida.created_at AS DATE) AS data"), DB::raw("CAST(saida_item.estornado_em AS DATE) AS data_estorno"), 'cliente_unidade_requisitante.id AS unidade_id', 'cliente_material.id AS material_id', 'entrada_item.lote', 'entrada_item.validade_lote', DB::raw('IF(saida_item.estornado_em IS NULL, 0, 1) AS is_estornada'), DB::raw("SUM(saida_item_entrada_item.quantidade_saida) AS quantidade"), ]) ->orderBy('saida.created_at') ->orderBy('saida_item.estornado_em') ->groupBy([ DB::raw("CAST(saida.created_at AS DATE)"), DB::raw("CAST(saida_item.estornado_em AS DATE)"), 'cliente_unidade_requisitante.id', 'cliente_material.id', 'entrada_item.lote', 'entrada_item.validade_lote', DB::raw('IF(saida_item.estornado_em IS NULL, 0, 1)'), ]) ->get(); return tap($saidas)->each(function ($saida) { $saida->is_estornada = (bool) $saida->is_estornada; $saida->quantidade = (int) $saida->quantidade; }); } private static function validateIndex($request) { $request->validate([ 'data_inicial' => [ 'required', 'date_format:Y-m-d', 'before_or_equal:data_final', ], 'data_final' => [ 'required', 'date_format:Y-m-d', 'after_or_equal:data_inicial', ], 'unidade_almoxarifado_id' => [ 'bail', 'required', 'integer', Rule::exists(Unidade::class, 'id'), function ($attribute, $value, $fail) { if (!Unidade::find($value)->is_almoxarifado) { $fail("O campo {$attribute} não é um almoxarifado."); } }, function ($attribute, $value, $fail) { if (is_null(Unidade::find($value)->conectasus_centro_custo_id)) { $fail("O campo {$attribute} não está vinculado com um centro de custo do ConectaSUS."); } }, ], 'unidade_id' => [ 'bail', 'integer', Rule::exists(Unidade::class, 'id'), function ($attribute, $value, $fail) { if (is_null(Unidade::find($value)->conectasus_centro_custo_id)) { $fail("O campo {$attribute} não está vinculado com um centro de custo do ConectaSUS."); } }, ], 'is_estornada' => [ 'string', Rule::in('true', 'false'), ] ]); $dataInicial = Carbon::create($request->data_inicial); $dataFinal = Carbon::create($request->data_final); if ($dataInicial->diff($dataFinal)->days > self::LIMITE_DIAS_PERIODO_BUSCA) { throw new InvalidSearchPeriodException(); } } }