# devices/signals.py
from django.db import transaction
from django.db.models import OuterRef, Subquery
from django.db.models.signals import post_save
from django.dispatch import receiver
from scalemanagement.models import ScaleCropMapping
from .models import CustomerDevice, MyDeviceMoistureThreshold


@receiver(post_save, sender=CustomerDevice)
def create_thresholds_for_new_device(sender, instance, created, **kwargs):
    if not created:
        return

    # Fetch all mappings for this product (include threshold field!)
    mappings = ScaleCropMapping.objects.filter(
        scale=instance.scale
    ).values("id", "universal_moisture_threshold")

    if not mappings.exists():
        return

    with transaction.atomic():
        # Create threshold entries using the mapping threshold values
        to_create = [
            MyDeviceMoistureThreshold(
                device=instance,
                mapping_id=m["id"],
                moisture_threshold=m["universal_moisture_threshold"],
            )
            for m in mappings
        ]
        MyDeviceMoistureThreshold.objects.bulk_create(to_create, ignore_conflicts=True)

        # Backfill any that were skipped due to unique constraint
        subquery = ScaleCropMapping.objects.filter(
            pk=OuterRef("mapping_id")
        ).values("universal_moisture_threshold")[:1]

        MyDeviceMoistureThreshold.objects.filter(
            device=instance,
            moisture_threshold__isnull=True
        ).update(moisture_threshold=Subquery(subquery))


@receiver(post_save, sender=ScaleCropMapping)
def create_thresholds_for_new_mapping(sender, instance, created, **kwargs):
    if not created:
        return

    # Get all devices that belong to the same product
    devices = CustomerDevice.objects.filter(scale=instance.scale).values("id")

    if not devices.exists():
        return

    with transaction.atomic():
        to_create = [
            MyDeviceMoistureThreshold(
                device_id=d["id"],
                mapping=instance,
                moisture_threshold=instance.universal_moisture_threshold,
            )
            for d in devices
        ]
        MyDeviceMoistureThreshold.objects.bulk_create(to_create, ignore_conflicts=True)

        # Backfill moisture_thresholds where null
        subquery = ScaleCropMapping.objects.filter(
            pk=OuterRef("mapping_id")
        ).values("universal_moisture_threshold")[:1]

        MyDeviceMoistureThreshold.objects.filter(
            mapping=instance,
            moisture_threshold__isnull=True
        ).update(moisture_threshold=Subquery(subquery))
