<?php

use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

/**
 * mder_visits — an emergency-department visit (SIFA §9 emergency / er_visit).
 *
 * A visit is the ER analogue of an encounter: it starts at arrival (often before
 * the patient is registered, so patient_id / contact_id are nullable and
 * patient_name is denormalised for board speed), is triaged (writing a real
 * clc_vitals row referenced by triage_vitals_id, appointment_id null), tracked
 * on the live ER board via board_status, then closed with a disposition.
 *
 * medward_admission_id points at Modules\MedWard's medward_admissions row when
 * the admit hand-off succeeds — fail-soft: null when MedWard is absent.
 *
 * business_id-scoped. References into ClinicCore / MedWard are plain indexed
 * columns (no cross-module FK constraints) matching the existing convention.
 */
return new class extends Migration {
    public function up(): void
    {
        if (Schema::hasTable('mder_visits')) {
            return;
        }

        Schema::create('mder_visits', function (Blueprint $t) {
            $t->bigIncrements('id');
            $t->unsignedInteger('business_id');
            $t->string('visit_no', 60);                          // ER-{biz}-{seq}
            $t->unsignedInteger('patient_id')->nullable();       // clc_patients.id (quick-reg fills later)
            $t->unsignedInteger('contact_id')->nullable();       // contacts.id
            $t->string('patient_name', 191)->nullable();         // denormalised for board speed
            $t->timestamp('arrival_at')->nullable();
            $t->enum('arrival_mode', ['walk_in', 'ambulance', 'police', 'transfer', 'other'])->default('walk_in');
            $t->text('chief_complaint')->nullable();
            $t->enum('triage_level', ['resuscitation', 'emergent', 'urgent', 'less_urgent', 'non_urgent'])->nullable();
            $t->enum('triage_system', ['esi', 'manchester', 'ctas'])->default('esi');
            $t->unsignedInteger('triaged_by')->nullable();       // users.id
            $t->timestamp('triaged_at')->nullable();
            $t->unsignedInteger('triage_vitals_id')->nullable(); // clc_vitals.id
            $t->unsignedInteger('assigned_doctor_id')->nullable(); // clc_doctors.id
            $t->enum('board_status', [
                'awaiting_triage', 'to_be_seen', 'in_progress', 'pending_results',
                'pending_disposition', 'admitted_awaiting_bed', 'done',
            ])->default('awaiting_triage');
            $t->enum('disposition', [
                'discharged', 'admitted', 'transferred', 'expired', 'lwbs', 'ama',
            ])->nullable();
            $t->timestamp('disposition_at')->nullable();
            $t->text('disposition_note')->nullable();
            $t->unsignedBigInteger('medward_admission_id')->nullable(); // medward_admissions.id (fail-soft)
            $t->unsignedInteger('created_by')->nullable();       // users.id
            $t->timestamps();

            $t->index(['business_id', 'board_status'], 'mder_visits_biz_board_idx');
            $t->index(['business_id', 'triage_level'], 'mder_visits_biz_triage_idx');
            $t->index(['business_id', 'patient_id'], 'mder_visits_biz_patient_idx');
            $t->index(['business_id', 'arrival_at'], 'mder_visits_biz_arrival_idx');
            $t->unique(['business_id', 'visit_no'], 'mder_visits_biz_no_uq');
        });
    }

    public function down(): void
    {
        Schema::dropIfExists('mder_visits');
    }
};
