import pghistory
from django.conf import settings
from django.contrib.postgres.fields import ArrayField
from django.db import models
from django.urls import reverse
from django.utils.text import slugify

from apps.core.choices.fields import RichChoiceField
from apps.core.history import HistoricalSlug
from apps.core.models import TrackedModel


@pghistory.track()
class Company(TrackedModel):
    name = models.CharField(max_length=255, help_text="Company name")
    slug = models.SlugField(max_length=255, unique=True, help_text="URL-friendly identifier")
    roles = ArrayField(
        RichChoiceField(choice_group="company_roles", domain="rides", max_length=20),
        default=list,
        blank=True,
        help_text="Company roles (manufacturer, designer, etc.)",
    )
    description = models.TextField(blank=True, help_text="Detailed company description")
    website = models.URLField(blank=True, help_text="Company website URL")
    
    # Person/Entity type
    PERSON_TYPE_CHOICES = [
        ("company", "Company"),
        ("individual", "Individual"),
        ("firm", "Firm"),
        ("organization", "Organization"),
    ]
    person_type = models.CharField(
        max_length=20,
        choices=PERSON_TYPE_CHOICES,
        blank=True,
        default="company",
        help_text="Type of entity (company, individual, firm, organization)",
    )

    # General company info
    founded_date = models.DateField(null=True, blank=True, help_text="Date the company was founded")
    founded_date_precision = models.CharField(
        max_length=20,
        choices=[
            ("exact", "Exact"),
            ("month", "Month"),
            ("year", "Year"),
            ("decade", "Decade"),
            ("century", "Century"),
            ("approximate", "Approximate"),
        ],
        blank=True,
        default="",
        help_text="Precision of the founded date",
    )
    founded_year = models.PositiveIntegerField(
        null=True,
        blank=True,
        help_text="Year the company was founded (alternative to founded_date)",
    )
    headquarters_location = models.CharField(
        max_length=200,
        blank=True,
        help_text="Headquarters location description (e.g., 'Los Angeles, CA, USA')",
    )

    # Location relationship (optional)
    location = models.ForeignKey(
        "parks.ParkLocation",
        on_delete=models.SET_NULL,
        null=True,
        blank=True,
        related_name="companies",
        help_text="Linked location record for headquarters",
    )

    # Image settings - stored as Cloudflare image IDs/URLs
    banner_image_id = models.CharField(
        max_length=255,
        blank=True,
        help_text="Cloudflare image ID for banner image",
    )
    card_image_id = models.CharField(
        max_length=255,
        blank=True,
        help_text="Cloudflare image ID for card image",
    )

    # Manufacturer-specific fields
    rides_count = models.IntegerField(default=0, help_text="Number of rides manufactured (auto-calculated)")
    coasters_count = models.IntegerField(default=0, help_text="Number of coasters manufactured (auto-calculated)")

    # Frontend URL
    url = models.URLField(blank=True, help_text="Frontend URL for this company")

    # Submission metadata fields (from frontend schema)
    source_url = models.URLField(
        blank=True,
        help_text="Source URL for the data (e.g., official website, Wikipedia)",
    )
    is_test_data = models.BooleanField(
        default=False,
        help_text="Whether this is test/development data",
    )

    def __str__(self):
        return self.name

    def save(self, *args, **kwargs):
        if not self.slug:
            self.slug = slugify(self.name)

        # Generate frontend URL based on primary role
        # CRITICAL: Only MANUFACTURER and DESIGNER are for rides domain
        # OPERATOR and PROPERTY_OWNER are for parks domain and handled separately
        if self.roles:
            frontend_domain = getattr(settings, "FRONTEND_DOMAIN", "https://thrillwiki.com")
            primary_role = self.roles[0]  # Use first role as primary

            if primary_role == "MANUFACTURER":
                self.url = f"{frontend_domain}/rides/manufacturers/{self.slug}/"
            elif primary_role == "DESIGNER":
                self.url = f"{frontend_domain}/rides/designers/{self.slug}/"
            # OPERATOR and PROPERTY_OWNER URLs are handled by parks domain, not here

        super().save(*args, **kwargs)

    def get_absolute_url(self):
        # This will need to be updated to handle different roles
        return reverse("companies:detail", kwargs={"slug": self.slug})

    @classmethod
    def get_by_slug(cls, slug):
        """Get company by current or historical slug"""
        try:
            return cls.objects.get(slug=slug), False
        except cls.DoesNotExist:
            # Check pghistory first
            try:
                from django.apps import apps

                history_model = apps.get_model("rides", f"{cls.__name__}Event")
                history_entry = history_model.objects.filter(slug=slug).order_by("-pgh_created_at").first()
                if history_entry:
                    return cls.objects.get(id=history_entry.pgh_obj_id), True
            except LookupError:
                # History model doesn't exist, skip pghistory check
                pass

            # Check manual slug history as fallback
            try:
                historical = HistoricalSlug.objects.get(content_type__model="company", slug=slug)
                return cls.objects.get(pk=historical.object_id), True
            except (HistoricalSlug.DoesNotExist, cls.DoesNotExist):
                raise cls.DoesNotExist("No company found with this slug") from None

    class Meta(TrackedModel.Meta):
        app_label = "rides"
        verbose_name = "Company"
        verbose_name_plural = "Companies"
        ordering = ["name"]
