from django.conf import settings
from django.db import models
from django_countries.fields import CountryField
from markdownx.models import MarkdownxField
from pirates import models as pirates_models


class User(pirates_models.AbstractUser):
    pass


class ContractExternalSigner(models.Model):
    name = models.CharField(
        max_length=256,
        verbose_name="Jméno",
    )

    is_legal_entity = models.BooleanField(
        verbose_name="Je právnická osoba",
        help_text="Důležité označit správně! Pokud není osoba právnická, zveřejňujeme pouze obec a zemi.",
    )

    address_street_with_number = models.CharField(
        max_length=256,
        verbose_name="Ulice, č.p.",
        help_text="Viditelné pouze u právnických osob.",
    )  # WARNING: Legal entity status dependent!

    address_district = models.CharField(
        max_length=256,
        verbose_name="Obec",
    )

    address_zip = models.CharField(
        max_length=16,
        verbose_name="PSČ",
        help_text="Viditelné pouze u právnických osob.",
    )  # WARNING: Legal entity status dependent!

    address_country = CountryField(
        verbose_name="Země",
    )

    ico_number = models.CharField(
        max_length=16,
        blank=True,
        null=True,
        verbose_name="IČO",
    )  # WARNING: Legal entity status dependent!

    date_of_birth = models.DateField(
        blank=True,
        null=True,
        verbose_name="Datum narození",
    )  # WARNING: Legal entity status dependent!

    representative_name = models.CharField(
        max_length=256,
        blank=True,
        null=True,
        verbose_name="Zástupce",
    )

    representative_role = models.CharField(
        max_length=256,
        blank=True,
        null=True,
        verbose_name="Funkce zástupce",
    )

    department = models.CharField(
        max_length=128,
        blank=True,
        null=True,
        verbose_name="Organizační složka",
    )

    class Meta:
        verbose_name = "Druhá smluvní strana"
        verbose_name_plural = "Druhé smluvní strany"


class ContractExternalSignature(models.Model):
    signer = models.ForeignKey(
        ContractExternalSigner,
        on_delete=models.CASCADE,
    )

    date = models.DateField(
        verbose_name="Datum podpisu",
    )


class ContractLocalSigner(models.Model):
    name = models.CharField(
        max_length=256,
        default=settings.DEFAULT_LOCAL_SIGNER_NAME,
        verbose_name="Jméno",
    )

    address_street_with_number = models.CharField(
        max_length=256,
        default=settings.DEFAULT_LCOAL_SIGNER_STREET,
        verbose_name="Ulice, č.p.",
    )

    address_district = models.CharField(
        max_length=256,
        default=settings.DEFAULT_LOCAL_SIGNER_DISTRICT,
        verbose_name="Obec",
    )

    address_zip = models.CharField(
        max_length=16,
        default=settings.DEFAULT_LOCAL_SIGNER_ZIP,
        verbose_name="PSČ",
    )

    address_country = CountryField(
        default=settings.DEFAULT_LOCAL_SIGNER_COUNTRY,
        verbose_name="Země",
    )

    ico_number = models.CharField(
        max_length=16,
        blank=True,
        null=True,
        default=settings.DEFAULT_LOCAL_SIGNER_ICO_NUMBER,
        verbose_name="IČO",
    )

    representative_name = models.CharField(
        max_length=256,
        blank=True,
        null=True,
        verbose_name="Zástupce",
    )

    representative_role = models.CharField(
        max_length=256,
        blank=True,
        null=True,
        verbose_name="Funkce zástupce",
    )

    department = models.CharField(
        max_length=128,
        blank=True,
        null=True,
        verbose_name="Organizační složka",
    )

    # TODO: Input validation
    color = models.CharField(
        max_length=6,  # e.g. "ffffff"
        verbose_name="Barva",
    )

    class Meta:
        verbose_name = "Naše smluvní strana"
        verbose_name_plural = "Naše smlouvní strany"


class ContractLocalSignature(models.Model):
    signer = models.ForeignKey(
        ContractLocalSigner,
        on_delete=models.CASCADE,
    )

    date = models.DateField(
        verbose_name="Datum podpisu",
    )


class ContractSubtype(models.Model):
    name = models.CharField(
        max_length=32,
        verbose_name="Jméno",
    )

    class Meta:
        verbose_name = "Podtyp smlouvy"
        verbose_name_plural = "Podtypy smlouvy"


class ContractIssue(models.Model):
    name = models.CharField(
        max_length=32,
        verbose_name="Jméno",
    )

    class Meta:
        verbose_name = "Problém se smlouvou"
        verbose_name_plural = "Problémy se smlouvou"


class ContractFilingArea(models.Model):
    name = models.CharField(
        max_length=32,
        verbose_name="Jméno",
    )

    person_responsible = models.CharField(
        max_length=256,
        verbose_name="Odpovědná osoba",
    )

    class Meta:
        verbose_name = "Spisovna"
        verbose_name_plural = "Spisovny"


class Contract(models.Model):
    class ContractTypes(models.TextChoices):
        PRIMARY = "primary", "Hlavní"
        AMENDMENT = "amendment", "Dodatek"
        FRAMEWORK_ORDER = "framework_order", "Objednávka u rámcové smlouvy"

    type = models.CharField(
        max_length=15,
        choices=ContractTypes.choices,
        default=ContractTypes.PRIMARY,
        verbose_name="Typ",
    )

    subtype = models.ForeignKey(
        ContractSubtype,
        on_delete=models.CASCADE,
        verbose_name="Podtyp",
    )

    contains_nda = models.BooleanField(
        default=False,
        verbose_name="Obsahuje NDA",
    )

    external_signature = models.ManyToManyField(ContractExternalSignature)

    local_signature = models.ManyToManyField(ContractLocalSignature)

    all_parties_sign_date = models.DateField(
        verbose_name="Datum podpisu všech stran",
    )  # WARNING: Exclude in admin, autofill

    valid_start_date = models.DateField(
        verbose_name="Začátek účinnosti",
    )
    valid_end_date = models.DateField(
        verbose_name="Konec platnosti",
    )

    uploaded_by = models.ForeignKey(
        User,
        on_delete=models.CASCADE,
        related_name="uploaded_contracts",
        verbose_name="Nahráno uživatelem",
        help_text="Informace není veřejně přístupná.",
    )  # WARNING: exclude in admin

    class LegalStates(models.TextChoices):
        VALID = "valid", "Platná"
        EFFECTIVE = "effective", "Účinná"
        NOT_EFFECTIVE = "not_effective", "Neúčinná"
        INVALID = "invalid", "Neplatná"

    class PublicStates(models.TextChoices):
        UNKNOWN = "unknown", "Nová"
        YES = "yes", "Zveřejněná"
        NO = "no", "Neveřejná"

    class PaperFormStates(models.TextChoices):
        SENT = "sent", "Odeslaná"
        STORED = "stored", "Uložená"
        TO_SHRED = "to_shred", "Ke skartaci"
        SHREDDED = "shredded", "Skartovaná"

    legal_state = models.CharField(
        max_length=13,
        choices=LegalStates.choices,
        verbose_name="Stav právního ujednání",
    )

    public_state = models.CharField(
        max_length=7,
        choices=PublicStates.choices,
        verbose_name="Veřejnost smlouvy",
    )

    paper_form_state = models.CharField(
        max_length=8,
        choices=PaperFormStates.choices,
        verbose_name="Stav papírové formy",
    )

    public_status_set_by = models.ForeignKey(
        User,
        on_delete=models.CASCADE,
        related_name="public_status_altered_contracts",
        verbose_name="Zveřejněno / nezveřejněno uživatelem",
        help_text="Obsah není veřejně přístupný.",
    )  # WARNING: exclude in admin

    publishing_rejection_comment = models.CharField(
        max_length=65536,
        blank=True,
        null=True,
        verbose_name="Důvod nezveřejnění",
        help_text="Obsah není veřejně přístupný.",
    )  # WARNING: exclude in admin

    tender_url = models.URLField(
        max_length=256,
        blank=True,
        null=True,
        verbose_name="Odkaz na výběrové řízení",
    )

    identifier = models.CharField(
        max_length=128,
        verbose_name="Identifikační číslo",
    )

    issues = models.ManyToManyField(ContractIssue)

    summary = models.CharField(
        max_length=65536,
        blank=True,
        null=True,
        verbose_name="Rekapitulace",
        help_text="Obsah není veřejně přístupný.",
    )

    anonymized_contract_file = models.FileField(
        verbose_name="Anonymizovaná smlouva (PDF)",
    )

    original_contract_file = models.FileField(
        verbose_name="Originální verze smlouvy (PDF)",
        help_text="Obsah není veřejně přístupný.",
    )

    primary_contract = models.ForeignKey(
        "Contract",
        on_delete=models.CASCADE,
        blank=True,
        null=True,
        verbose_name="Hlavní smlouva",
    )  # WARNING: Dependent on the type!

    expected_cost_total = models.IntegerField(verbose_name="Očekáváná celková cena")

    expected_cost_year = models.IntegerField(verbose_name="Očekáváná cena za rok")

    expected_cost_month = models.IntegerField(verbose_name="Očekáváná cena za měsíc")

    expected_cost_hour = models.IntegerField(verbose_name="Očekáváná cena za hodinu")

    intent_url = models.URLField(
        max_length=256,
        blank=True,
        null=True,
        verbose_name="Odkaz na záměr",
    )

    agreement_url = models.URLField(
        max_length=256,
        blank=True,
        null=True,
        verbose_name="Odkaz na schválení",
    )  # WARNING: Dependent on the type!

    filing_area = models.ForeignKey(
        ContractFilingArea,
        on_delete=models.CASCADE,
        blank=True,
        null=True,
        help_text="Obsah není veřejně přístupný.",
    )  # WARNING: Dependent on the type!

    class Meta:
        verbose_name = "Smlouva"
        verbose_name_plural = "Smlouvy"


class ContractNote(models.Model):
    contract = models.ForeignKey(
        Contract,
        on_delete=models.CASCADE,
    )

    author = models.ForeignKey(
        User,
        related_name="contract_notes",
        on_delete=models.CASCADE,
        verbose_name="Autor",
    )

    created_date = models.DateTimeField(
        verbose_name="Datum vytvoření",
    )

    content = MarkdownxField(
        verbose_name="Obsah",
    )

    class Meta:
        verbose_name = "Poznámka ke smlouvě"
        verbose_name_plural = "Poznámky ke smlouvě"