<?php

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

return new class extends Migration
{
    public function up(): void
    {
        /**
         * 1) addresses per user (supports billing/shipping/home/work/etc.)
         *    optional link to `locations` for normalized/geocoded data.
         */
        Schema::create('user_addresses', function (Blueprint $table) {
            $table->bigIncrements('id');

            // users.id is char(26)
            $table->char('user_id', 26);
            $table->string('label', 100)->nullable();  // "Home", "Office"
            $table->string('kind', 20)->nullable();    // "home", "work", etc

            // raw, user-entered fields
            $table->string('line1', 255)->nullable();
            $table->string('line2', 255)->nullable();
            $table->string('city', 100)->nullable();
            $table->string('state', 64)->nullable();
            $table->string('postal', 32)->nullable();
            $table->string('country', 64)->nullable();

            // optional normalized location
            $table->unsignedBigInteger('location_id')->nullable();

            // nullable so unique index allows many NULLs (only 1 with value 1)
            $table->boolean('is_primary')->nullable()->default(null);

            // flag for whether this is the user's billing address
            $table->boolean('is_billing')->default(false);

            $table->timestamps();

            // helpful indexes
            $table->index(['user_id', 'kind']);
            $table->index('postal');
            $table->index(['user_id', 'is_billing']);
            $table->foreign('user_id')->references('id')->on('users')->cascadeOnDelete();
            $table->foreign('location_id')->references('id')->on('locations')->nullOnDelete();

            // enforce at most one primary per (user,kind)
            $table->unique(['user_id', 'kind', 'is_primary'], 'user_kind_primary_unique');
        });

        /**
         * 2) lightweight geocoder bias on users (postal/country + optional centroid).
         */
        Schema::table('users', function (Blueprint $table) {
            $table->string('postal', 32)->nullable()->after('timezone');
            $table->string('country', 64)->nullable()->after('postal');
            $table->decimal('lat', 9, 6)->nullable()->after('country');
            $table->decimal('lon', 9, 6)->nullable()->after('lat');
            $table->index('postal');
        });
    }

    public function down(): void
    {
        Schema::table('users', function (Blueprint $table) {
            if (Schema::hasColumn('users', 'postal'))  $table->dropIndex(['postal']);
            foreach (['postal','country','lat','lon'] as $col) {
                if (Schema::hasColumn('users', $col)) $table->dropColumn($col);
            }
        });

        Schema::table('user_addresses', function (Blueprint $table) {
            if (Schema::hasColumn('user_addresses', 'user_id'))     $table->dropForeign(['user_id']);
            if (Schema::hasColumn('user_addresses', 'location_id')) $table->dropForeign(['location_id']);
        });

        Schema::dropIfExists('user_addresses');
    }
};
