# Generated by Django 5.2.5 on 2025-09-14 19:12

from django.db import migrations


class Migration(migrations.Migration):

    dependencies = [
        ("parks", "0015_populate_hybrid_filtering_fields"),
    ]

    operations = [
        # Composite indexes for common filter combinations
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_status_park_type_idx ON parks_park (status, park_type);",
            reverse_sql="DROP INDEX IF EXISTS parks_park_status_park_type_idx;",
        ),
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_opening_year_status_idx ON parks_park (opening_year, status) WHERE opening_year IS NOT NULL;",
            reverse_sql="DROP INDEX IF EXISTS parks_park_opening_year_status_idx;",
        ),
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_size_rating_idx ON parks_park (size_acres, average_rating) WHERE size_acres IS NOT NULL AND average_rating IS NOT NULL;",
            reverse_sql="DROP INDEX IF EXISTS parks_park_size_rating_idx;",
        ),
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_ride_coaster_count_idx ON parks_park (ride_count, coaster_count) WHERE ride_count IS NOT NULL AND coaster_count IS NOT NULL;",
            reverse_sql="DROP INDEX IF EXISTS parks_park_ride_coaster_count_idx;",
        ),
        # Full-text search index for search_text field
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_search_text_gin_idx ON parks_park USING gin(to_tsvector('english', search_text));",
            reverse_sql="DROP INDEX IF EXISTS parks_park_search_text_gin_idx;",
        ),
        # Trigram index for fuzzy search on search_text
        migrations.RunSQL(
            "CREATE EXTENSION IF NOT EXISTS pg_trgm;",
            reverse_sql="-- Cannot drop extension as it might be used elsewhere",
        ),
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_search_text_trgm_idx ON parks_park USING gin(search_text gin_trgm_ops);",
            reverse_sql="DROP INDEX IF EXISTS parks_park_search_text_trgm_idx;",
        ),
        # Indexes for location-based filtering (assuming location relationship exists)
        migrations.RunSQL(
            """
            CREATE INDEX IF NOT EXISTS parks_parklocation_country_state_idx
            ON parks_parklocation (country, state)
            WHERE country IS NOT NULL AND state IS NOT NULL;
            """,
            reverse_sql="DROP INDEX IF EXISTS parks_parklocation_country_state_idx;",
        ),
        # Index for operator-based filtering
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_operator_status_idx ON parks_park (operator_id, status);",
            reverse_sql="DROP INDEX IF EXISTS parks_park_operator_status_idx;",
        ),
        # Partial indexes for common status filters
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_operating_parks_idx ON parks_park (name, opening_year) WHERE status IN ('OPERATING', 'CLOSED_TEMP');",
            reverse_sql="DROP INDEX IF EXISTS parks_park_operating_parks_idx;",
        ),
        # Index for ordering by name (already exists but ensuring it's optimized)
        migrations.RunSQL(
            "CREATE INDEX IF NOT EXISTS parks_park_name_lower_idx ON parks_park (LOWER(name));",
            reverse_sql="DROP INDEX IF EXISTS parks_park_name_lower_idx;",
        ),
        # Covering index for common query patterns
        migrations.RunSQL(
            """
            CREATE INDEX IF NOT EXISTS parks_park_hybrid_covering_idx
            ON parks_park (status, park_type, opening_year)
            INCLUDE (name, slug, size_acres, average_rating, ride_count, coaster_count, operator_id)
            WHERE status IN ('OPERATING', 'CLOSED_TEMP');
            """,
            reverse_sql="DROP INDEX IF EXISTS parks_park_hybrid_covering_idx;",
        ),
    ]
