Files
onboard/app/Services/Reports/PatientQueryBuilder.php

119 lines
4.7 KiB
PHP

<?php
namespace App\Services\Reports;
use App\Models\MisMedicalHistory;
use App\Models\MisMigrationPatient;
use Illuminate\Support\Carbon;
class PatientQueryBuilder
{
public function __construct(
private int $branchId,
private string $startDate,
private string $endDate,
private bool $isHeadOrAdmin
) {}
public function forStatus(string $status, bool $onlyIds = false): mixed
{
$query = match ($status) {
'plan', 'emergency' => $this->buildPlanEmergencyQuery($status),
'outcome', 'outcome-transferred', 'outcome-deceased' => $this->buildOutcomeQuery($status),
'recipient' => $this->buildRecipientQuery(),
'current' => $this->buildCurrentQuery(),
default => throw new \InvalidArgumentException("Unknown status: $status"),
};
return $onlyIds ? $query->pluck('MedicalHistoryID')->values() : $query->get();
}
private function buildPlanEmergencyQuery(string $status)
{
// Логика из getPlanOrEmergencyPatients, но без if/else по роли внутри
$medicalHistoryIds = $this->isHeadOrAdmin
? MisMigrationPatient::whereInDepartment($this->branchId)
->whereBetween('DateIngoing', [$this->startDate, $this->endDate])
->pluck('rf_MedicalHistoryID')
: MisMigrationPatient::currentlyInTreatment($this->branchId)
->whereBetween('DateIngoing', [$this->startDate, $this->endDate])
->pluck('rf_MedicalHistoryID');
if ($medicalHistoryIds->isEmpty()) {
return MisMedicalHistory::query()->whereRaw('1=0'); // пустой запрос
}
$query = MisMedicalHistory::whereIn('MedicalHistoryID', $medicalHistoryIds)
->with(['surgicalOperations' => fn($q) => $q->whereBetween('Date', [$this->startDate, $this->endDate])])
->orderBy('DateRecipient', 'DESC');
if ($status === 'plan') {
$query->plan();
} elseif ($status === 'emergency') {
$query->emergency();
}
if (! $this->isHeadOrAdmin) {
$query->currentlyHospitalized();
}
return $query;
}
private function buildOutcomeQuery(string $status): \Illuminate\Database\Eloquent\Builder
{
$visitResultIds = match ($status) {
'outcome-transferred' => [4, 14],
'outcome-deceased' => [5, 6, 15, 16],
default => [1, 11, 2, 12, 7, 18, 48], // discharged
};
return MisMedicalHistory::query()
->whereDate('DateExtract', '>', Carbon::parse($this->startDate)->toDateString())
->whereDate('DateExtract', '<=', Carbon::parse($this->endDate)->toDateString())
->whereHas('migrations', function ($q) use ($visitResultIds) {
$q->where('rf_StationarBranchID', $this->branchId)
->whereIn('rf_kl_VisitResultID', $visitResultIds);
})
->with(['surgicalOperations'])
->orderBy('DateRecipient', 'DESC');
}
private function buildRecipientQuery(string $status): \Illuminate\Database\Eloquent\Builder
{
$visitResultIds = match ($status) {
'outcome-transferred' => [4, 14],
'outcome-deceased' => [5, 6, 15, 16],
default => [1, 11, 2, 12, 7, 18, 48], // discharged
};
return MisMedicalHistory::query()
->whereDate('DateExtract', '>', Carbon::parse($this->startDate)->toDateString())
->whereDate('DateExtract', '<=', Carbon::parse($this->endDate)->toDateString())
->whereHas('migrations', function ($q) use ($visitResultIds) {
$q->where('rf_StationarBranchID', $this->branchId)
->whereIn('rf_kl_VisitResultID', $visitResultIds);
})
->with(['surgicalOperations'])
->orderBy('DateRecipient', 'DESC');
}
private function buildCurrentQuery(string $status): \Illuminate\Database\Eloquent\Builder
{
$visitResultIds = match ($status) {
'outcome-transferred' => [4, 14],
'outcome-deceased' => [5, 6, 15, 16],
default => [1, 11, 2, 12, 7, 18, 48], // discharged
};
return MisMedicalHistory::query()
->whereDate('DateExtract', '>', Carbon::parse($this->startDate)->toDateString())
->whereDate('DateExtract', '<=', Carbon::parse($this->endDate)->toDateString())
->whereHas('migrations', function ($q) use ($visitResultIds) {
$q->where('rf_StationarBranchID', $this->branchId)
->whereIn('rf_kl_VisitResultID', $visitResultIds);
})
->with(['surgicalOperations'])
->orderBy('DateRecipient', 'DESC');
}
}