<?php

/*
 * This file is part of the Serenity package.
 *
 * (c) CP Creation <web@cpcreation.fr>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Serenity\CoreBundle\Shared\Form\Trait;

use Symfony\Component\Form\FormError;
use Symfony\Component\Form\FormInterface;
use Symfony\Component\Validator\ConstraintViolationListInterface;

trait ValidationErrorMapperTrait
{
    /**
     * @param array<string, FormInterface> $forms
     */
    protected function mapViolationsToForms(array $forms, ConstraintViolationListInterface $violations): bool
    {
        if (0 === \count($violations)) {
            return false;
        }

        foreach ($violations as $violation) {
            $this->addViolationToForm($forms, $violation->getPropertyPath(), $violation->getMessage());
        }

        return true;
    }

    /**
     * @param array<string, FormInterface> $forms
     */
    private function addViolationToForm(array $forms, string $propertyPath, string $message): void
    {
        $pathParts = explode('.', $propertyPath);
        $rootProperty = $pathParts[0];
        $childProperty = $pathParts[1] ?? null;

        if (isset($forms[$rootProperty])) {
            if ($childProperty && $forms[$rootProperty]->has($childProperty)) {
                $forms[$rootProperty]->get($childProperty)->addError(new FormError($message));
            } else {
                $forms[$rootProperty]->addError(new FormError($message));
            }
        } elseif (isset($forms[$propertyPath])) {
            $forms[$propertyPath]->addError(new FormError($message));
        }
    }
}
