from django.db import models
from django.contrib.auth.models import User
from django.core.validators import MinLengthValidator
import uuid
from datetime import timedelta
from django.utils import timezone


class Company(models.Model):
    name = models.CharField(max_length=255)
    is_uprn_required = models.BooleanField(default=False)
    created_at = models.DateTimeField(auto_now_add=True)

    def __str__(self):
        return self.name

class Profile(models.Model):
    ROLE_CHOICES = [
        ('ADMIN', 'Admin'),
        ('STANDARD', 'Standard User'),
    ]
    user = models.OneToOneField(User, on_delete=models.CASCADE, related_name='profile')
    company = models.ForeignKey(Company, on_delete=models.CASCADE, related_name='users', null=True, blank=True)
    role = models.CharField(max_length=20, choices=ROLE_CHOICES, default='STANDARD')

    def __str__(self):
        return f"{self.user.username} - {self.company.name if self.company else 'No Company'}"

class JobStatus(models.Model):
    company = models.ForeignKey(Company, on_delete=models.CASCADE, related_name='statuses')
    name = models.CharField(max_length=100)
    is_starting_status = models.BooleanField(default=False)
    order = models.PositiveIntegerField(default=0)

    class Meta:
        verbose_name_plural = "Job Statuses"
        ordering = ['order']

    def __str__(self):
        return f"{self.name} ({self.company.name})"

class RequiredFolder(models.Model):
    company = models.ForeignKey(Company, on_delete=models.CASCADE, related_name='required_folders')
    name = models.CharField(max_length=100)

    def __str__(self):
        return f"{self.name} ({self.company.name})"

class Client(models.Model):
    company = models.ForeignKey(Company, on_delete=models.CASCADE, related_name='clients')
    name = models.CharField(max_length=255)
    client_job_ref_prefix = models.CharField(max_length=50, blank=True, null=True)

    class Meta:
        unique_together = [['company', 'name']]

    def __str__(self):
        return self.name

class Job(models.Model):
    company = models.ForeignKey(Company, on_delete=models.CASCADE, related_name='jobs')
    client = models.ForeignKey(Client, on_delete=models.PROTECT, related_name='jobs', null=True, blank=True)
    job_ref = models.CharField(max_length=100)
    uprn = models.CharField(max_length=100, null=True, blank=True)
    address_line_1 = models.CharField(max_length=255)
    address_line_2 = models.CharField(max_length=255, null=True, blank=True)
    address_line_3 = models.CharField(max_length=255, null=True, blank=True)
    postcode = models.CharField(max_length=20)
    description = models.TextField(null=True, blank=True)
    action = models.TextField(null=True, blank=True)
    notes = models.TextField(null=True, blank=True)
    status = models.ForeignKey(JobStatus, on_delete=models.PROTECT, related_name='jobs')
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)

    class Meta:
        unique_together = [['company', 'job_ref'], ['company', 'uprn']]
    # Add a custom constraint to allow null=True and blank=True for uprn,
    # but still enforce unique_together when it's not null.
    # This is handled by a custom validator or by overriding save method if needed.
    # For now, Django's unique_together with null=True will allow multiple nulls.


    def __str__(self):
        return f"{self.job_ref} - {self.address_line_1}"

class JobFolderCompletion(models.Model):
    job = models.ForeignKey(Job, on_delete=models.CASCADE, related_name='folder_completions')
    folder = models.ForeignKey(RequiredFolder, on_delete=models.CASCADE)
    is_completed = models.BooleanField(default=False)

    class Meta:
        unique_together = ['job', 'folder']

class JobFile(models.Model):
    job = models.ForeignKey(Job, on_delete=models.CASCADE, related_name='files')
    folder = models.ForeignKey(RequiredFolder, on_delete=models.CASCADE, related_name='files')
    file = models.FileField(upload_to='job_files/')
    uploaded_at = models.DateTimeField(auto_now_add=True)
    uploaded_by = models.ForeignKey(User, on_delete=models.SET_NULL, null=True)

    def __str__(self):
        return f"{self.file.name} in {self.folder.name}"

class Invitation(models.Model):
    company = models.ForeignKey(Company, on_delete=models.CASCADE, related_name='invitations')
    invited_by = models.ForeignKey(User, on_delete=models.CASCADE)
    email = models.EmailField(unique=True)
    token = models.CharField(max_length=32, unique=True, default=uuid.uuid4().hex)
    created_at = models.DateTimeField(auto_now_add=True)
    expires_at = models.DateTimeField(default=timezone.now() + timedelta(days=7))
    is_accepted = models.BooleanField(default=False)

    def __str__(self):
        return f"Invitation for {self.email} to {self.company.name}"