from django.db import models


# Create your models here.


class TimeAt(models.Model):
    """
    Abstract base model to track creation and update timestamps.
    """
    createdAt = models.DateTimeField(auto_now_add=True)
    updatedAt = models.DateTimeField(auto_now=True)

    class Meta:
        abstract = True


class DeviceType(models.TextChoices):
    ANDROID = "Android"
    IOS = "IOS"
    OTHER = "Other"


class Device(TimeAt):
    deviceToken = models.CharField(max_length=256)
    deviceType = models.CharField(max_length=10, choices=DeviceType.choices)
    # Subscription details
    isSubscription = models.BooleanField(default=False)
    expireAt = models.DateTimeField(null=True, blank=True)
    lastPurchaseToken = models.CharField(max_length=256, null=True, blank=True)
    originalTransactionId = models.TextField(null=True, blank=True)
    appleTransactionId = models.TextField(null=True, blank=True)
    productId = models.CharField(max_length=256, null=True, blank=True)

    def __str__(self):
        return f'{self.pk} - {self.deviceToken}'


class Category(models.Model):
    description = models.TextField()
    image = models.ImageField(upload_to='category/')

    def __str__(self):
        return f'{self.pk}'


class Craptitude(models.Model):
    category = models.ForeignKey(Category, on_delete=models.CASCADE)
    roundNumber = models.PositiveIntegerField()
    diaperPrefix = models.CharField(max_length=256)
    dumpsterPrefix = models.CharField(max_length=256)

    class Meta:
        unique_together = ('category', 'roundNumber')

    def __str__(self):
        return f"{self.pk}"


class TeamName(models.TextChoices):
    DIAPER = "Diaper Team"
    DUMPSTER = "Dumpster Team"


class Team(models.Model):
    name = models.CharField(max_length=20, choices=TeamName.choices, unique=True)

    def __str__(self):
        return f"{self.pk} - {self.name}"


class GameSession(TimeAt):
    device = models.ForeignKey(Device, on_delete=models.CASCADE)
    category = models.ForeignKey(Category, on_delete=models.CASCADE)
    craptitude = models.ForeignKey(Craptitude, on_delete=models.CASCADE)

    def __str__(self):
        return f"{self.pk}"


class Player(TimeAt):
    session = models.ForeignKey(GameSession, on_delete=models.CASCADE)
    team = models.ForeignKey(Team, on_delete=models.CASCADE)
    name = models.CharField(max_length=256)

    def __str__(self):
        return f"{self.pk} ({self.name})"


class Sentence(TimeAt):
    session = models.ForeignKey(GameSession, on_delete=models.CASCADE)
    team = models.ForeignKey(Team, on_delete=models.CASCADE)
    player = models.ForeignKey(Player, on_delete=models.CASCADE)
    text = models.TextField()

    def __str__(self):
        return f"{self.pk}"


class RatingScore(models.IntegerChoices):
    BOWEL_MOVEMENT = 1
    URINAL_SPLASH = 2
    TINY_TOOT = 3
    TOILET_FLUSH = 4


class Rating(TimeAt):
    session = models.ForeignKey(GameSession, on_delete=models.CASCADE)
    sentence = models.ManyToManyField(Sentence)
    diaperScore = models.PositiveIntegerField()
    dumpsterScore = models.PositiveIntegerField()

    def __str__(self):
        return f"{self.pk}"


class CraptitudeHistory(TimeAt):
    session = models.ForeignKey(GameSession, on_delete=models.CASCADE)
    levelCompleted = models.IntegerField(default=0)

    def __str__(self):
        return f"{self.pk}"


class OptionChoice(models.TextChoices):
    PART_TWO = 1
    PART_ONE_AND_PART_TWO = 2
    CRAPTITUDE = 3
    CATEGORY = 4


class PlanType(models.IntegerChoices):
    FREE_ACCESS = 1
    BASIC_PREMIUM = 2
    FULL_ACCESS = 3


class PlanPeriod(models.TextChoices):
    FREE = "FREE"
    YEAR = "YEAR"


class Plan(TimeAt):
    name = models.CharField(max_length=99)
    price = models.DecimalField(max_digits=5, decimal_places=2, default=0)
    description = models.JSONField(default=list)
    unlockCategory = models.IntegerField(default=0)
    type = models.IntegerField(choices=PlanType.choices, default=PlanType.FREE_ACCESS)
    productId = models.CharField(max_length=100, unique=True)  # matches Play Store product ID
    period = models.CharField(max_length=256, choices=PlanPeriod.choices, null=True, blank=True)

    def __str__(self):
        return f"{self.pk}"


class AndroidTransaction(TimeAt):
    device = models.ForeignKey(Device, on_delete=models.CASCADE)
    productId = models.CharField(max_length=255)
    orderId = models.CharField(max_length=255)
    purchaseToken = models.CharField(max_length=255)
    notificationType = models.IntegerField()
    startAt = models.DateTimeField()
    expireAt = models.DateTimeField()

    def __str__(self):
        return f"{self.pk}"


class AppleTransaction(TimeAt):
    device = models.ForeignKey(Device, on_delete=models.CASCADE, null=True, blank=True)
    productId = models.CharField(max_length=255)
    appleTransactionId = models.CharField(max_length=255, null=True, blank=True)
    originalTransactionId = models.CharField(max_length=255)
    webOrderLineItemId = models.CharField(max_length=255, null=True, blank=True)
    appleReceipt = models.TextField(null=True, blank=True)
    startAt = models.DateTimeField()
    expireAt = models.DateTimeField()
    environment = models.CharField(max_length=50, null=True, blank=True)
    transactionReason = models.CharField(max_length=50, null=True, blank=True)
    notificationType = models.CharField(max_length=50, null=True, blank=True)

    def __str__(self):
        return f"{self.pk}"


class Transaction(TimeAt):
    device = models.ForeignKey(Device, on_delete=models.CASCADE)
    plan = models.ForeignKey(Plan, on_delete=models.CASCADE)
    productId = models.CharField(max_length=50)
    orderId = models.CharField(max_length=50)
    originalTransactionId = models.TextField()
    appleTransactionId = models.TextField()
    purchaseToken = models.TextField()
    amount = models.FloatField(default=0)
    startAt = models.DateTimeField()
    expireAt = models.DateTimeField(null=True)
    notificationType = models.CharField(max_length=50)

    def __str__(self):
        return f"{self.pk}"


class AppVersion(TimeAt):
    versionCode = models.CharField(max_length=50)
    deviceType = models.CharField(max_length=10, choices=DeviceType.choices)
    deletedAt = models.DateTimeField(null=True, blank=True)

    def __str__(self):
        return f"{self.pk}"
