from django.db import models from django.utils.text import slugify from django.urls import reverse from django.contrib.contenttypes.models import ContentType from typing import Tuple, Optional, ClassVar, TYPE_CHECKING from history_tracking.models import HistoricalModel, VersionBranch, ChangeSet from history_tracking.signals import get_current_branch, ChangesetContextManager if TYPE_CHECKING: from history_tracking.models import HistoricalSlug class Company(HistoricalModel): name = models.CharField(max_length=255) slug = models.SlugField(max_length=255, unique=True) website = models.URLField(blank=True) headquarters = models.CharField(max_length=255, blank=True) description = models.TextField(blank=True) total_parks = models.IntegerField(default=0) total_rides = models.IntegerField(default=0) created_at = models.DateTimeField(auto_now_add=True) updated_at = models.DateTimeField(auto_now=True) objects: ClassVar[models.Manager['Company']] class Meta: verbose_name_plural = 'companies' ordering = ['name'] def __str__(self) -> str: return self.name def save(self, *args, **kwargs) -> None: if not self.slug: self.slug = slugify(self.name) # Get the branch from context or use default current_branch = get_current_branch() if current_branch: # Save in the context of the current branch super().save(*args, **kwargs) else: # If no branch context, save in main branch main_branch, _ = VersionBranch.objects.get_or_create( name='main', defaults={'metadata': {'type': 'default_branch'}} ) with ChangesetContextManager(branch=main_branch): super().save(*args, **kwargs) def get_version_info(self) -> dict: """Get version control information for this company""" content_type = ContentType.objects.get_for_model(self) latest_changes = ChangeSet.objects.filter( content_type=content_type, object_id=self.pk, status='applied' ).order_by('-created_at')[:5] active_branches = VersionBranch.objects.filter( changesets__content_type=content_type, changesets__object_id=self.pk, is_active=True ).distinct() return { 'latest_changes': latest_changes, 'active_branches': active_branches, 'current_branch': get_current_branch(), 'total_changes': latest_changes.count() } def get_absolute_url(self) -> str: return reverse("companies:company_detail", kwargs={"slug": self.slug}) @classmethod def get_by_slug(cls, slug: str) -> Tuple['Company', bool]: """Get company by slug, checking historical slugs if needed""" try: return cls.objects.get(slug=slug), False except cls.DoesNotExist: # Check historical slugs from history_tracking.models import HistoricalSlug 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() class Manufacturer(HistoricalModel): name = models.CharField(max_length=255) slug = models.SlugField(max_length=255, unique=True) website = models.URLField(blank=True) headquarters = models.CharField(max_length=255, blank=True) description = models.TextField(blank=True) total_rides = models.IntegerField(default=0) total_roller_coasters = models.IntegerField(default=0) created_at = models.DateTimeField(auto_now_add=True) updated_at = models.DateTimeField(auto_now=True) objects: ClassVar[models.Manager['Manufacturer']] class Meta: ordering = ['name'] def __str__(self) -> str: return self.name def save(self, *args, **kwargs) -> None: if not self.slug: self.slug = slugify(self.name) # Get the branch from context or use default current_branch = get_current_branch() if current_branch: # Save in the context of the current branch super().save(*args, **kwargs) else: # If no branch context, save in main branch main_branch, _ = VersionBranch.objects.get_or_create( name='main', defaults={'metadata': {'type': 'default_branch'}} ) with ChangesetContextManager(branch=main_branch): super().save(*args, **kwargs) def get_version_info(self) -> dict: """Get version control information for this manufacturer""" content_type = ContentType.objects.get_for_model(self) latest_changes = ChangeSet.objects.filter( content_type=content_type, object_id=self.pk, status='applied' ).order_by('-created_at')[:5] active_branches = VersionBranch.objects.filter( changesets__content_type=content_type, changesets__object_id=self.pk, is_active=True ).distinct() return { 'latest_changes': latest_changes, 'active_branches': active_branches, 'current_branch': get_current_branch(), 'total_changes': latest_changes.count() } def get_absolute_url(self) -> str: return reverse("companies:manufacturer_detail", kwargs={"slug": self.slug}) @classmethod def get_by_slug(cls, slug: str) -> Tuple['Manufacturer', bool]: """Get manufacturer by slug, checking historical slugs if needed""" try: return cls.objects.get(slug=slug), False except cls.DoesNotExist: # Check historical slugs from history_tracking.models import HistoricalSlug try: historical = HistoricalSlug.objects.get( content_type__model='manufacturer', slug=slug ) return cls.objects.get(pk=historical.object_id), True except (HistoricalSlug.DoesNotExist, cls.DoesNotExist): raise cls.DoesNotExist() class Designer(HistoricalModel): name = models.CharField(max_length=255) slug = models.SlugField(max_length=255, unique=True) website = models.URLField(blank=True) description = models.TextField(blank=True) total_rides = models.IntegerField(default=0) total_roller_coasters = models.IntegerField(default=0) created_at = models.DateTimeField(auto_now_add=True) updated_at = models.DateTimeField(auto_now=True) objects: ClassVar[models.Manager['Designer']] class Meta: ordering = ['name'] def __str__(self) -> str: return self.name def save(self, *args, **kwargs) -> None: if not self.slug: self.slug = slugify(self.name) # Get the branch from context or use default current_branch = get_current_branch() if current_branch: # Save in the context of the current branch super().save(*args, **kwargs) else: # If no branch context, save in main branch main_branch, _ = VersionBranch.objects.get_or_create( name='main', defaults={'metadata': {'type': 'default_branch'}} ) with ChangesetContextManager(branch=main_branch): super().save(*args, **kwargs) def get_version_info(self) -> dict: """Get version control information for this designer""" content_type = ContentType.objects.get_for_model(self) latest_changes = ChangeSet.objects.filter( content_type=content_type, object_id=self.pk, status='applied' ).order_by('-created_at')[:5] active_branches = VersionBranch.objects.filter( changesets__content_type=content_type, changesets__object_id=self.pk, is_active=True ).distinct() return { 'latest_changes': latest_changes, 'active_branches': active_branches, 'current_branch': get_current_branch(), 'total_changes': latest_changes.count() } def get_absolute_url(self) -> str: return reverse("companies:designer_detail", kwargs={"slug": self.slug}) @classmethod def get_by_slug(cls, slug: str) -> Tuple['Designer', bool]: """Get designer by slug, checking historical slugs if needed""" try: return cls.objects.get(slug=slug), False except cls.DoesNotExist: # Check historical slugs from history_tracking.models import HistoricalSlug try: historical = HistoricalSlug.objects.get( content_type__model='designer', slug=slug ) return cls.objects.get(pk=historical.object_id), True except (HistoricalSlug.DoesNotExist, cls.DoesNotExist): raise cls.DoesNotExist()