<?php

declare(strict_types=1);

namespace NoahVet\Reef\Jane\Normalizer;

use Jane\Component\JsonSchemaRuntime\Reference;
use NoahVet\Reef\Jane\Runtime\Normalizer\CheckArray;
use NoahVet\Reef\Jane\Runtime\Normalizer\ValidatorTrait;
use Symfony\Component\Serializer\Normalizer\DenormalizerAwareInterface;
use Symfony\Component\Serializer\Normalizer\DenormalizerAwareTrait;
use Symfony\Component\Serializer\Normalizer\DenormalizerInterface;
use Symfony\Component\Serializer\Normalizer\NormalizerAwareInterface;
use Symfony\Component\Serializer\Normalizer\NormalizerAwareTrait;
use Symfony\Component\Serializer\Normalizer\NormalizerInterface;

class SupplierOrderResponseNormalizer implements DenormalizerInterface, NormalizerInterface, DenormalizerAwareInterface, NormalizerAwareInterface
{
    use CheckArray;
    use DenormalizerAwareTrait;
    use NormalizerAwareTrait;
    use ValidatorTrait;

    public function supportsDenormalization(mixed $data, string $type, ?string $format = null, array $context = []): bool
    {
        return \NoahVet\Reef\Jane\Model\SupplierOrderResponse::class === $type;
    }

    public function supportsNormalization(mixed $data, ?string $format = null, array $context = []): bool
    {
        return \is_object($data) && \NoahVet\Reef\Jane\Model\SupplierOrderResponse::class === $data::class;
    }

    public function denormalize(mixed $data, string $type, ?string $format = null, array $context = []): mixed
    {
        if (isset($data['$ref'])) {
            return new Reference($data['$ref'], $context['document-origin']);
        }
        if (isset($data['$recursiveRef'])) {
            return new Reference($data['$recursiveRef'], $context['document-origin']);
        }
        $object = new \NoahVet\Reef\Jane\Model\SupplierOrderResponse();
        if (\array_key_exists('unitPrice', $data) && \is_int($data['unitPrice'])) {
            $data['unitPrice'] = (float) $data['unitPrice'];
        }
        if (\array_key_exists('rebatedUnitPrice', $data) && \is_int($data['rebatedUnitPrice'])) {
            $data['rebatedUnitPrice'] = (float) $data['rebatedUnitPrice'];
        }
        if (\array_key_exists('taxRate', $data) && \is_int($data['taxRate'])) {
            $data['taxRate'] = (float) $data['taxRate'];
        }
        if (\array_key_exists('rebatedTotalPrice', $data) && \is_int($data['rebatedTotalPrice'])) {
            $data['rebatedTotalPrice'] = (float) $data['rebatedTotalPrice'];
        }
        if (\array_key_exists('weight', $data) && \is_int($data['weight'])) {
            $data['weight'] = (float) $data['weight'];
        }
        if (\array_key_exists('netWeight', $data) && \is_int($data['netWeight'])) {
            $data['netWeight'] = (float) $data['netWeight'];
        }
        if (\array_key_exists('totalPrice', $data) && \is_int($data['totalPrice'])) {
            $data['totalPrice'] = (float) $data['totalPrice'];
        }
        if (\array_key_exists('rebatingRate', $data) && \is_int($data['rebatingRate'])) {
            $data['rebatingRate'] = (float) $data['rebatingRate'];
        }
        if (null === $data || false === \is_array($data)) {
            return $object;
        }
        if (\array_key_exists('id', $data)) {
            $object->setId($data['id']);
            unset($data['id']);
        }
        if (\array_key_exists('orderCode', $data) && null !== $data['orderCode']) {
            $object->setOrderCode($data['orderCode']);
            unset($data['orderCode']);
        } elseif (\array_key_exists('orderCode', $data) && null === $data['orderCode']) {
            $object->setOrderCode(null);
        }
        if (\array_key_exists('billedSupplierCode', $data) && null !== $data['billedSupplierCode']) {
            $object->setBilledSupplierCode($data['billedSupplierCode']);
            unset($data['billedSupplierCode']);
        } elseif (\array_key_exists('billedSupplierCode', $data) && null === $data['billedSupplierCode']) {
            $object->setBilledSupplierCode(null);
        }
        if (\array_key_exists('deliveredSupplierCode', $data) && null !== $data['deliveredSupplierCode']) {
            $object->setDeliveredSupplierCode($data['deliveredSupplierCode']);
            unset($data['deliveredSupplierCode']);
        } elseif (\array_key_exists('deliveredSupplierCode', $data) && null === $data['deliveredSupplierCode']) {
            $object->setDeliveredSupplierCode(null);
        }
        if (\array_key_exists('deliveredSupplierName', $data) && null !== $data['deliveredSupplierName']) {
            $object->setDeliveredSupplierName($data['deliveredSupplierName']);
            unset($data['deliveredSupplierName']);
        } elseif (\array_key_exists('deliveredSupplierName', $data) && null === $data['deliveredSupplierName']) {
            $object->setDeliveredSupplierName(null);
        }
        if (\array_key_exists('invoiceDate', $data) && null !== $data['invoiceDate']) {
            $object->setInvoiceDate(\DateTime::createFromFormat('Y-m-d', $data['invoiceDate'])->setTime(0, 0, 0));
            unset($data['invoiceDate']);
        } elseif (\array_key_exists('invoiceDate', $data) && null === $data['invoiceDate']) {
            $object->setInvoiceDate(null);
        }
        if (\array_key_exists('deliveryDate', $data) && null !== $data['deliveryDate']) {
            $object->setDeliveryDate(\DateTime::createFromFormat('Y-m-d', $data['deliveryDate'])->setTime(0, 0, 0));
            unset($data['deliveryDate']);
        } elseif (\array_key_exists('deliveryDate', $data) && null === $data['deliveryDate']) {
            $object->setDeliveryDate(null);
        }
        if (\array_key_exists('type', $data) && null !== $data['type']) {
            $object->setType($data['type']);
            unset($data['type']);
        } elseif (\array_key_exists('type', $data) && null === $data['type']) {
            $object->setType(null);
        }
        if (\array_key_exists('invoiceCode', $data) && null !== $data['invoiceCode']) {
            $object->setInvoiceCode($data['invoiceCode']);
            unset($data['invoiceCode']);
        } elseif (\array_key_exists('invoiceCode', $data) && null === $data['invoiceCode']) {
            $object->setInvoiceCode(null);
        }
        if (\array_key_exists('deliveryCode', $data) && null !== $data['deliveryCode']) {
            $object->setDeliveryCode($data['deliveryCode']);
            unset($data['deliveryCode']);
        } elseif (\array_key_exists('deliveryCode', $data) && null === $data['deliveryCode']) {
            $object->setDeliveryCode(null);
        }
        if (\array_key_exists('productCode', $data) && null !== $data['productCode']) {
            $object->setProductCode($data['productCode']);
            unset($data['productCode']);
        } elseif (\array_key_exists('productCode', $data) && null === $data['productCode']) {
            $object->setProductCode(null);
        }
        if (\array_key_exists('productName', $data) && null !== $data['productName']) {
            $object->setProductName($data['productName']);
            unset($data['productName']);
        } elseif (\array_key_exists('productName', $data) && null === $data['productName']) {
            $object->setProductName(null);
        }
        if (\array_key_exists('unitPrice', $data) && null !== $data['unitPrice']) {
            $object->setUnitPrice($data['unitPrice']);
            unset($data['unitPrice']);
        } elseif (\array_key_exists('unitPrice', $data) && null === $data['unitPrice']) {
            $object->setUnitPrice(null);
        }
        if (\array_key_exists('rebatedUnitPrice', $data) && null !== $data['rebatedUnitPrice']) {
            $object->setRebatedUnitPrice($data['rebatedUnitPrice']);
            unset($data['rebatedUnitPrice']);
        } elseif (\array_key_exists('rebatedUnitPrice', $data) && null === $data['rebatedUnitPrice']) {
            $object->setRebatedUnitPrice(null);
        }
        if (\array_key_exists('taxRate', $data) && null !== $data['taxRate']) {
            $object->setTaxRate($data['taxRate']);
            unset($data['taxRate']);
        } elseif (\array_key_exists('taxRate', $data) && null === $data['taxRate']) {
            $object->setTaxRate(null);
        }
        if (\array_key_exists('quantity', $data) && null !== $data['quantity']) {
            $object->setQuantity($data['quantity']);
            unset($data['quantity']);
        } elseif (\array_key_exists('quantity', $data) && null === $data['quantity']) {
            $object->setQuantity(null);
        }
        if (\array_key_exists('rebatedTotalPrice', $data) && null !== $data['rebatedTotalPrice']) {
            $object->setRebatedTotalPrice($data['rebatedTotalPrice']);
            unset($data['rebatedTotalPrice']);
        } elseif (\array_key_exists('rebatedTotalPrice', $data) && null === $data['rebatedTotalPrice']) {
            $object->setRebatedTotalPrice(null);
        }
        if (\array_key_exists('weight', $data) && null !== $data['weight']) {
            $object->setWeight($data['weight']);
            unset($data['weight']);
        } elseif (\array_key_exists('weight', $data) && null === $data['weight']) {
            $object->setWeight(null);
        }
        if (\array_key_exists('netWeight', $data) && null !== $data['netWeight']) {
            $object->setNetWeight($data['netWeight']);
            unset($data['netWeight']);
        } elseif (\array_key_exists('netWeight', $data) && null === $data['netWeight']) {
            $object->setNetWeight(null);
        }
        if (\array_key_exists('gtin', $data) && null !== $data['gtin']) {
            $object->setGtin($data['gtin']);
            unset($data['gtin']);
        } elseif (\array_key_exists('gtin', $data) && null === $data['gtin']) {
            $object->setGtin(null);
        }
        if (\array_key_exists('class', $data) && null !== $data['class']) {
            $object->setClass($data['class']);
            unset($data['class']);
        } elseif (\array_key_exists('class', $data) && null === $data['class']) {
            $object->setClass(null);
        }
        if (\array_key_exists('manufacturer', $data) && null !== $data['manufacturer']) {
            $object->setManufacturer($data['manufacturer']);
            unset($data['manufacturer']);
        } elseif (\array_key_exists('manufacturer', $data) && null === $data['manufacturer']) {
            $object->setManufacturer(null);
        }
        if (\array_key_exists('totalPrice', $data) && null !== $data['totalPrice']) {
            $object->setTotalPrice($data['totalPrice']);
            unset($data['totalPrice']);
        } elseif (\array_key_exists('totalPrice', $data) && null === $data['totalPrice']) {
            $object->setTotalPrice(null);
        }
        if (\array_key_exists('rebatingRate', $data) && null !== $data['rebatingRate']) {
            $object->setRebatingRate($data['rebatingRate']);
            unset($data['rebatingRate']);
        } elseif (\array_key_exists('rebatingRate', $data) && null === $data['rebatingRate']) {
            $object->setRebatingRate(null);
        }
        if (\array_key_exists('veterinaryEstablishmentId', $data)) {
            $object->setVeterinaryEstablishmentId($data['veterinaryEstablishmentId']);
            unset($data['veterinaryEstablishmentId']);
        }
        if (\array_key_exists('supplier', $data)) {
            $object->setSupplier($data['supplier']);
            unset($data['supplier']);
        }
        foreach ($data as $key => $value) {
            if (\preg_match('/.*/', (string) $key)) {
                $object[$key] = $value;
            }
        }

        return $object;
    }

    public function normalize(mixed $data, ?string $format = null, array $context = []): array|string|int|float|bool|\ArrayObject|null
    {
        $dataArray = [];
        $dataArray['id'] = $data->getId();
        $dataArray['orderCode'] = $data->getOrderCode();
        $dataArray['billedSupplierCode'] = $data->getBilledSupplierCode();
        $dataArray['deliveredSupplierCode'] = $data->getDeliveredSupplierCode();
        $dataArray['deliveredSupplierName'] = $data->getDeliveredSupplierName();
        $dataArray['invoiceDate'] = $data->getInvoiceDate()->format('Y-m-d');
        $dataArray['deliveryDate'] = $data->getDeliveryDate()->format('Y-m-d');
        $dataArray['type'] = $data->getType();
        $dataArray['invoiceCode'] = $data->getInvoiceCode();
        $dataArray['deliveryCode'] = $data->getDeliveryCode();
        $dataArray['productCode'] = $data->getProductCode();
        $dataArray['productName'] = $data->getProductName();
        $dataArray['unitPrice'] = $data->getUnitPrice();
        $dataArray['rebatedUnitPrice'] = $data->getRebatedUnitPrice();
        $dataArray['taxRate'] = $data->getTaxRate();
        $dataArray['quantity'] = $data->getQuantity();
        $dataArray['rebatedTotalPrice'] = $data->getRebatedTotalPrice();
        $dataArray['weight'] = $data->getWeight();
        $dataArray['netWeight'] = $data->getNetWeight();
        $dataArray['gtin'] = $data->getGtin();
        $dataArray['class'] = $data->getClass();
        $dataArray['manufacturer'] = $data->getManufacturer();
        $dataArray['totalPrice'] = $data->getTotalPrice();
        $dataArray['rebatingRate'] = $data->getRebatingRate();
        if ($data->isInitialized('veterinaryEstablishmentId') && null !== $data->getVeterinaryEstablishmentId()) {
            $dataArray['veterinaryEstablishmentId'] = $data->getVeterinaryEstablishmentId();
        }
        if ($data->isInitialized('supplier') && null !== $data->getSupplier()) {
            $dataArray['supplier'] = $data->getSupplier();
        }
        foreach ($data as $key => $value) {
            if (\preg_match('/.*/', (string) $key)) {
                $dataArray[$key] = $value;
            }
        }

        return $dataArray;
    }

    public function getSupportedTypes(?string $format = null): array
    {
        return [\NoahVet\Reef\Jane\Model\SupplierOrderResponse::class => false];
    }
}
