<?php

declare(strict_types=1);

namespace External\PompoBundle\Overrides\GraphQL\Types\Extension;

use External\PompoBundle\Overrides\GraphQL\Types\User\PompoUserCard;
use External\PompoBundle\Overrides\GraphQL\Types\User\PompoUserChild;
use KupShop\GraphQLBundle\ApiAdmin\Types\User\User;
use KupShop\GraphQLBundle\ApiShared\ApiUtil;
use Query\Operator;
use TheCodingMachine\GraphQLite\Annotations\ExtendType;
use TheCodingMachine\GraphQLite\Annotations\Field;

#[ExtendType(class: User::class)]
class UserExtension
{
    #[Field(prefetchMethod: 'prefetchPompoId', description: 'POMPO číslo zákazníka.')]
    public function getPompoId(User $user, array $pompoIds): ?int
    {
        if ($pompoIds[$user->getId()] ?? false) {
            return (int) $pompoIds[$user->getId()];
        }

        return null;
    }

    /**
     * @return PompoUserCard[]
     */
    #[Field(prefetchMethod: 'prefetchPompoCards', description: 'POMPO zákaznické karty.')]
    public function getPompoCards(User $user, array $cards): array
    {
        return ApiUtil::wrapItems($cards[$user->getId()] ?? [], PompoUserCard::class);
    }

    /**
     * @return PompoUserChild[]
     */
    #[Field(prefetchMethod: 'prefetchPompoChildren', description: 'POMPO děti zákazníka.')]
    public function getPompoChildren(User $user, array $children): array
    {
        return ApiUtil::wrapItems($children[$user->getId()] ?? [], PompoUserChild::class);
    }

    public function prefetchPompoId(array $users): array
    {
        return $this->prefetchForUsers($users, function (array $ids) {
            $drsIdQb = sqlQueryBuilder()
                ->select('*')
                ->from('drs_users')
                ->where(Operator::inStringArray($ids, 'id_user'));

            $data = [];
            foreach ($drsIdQb->execute() as $item) {
                $data[$item['id_user']] = $item['id_drs'];
            }

            return $data;
        });
    }

    public function prefetchPompoCards(array $users): array
    {
        return $this->prefetchForUsers($users, function (array $ids) {
            $userCardsQb = sqlQueryBuilder()
                ->select('*')
                ->from('user_cards')
                ->where(Operator::inIntArray($ids, 'id_user'));

            $data = [];
            foreach ($userCardsQb->execute() as $item) {
                $data[$item['id_user']][] = $item;
            }

            return $data;
        });
    }

    public function prefetchPompoChildren(array $users): array
    {
        return $this->prefetchForUsers($users, function (array $ids) {
            $childrenQb = sqlQueryBuilder()
                ->select('*')
                ->from('users_family')
                ->where(Operator::inIntArray($ids, 'id_user'));

            $data = [];
            foreach ($childrenQb->execute() as $item) {
                $data[$item['id_user']][] = $item;
            }

            return $data;
        });
    }

    private function prefetchForUsers(array $users, callable $prefetch): array
    {
        $userIds = array_map(fn (User $x) => $x->getId(), $users);
        if (empty($userIds)) {
            return [];
        }

        return $prefetch($userIds);
    }
}
