hp

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures\Flow;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Flow\Type\NavigatorFlowType;
use Symfony\Component\Form\Flow\Type\NextFlowType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\Opt

         'clear_submission' => true,
            'include_if' => ['professional'],
        ]);
    }

    public function configureOptions(OptionsResolver $resolver): void
    {
        $resolver->setDefaults([
            'with_reset' => true,
        ]);

ionsResolver\OptionsResolver;

class UserSignUpNavigatorType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options): void
    {
        $builder->add('skip', NextFlowType::class, [


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures\Flow;

use Symfony\Component\Form\Flow\AbstractFlowType;
use Symfony\Component\Form\Flow\DataStorage\InMemoryDataStorage;
use Symfony\Component\Form\Flow\FormFlowBuilderInterface;
use Symfony\Component\Form\Tests\Fixtures\Flow\Data\UserSignUp;
use Sym

ymfony\Component\OptionsResolver\OptionsResolver;

class UserSignUpType extends AbstractFlowType
{
    public function buildFormFlow(FormFlowBuilderInterface $builder, array $options): void
    {
        $skip = $options['data_class']
            ? static

fony\Component\Form\Tests\Fixtures\Flow\Step\UserSignUpAccountType;
use Symfony\Component\Form\Tests\Fixtures\Flow\Step\UserSignUpPersonalType;
use Symfony\Component\Form\Tests\Fixtures\Flow\Step\UserSignUpProfessionalType;
use S


n Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures\Flow\Step;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\EmailType;
use Symfony\Component\Form\Extension\Core\Type\PasswordType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;

class UserSignUpAcc

buildForm(FormBuilderInterface $builder, array $options): void
    {
        $builder->add('email', EmailType::class);
        $builder->add('password', PasswordType::class);
    }

    public function configureOptions(OptionsResolver $resolver): void

ountType extends AbstractType
{
    public function


?php

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures\Flow\Step;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\CheckboxType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\FormBuilderInterface;
use Sym

Type::class);
        $builder->add('lastName', TextType::class);
        $builder->add('worker', CheckboxType::class, ['required' => false]);
    }

    public function configureOptions(OptionsResolver $resolver): void
    {
        $resolver->setDefaults

fony\Component\OptionsResolver\OptionsResolver;

class UserSignUpPersonalType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options): void
    {
        $builder->add('firstName', Text


hp

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures\Flow\Step;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;

class UserSi

 'choices' => [
                'Product Manager' => 'ROLE_MANAGER',
                'Developer' => 'ROLE_DEVELOPER',
                'Designer' => 'ROLE_DESIGNER',
            ],
        ]);
    }

    public function configureOptions(OptionsResolver $res

gnUpProfessionalType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options): void
    {
        $builder->add('company');
        $builder->add('role', ChoiceType::class, [


/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures\Flow\Extension;

use Symfony\Component\Form\AbstractTypeExtension;
use Symfony\Component\Form\Extension\Core\Type\FormType;
use Symfony\Component\Form\Flow\FormFlowBuilderInterface;
use Symfony\Component\Form\FormBuilderInterface;
u

uilder instanceof FormFlowBuilderInterface) {
            throw new \InvalidArgumentException(\sprintf('The "%s" can only be used with FormFlowType.', self::class));
        }

        $builder->addStep('first', FormType::class, ['mapped' => false], null,

se Symfony\Component\Form\Tests\Fixtures\Flow\UserSignUpType;

class UserSignUpTypeExtension extends AbstractTypeExtension
{
    public function buildForm(FormBuilderInterface $builder, array $options): void
    {
        if (!$b


hp

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures\Flow\Data;

use Symfony\Component\Validator\Constraints as Assert;

final class UserSignUp
{
    // personal step
    #[Assert\NotBlank(groups: ['personal'])]
    #[Assert\Length(min: 3, groups: ['personal'])]
    public ?string

 ?string $company = null;
    public ?string $role = null;

    // account step
    #[Assert\NotBlank(groups: ['account'])]
    #[Assert\Email(groups: ['account'])]
    public ?string $email = null;
    #[Assert\NotBlank(groups: ['account'])]
    #[Assert\

$firstName = null;
    public ?string $lastName = null;
    public bool $worker = false;

    // professional step
    #[Assert\NotBlank(groups: ['professional'])]
    #[Assert\Length(min: 3, groups: ['professional'])]
    public


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Resources;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Translation\Util\XliffUtils;

class TranslationFilesTest extends TestCase
{
    #[DataProvider('provideTranslationFiles')]
    public function test

rrors, \sprintf('"%s" is invalid:%s', $filePath, \PHP_EOL.implode(\PHP_EOL, array_column($errors, 'message'))));
    }

    #[DataProvider('provideTranslationFiles')]
    public function testTranslationFileIsValidWithoutEntityLoader($filePath)
    {

TranslationFileIsValid($filePath)
    {
        $document = new \DOMDocument();
        $document->loadXML(file_get_contents($filePath));

        $errors = XliffUtils::validateSchema($document);

        $this->assertCount(0, $e


use Symfony\Component\Console\Exception\InvalidArgumentException;
use Symfony\Component\Console\Tester\CommandCompletionTester;
use Symfony\Component\Console\Tester\CommandTester;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Command\DebugCommand;
use Symfony\Component\Form\Extension\Core\CoreExtension;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\FormRegistry;
use Symfony\Component\Form\FormTypeInterface;
use Symfony\Component\Form\ResolvedFormTy

eateCommandTester();
        $ret = $tester->execute([], ['decorated' => false]);

        $this->assertEquals(0, $ret, 'Returns 0 in case of success');
        $this->assertStringContainsString('Built-in form types', $tester->getDisplay());
    }

    pub

peFactory;
use Symfony\Component\OptionsResolver\Options;
use Symfony\Component\OptionsResolver\OptionsResolver;

class DebugCommandTest extends TestCase
{
    public function testDebugDefaults()
    {
        $tester = $this->cr


ony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Guess;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\Guess\Guess;

class TestGuess extends Guess
{
}

class GuessTest extends TestCase
{
    public function testGetBestGuessReturnsGuessWithHighestConfidence()
    {
        $guess1 = new TestGuess(Guess::MEDIUM_CONFIDENCE);
        $guess2 = new TestGuess(Guess::LO

::HIGH_CONFIDENCE);

        $this->assertSame($guess3, Guess::getBestGuess([$guess1, $guess2, $guess3]));
    }

    public function testGuessExpectsValidConfidence()
    {
        $this->expectException(\InvalidArgumentException::class);
        new Test

W_CONFIDENCE);
        $guess3 = new TestGuess(Guess


yInjection\Argument\IteratorArgument;
use Symfony\Component\DependencyInjection\Argument\ServiceClosureArgument;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Definition;
use Symfony\Component\DependencyInjection\Reference;
use Symfony\Component\DependencyInjection\ServiceLocator;
use Symfony\Component\Form\AbstractTypeExtension;
use Symfony\Component\Form\Command\DebugCommand;
use Symfony\Component\Form\DependencyInjection\FormPass;
use Symfony\Compon

mExtensionNotLoaded()
    {
        $container = $this->createContainerBuilder();

        $container->compile();

        $this->assertFalse($container->hasDefinition('form.extension'));
    }

    public function testDoNothingIfDebugCommandNotLoaded()

ent\Form\Extension\Csrf\Type\FormTypeCsrfExtension;
use Symfony\Component\Form\FormRegistry;

/**
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class FormPassTest extends TestCase
{
    public function testDoNothingIfFor


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Guess;

use Symfony\Component\Form\Exception\InvalidArgumentException;

/**
 * Base class for guesses made by FormTypeGuesserInterface implementation.
 *
 * Each instance contains a confidence value about the correctness of the guess.
 * Thus an instance with confidence HIGH_CONFIDENCE is mo

o be correct.
     */
    public const VERY_HIGH_CONFIDENCE = 3;

    /**
     * Marks an instance with a value that is very likely to be correct.
     */
    public const HIGH_CONFIDENCE = 2;

    /**
     * Marks an instance with a value that is likely t

re likely to be
 * correct than an instance with confidence LOW_CONFIDENCE.
 *
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
abstract class Guess
{
    /**
     * Marks an instance with a value that is extremely likely t


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Guess;

/**
 * Contains a guessed class name and a list of options for creating an instance
 * of that class.
 *
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class TypeGuess extends Guess
{
    /**
     * @param string $type       The guessed

             is correct
     */
    public function __construct(
        private string $type,
        private array $options,
        int $confidence,
    ) {
        parent::__construct($confidence);
    }

    /**
     * Returns the guessed field type.

field type
     * @param array  $options    The options for creating instances of the
     *                           guessed class
     * @param int    $confidence The confidence that the guessed class name
     *


s part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Guess;

/**
 * Contains a guessed value.
 *
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class ValueGuess extends Guess
{
    /**
     * @param int $confidence The confidence that the guessed class name is correct
     */
    public function __construct(

e string|int|bool|null $value,
        int $confidence,
    ) {
        parent::__construct($confidence);
    }

    /**
     * Returns the guessed value.
     */
    public function getValue(): string|int|bool|null
    {
        return $this->value;
    }


p

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Event;

use Symfony\Component\Form\Exception\BadMethodCallException;
use Symfony\Component\Form\FormEvent;

/**
 * This event is dispatched at the end of the Form::setData() method.
 *
 * It can be used to modify a form depending on the populate

*/
final class PostSetDataEvent extends FormEvent
{
    public function setData(mixed $data): never
    {
        throw new BadMethodCallException('Form data cannot be changed during "form.post_set_data", you should use "form.pre_set_data" instead.');

d data (adding or
 * removing fields dynamically).


php

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Event;

use Symfony\Component\Form\Exception\BadMethodCallException;
use Symfony\Component\Form\FormEvent;

/**
 * This event is dispatched after the Form::submit()
 * once the model and view data have been denormalized.
 *
 * It can be used t

PostSubmitEvent extends FormEvent
{
    public function setData(mixed $data): never
    {
        throw new BadMethodCallException('Form data cannot be changed during "form.post_submit", you should use "form.pre_submit" or "form.submit" instead.');
    }
}

o fetch data after denormalization.
 */
final class


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Test;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\FormExtensionInterface;
use Symfony\Component\Form\FormFactoryInterface;
use Symfony\Component\Form\Forms;
use Symfony\Component\Form\FormTypeExtensionInterface;
use Symfony\Component\Form\FormTypeGue

protected function setUp(): void
    {
        $this->factory = Forms::createFormFactoryBuilder()
            ->addExtensions($this->getExtensions())
            ->addTypeExtensions($this->getTypeExtensions())
            ->addTypes($this->getTypes())

sserInterface;
use Symfony\Component\Form\FormTypeInterface;

/**
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
abstract class FormIntegrationTestCase extends TestCase
{
    protected FormFactoryInterface $factory;


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Test;

/**
 * Base class for performance tests.
 *
 * Copied from Doctrine 2's OrmPerformanceTestCase.
 *
 * @author robo
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
abstract class FormPerformanceTestCase extends FormIntegrationTestCase
{

s(): void
    {
        parent::assertPostConditions();

        $time = microtime(true) - $this->startTime;

        if (0 != $this->maxRunningTime && $time > $this->maxRunningTime) {
            $this->fail(\sprintf('expected running time: <= %s but was:

 private float $startTime;
    protected int $maxRunningTime = 0;

    protected function setUp(): void
    {
        parent::setUp();

        $this->startTime = microtime(true);
    }

    protected function assertPostCondition


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Test;

use Symfony\Component\EventDispatcher\EventDispatcherInterface;
use Symfony\Component\Form\Extension\Validator\ViolationMapper\ViolationMapperInterface;
use Symfony\Component\Form\FormBuilder;
use Symfony\Component\Form\FormExtensionInterface;
use Symfony\Com

(): void
    {
        parent::setUp();

        if (!isset($this->dispatcher)) {
            $this->dispatcher = $this->createMock(EventDispatcherInterface::class);
        }
        $this->builder = new FormBuilder('', null, $this->dispatcher, $this->fac

ponent\Form\Test\Traits\ValidatorExtensionTrait;

abstract class TypeTestCase extends FormIntegrationTestCase
{
    protected FormBuilder $builder;
    protected EventDispatcherInterface $dispatcher;

    protected function setUp


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Test\Traits;

use Symfony\Component\Form\Extension\Validator\ValidatorExtension;
use Symfony\Component\Form\Extension\Validator\ViolationMapper\ViolationMapperInterface;
use Symfony\Component\Form\Test\TypeTestCase;
use Symfony\Component\Validator\ConstraintViolatio

ationMapperInterface|null $violationMapper
     */
    protected function getValidatorExtension(/* ?ViolationMapperInterface $violationMapper = null */): ValidatorExtension
    {
        $violationMapper = \func_num_args() ? func_get_arg(0) : null;

nList;
use Symfony\Component\Validator\Mapping\ClassMetadata;
use Symfony\Component\Validator\Validator\ValidatorInterface;

trait ValidatorExtensionTrait
{
    protected ValidatorInterface $validator;

    /**
     * @param Viol


buted with this source code.
 */

namespace Symfony\Component\Form\DependencyInjection;

use Symfony\Component\DependencyInjection\Argument\ArgumentInterface;
use Symfony\Component\DependencyInjection\Argument\IteratorArgument;
use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface;
use Symfony\Component\DependencyInjection\Compiler\PriorityTaggedServiceTrait;
use Symfony\Component\DependencyInjection\Compiler\ServiceLocatorTagPass;
use Symfony\Component\DependencyInjection\ContainerBuilde

esser" as arguments of the "form.extension" service.
 *
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class FormPass implements CompilerPassInterface
{
    use PriorityTaggedServiceTrait;

    public function process(ContainerBuilder $container):

r;
use Symfony\Component\DependencyInjection\Exception\InvalidArgumentException;
use Symfony\Component\DependencyInjection\Reference;

/**
 * Adds all services with the tags "form.type", "form.type_extension" and
 * "form.type_gu


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\ChoiceList\LazyChoiceList;
use Symfony\Component\Form\Tests\Fixtures\ArrayChoiceLoader;

/**
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class LazyChoiceListTest extends TestCase
{
    public function testGetChoiceLoadersLoadsLoadedListOnFirstCall()

choice, $choices);
        });

        $this->assertSame(['RESULT'], $list->getChoices());
        $this->assertSame(['RESULT'], $list->getChoices());
        $this->assertSame(2, $calls);
    }

    public function testGetValuesLoadsLoadedListOnFirstCall

{
        $choices = ['RESULT'];
        $calls = 0;
        $list = new LazyChoiceList(new ArrayChoiceLoader($choices), static function ($choice) use ($choices, &$calls) {
            ++$calls;

            return array_search($


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList\Loader;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\ChoiceList\ChoiceListInterface;
use Symfony\Component\Form\ChoiceList\LazyChoiceList;
use Symfony\Component\Form\ChoiceList\Loader\CallbackChoiceLoader;

/**
 * @author Jules Pietri <jules@heahprod.com>
 */

oice_two'];
    private static LazyChoiceList $lazyChoiceList;

    public static function setUpBeforeClass(): void
    {
        self::$loader = new CallbackChoiceLoader(static fn () => self::$choices);
        self::$value = static fn ($choice) => $choic

class CallbackChoiceLoaderTest extends TestCase
{
    private static CallbackChoiceLoader $loader;
    private static \Closure $value;
    private static array $choices;
    private static array $choiceValues = ['choice_one', 'ch


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList\Loader;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\ChoiceList\ChoiceListInterface;
use Symfony\Component\Form\ChoiceList\LazyChoiceList;
use Symfony\Component\Form\ChoiceList\Loader\IntlCallbackChoiceLoader;

/**
 * @author Jules Pietri <jules@heahprod.com>

    private static array $choiceValues = ['choice_one', 'choice_two'];
    private static LazyChoiceList $lazyChoiceList;

    public static function setUpBeforeClass(): void
    {
        self::$loader = new IntlCallbackChoiceLoader(static fn () => self:

 * @author Yonel Ceruto <yonelceruto@gmail.com>
 */
class IntlCallbackChoiceLoaderTest extends TestCase
{
    private static IntlCallbackChoiceLoader $loader;
    private static \Closure $value;
    private static array $choices;


se Symfony\Component\Form\Tests\ChoiceList\ChoiceListAssertionTrait;
use Symfony\Component\Form\Tests\Fixtures\ArrayChoiceLoader;
use Symfony\Component\Translation\TranslatableMessage;
use Symfony\Contracts\Translation\TranslatableInterface;
use Symfony\Contracts\Translation\TranslatorInterface;

class DefaultChoiceListFactoryTest extends TestCase
{
    use ChoiceListAssertionTrait;

    private \stdClass $obj1;
    private \stdClass $obj2;
    private \stdClass $obj3;
    private \stdClass $obj4;
    priva

) {
            case 'a': return 'a';
            case 'b': return 'b';
            case 'c': return '1';
            case 'd': return '2';
        }
    }

    public function getLabel($object)
    {
        return $object->label;
    }

    public functi

te ArrayChoiceList $list;
    private DefaultChoiceListFactory $factory;

    public function getValue($object)
    {
        return $object->value;
    }

    public function getScalarValue($choice)
    {
        switch ($choice


rm\ChoiceList\Factory\DefaultChoiceListFactory;
use Symfony\Component\Form\ChoiceList\Factory\PropertyAccessDecorator;
use Symfony\Component\Form\ChoiceList\View\ChoiceGroupView;
use Symfony\Component\Form\ChoiceList\View\ChoiceView;
use Symfony\Component\Form\Tests\Fixtures\ArrayChoiceLoader;
use Symfony\Component\PropertyAccess\PropertyPath;

/**
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class PropertyAccessDecoratorTest extends TestCase
{
    private PropertyAccessDecorator $factory;

    pr

' => 'value'];

        $this->assertSame(['value' => $object], $this->factory->createListFromChoices([$object], 'property')->getChoices());
    }

    public function testCreateFromChoicesPropertyPathInstance()
    {
        $object = (object) ['property'

otected function setUp(): void
    {
        $this->factory = new PropertyAccessDecorator(new DefaultChoiceListFactory());
    }

    public function testCreateFromChoicesPropertyPath()
    {
        $object = (object) ['property


n Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\Form\FormEvent;
use Symfony\Component\Form\FormEvents;

class AlternatingRowType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options):

ents::PRE_SET_DATA, function (FormEvent $event) {
            $form = $event->getForm();
            $type = 0 === $form->getName() % 2
                ? 'Symfony\Component\Form\Extension\Core\Type\TextType'
                : 'Symfony\Component\Form\Extens

void
    {
        $builder->addEventListener(FormEv


 file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;

class AuthorType extends AbstractType
{
    public function buildForm(FormBuilderInterface $bui

           ->add('firstName')
            ->add('lastName')
        ;
    }

    public function configureOptions(OptionsResolver $resolver): void
    {
        $resolver->setDefaults([
            'data_class' => 'Symfony\Component\Form\Tests\Fixtures\Aut

lder, array $options): void
    {
        $builder


/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\CollectionType;
use Symfony\Component\Form\Extension\Core\Type\TextareaType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symf

builder, array $options): void
    {
        $builder->addEventListener(FormEvents::PRE_SET_DATA, static function (FormEvent $event): void {
            $event->getForm()
                ->add('0', TextareaType::class)
                ->add('foo', TextType

ony\Component\Form\FormBuilderInterface;
use Symfony\Component\Form\FormEvent;
use Symfony\Component\Form\FormEvents;

class CollectionWithPreSetDataType extends AbstractType
{
    public function buildForm(FormBuilderInterface $


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\CollectionType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\Form

ntListener(FormEvents::PRE_SET_DATA, static function (FormEvent $event): void {
            $event->getForm()->add('foo', TextType::class);
        });

        $builder->addEventListener(FormEvents::POST_SET_DATA, static function (FormEvent $event): void

\FormEvent;
use Symfony\Component\Form\FormEvents;

class CollectionWithRecursiveSetDataType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options): void
    {
        $builder->addEve


     \Locale::setDefault('en');
        parent::setUp();
    }

    protected function tearDown(): void
    {
        \Locale::setDefault($this->defaultLocale);
    }

    public function testSubmitDateTime()
    {
        $form = $this->factory->create(static::TESTED_TYPE, null, [
            'model_timezone' => 'UTC',
            'view_timezone' => 'UTC',
            'date_widget' => 'choice',
            'years' => [2010],
            'time_widget' => 'choice',
            'input' => 'datetime',

      'minute' => '4',
            ],
        ]);

        $dateTime = new \DateTime('2010-06-02 03:04:00 UTC');

        $this->assertEquals($dateTime, $form->getData());
    }

    public function testSubmitDatePoint()
    {
        $form = $this->factor


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Extension\Core\Type;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Form\Extension\Core\Type\ColorType;
use Symfony\Component\Form\FormError;
use Symfony\Component\Form\FormErrorIterator;

final class ColorTypeTest extends BaseTypeTestCase
{
    public const TEST

 null, [
            'html5' => $html5,
            'trim' => true,
        ]);

        $form->submit($submittedValue);

        $this->assertInstanceOf(FormErrorIterator::class, $form->getErrors());
        $this->assertCount(0, $form->getErrors());

ED_TYPE = ColorType::class;

    #[DataProvider('validationShouldPassProvider')]
    public function testValidationShouldPass(bool $html5, ?string $submittedValue)
    {
        $form = $this->factory->create(static::TESTED_TYPE,


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Extension\Core\DataTransformer;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\Exception\TransformationFailedException;
use Symfony\Component\Form\Extension\Core\DataTransformer\WeekToArrayTransformer;

class WeekToArrayTransformerTest extends TestCase
{
    public function te

  $transformer = new WeekToArrayTransformer();

        $this->assertSame(['year' => null, 'week' => null], $transformer->transform(null));
    }

    #[DataProvider('transformationFailuresProvider')]
    public function testTransformationFailures($input,

stTransform()
    {
        $transformer = new WeekToArrayTransformer();

        $this->assertSame(['year' => 2019, 'week' => 1], $transformer->transform('2019-W01'));
    }

    public function testTransformEmpty()
    {


ntDispatcher\EventDispatcher;
use Symfony\Component\Form\Extension\Core\DataAccessor\PropertyPathAccessor;
use Symfony\Component\Form\Extension\Core\DataMapper\DataMapper;
use Symfony\Component\Form\Extension\Core\Type\DateType;
use Symfony\Component\Form\Extension\Core\Type\FormType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\Form;
use Symfony\Component\Form\FormConfigBuilder;
use Symfony\Component\Form\FormFactoryBuilder;
use Symfony\Component\Form\Tests\Fixtures\T

$dispatcher;

    protected function setUp(): void
    {
        $this->mapper = new DataMapper();
        $this->dispatcher = new EventDispatcher();
    }

    public function testMapDataToFormsPassesObjectRefIfByReference()
    {
        $car = new \stdC

ypehintedPropertiesCar;
use Symfony\Component\PropertyAccess\PropertyAccess;
use Symfony\Component\PropertyAccess\PropertyPath;

class DataMapperTest extends TestCase
{
    private DataMapper $mapper;
    private EventDispatcher


gmail.com>
 */
class OrderedHashMapTest extends TestCase
{
    public function testGet()
    {
        $map = new OrderedHashMap();
        $map['first'] = 1;

        $this->assertSame(1, $map['first']);
    }

    public function testGetNonExistingFails()
    {
        $this->expectException(\OutOfBoundsException::class);
        $map = new OrderedHashMap();

        $map['first'];
    }

    public function testInsertStringKeys()
    {
        $map = new OrderedHashMap();
        $map['first'] = 1;

p['foo'] = 2;
        $map[] = 3;

        $this->assertSame(['0' => 1, 'foo' => 2, '1' => 3], iterator_to_array($map));
    }

    public function testInsertLooselyEqualKeys()
    {
        $map = new OrderedHashMap();
        $map['1 as a string'] = '1 a

   $map['second'] = 2;

        $this->assertSame(['first' => 1, 'second' => 2], iterator_to_array($map));
    }

    public function testInsertNullKeys()
    {
        $map = new OrderedHashMap();
        $map[] = 1;
        $ma


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Util;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\Util\StringUtil;

class StringUtilTest extends TestCase
{
    public static function trimProvider(): array
    {
        return [
            [' Foo! ', 'Foo!'],
            ["\u{1F92E}", "\u{1F92E}"], // unassigned characte

vider('spaceProvider')]
    public function testTrimUtf8Separators($hex)
    {
        // Convert hexadecimal representation into binary
        // H: hex string, high nibble first (UCS-2BE)
        // *: repeat until end of string
        $binary = pack('

r in PCRE versions of <PHP 7.3
        ];
    }

    #[DataProvider('trimProvider')]
    public function testTrim($data, $expectedData)
    {
        $this->assertSame($expectedData, StringUtil::trim($data));
    }

    #[DataPro


buted with this source code.
 */

namespace Symfony\Component\Form\Tests\Console\Descriptor;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Console\Input\ArrayInput;
use Symfony\Component\Console\Output\BufferedOutput;
use Symfony\Component\Console\Style\SymfonyStyle;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\Form\Extension\Core\Type\FormType;
use Symfony\Component\Form\Exte

e Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\Security\Csrf\CsrfTokenManager;

abstract class AbstractDescriptorTestCase extends TestCase
{
    private string|false $colSize;

    protected function setUp(): void
    {

nsion\Csrf\Type\FormTypeCsrfExtension;
use Symfony\Component\Form\FormInterface;
use Symfony\Component\Form\ResolvedFormType;
use Symfony\Component\Form\ResolvedFormTypeInterface;
use Symfony\Component\OptionsResolver\Options;
us


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList\Loader;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\ChoiceList\ArrayChoiceList;
use Symfony\Component\Form\ChoiceList\Loader\FilterChoiceLoaderDecorator;
use Symfony\Component\Form\Tests\ChoiceList\ChoiceListAssertionTrait;
use Symfony\Component\Form\Tests\Fi

      $loader = new FilterChoiceLoaderDecorator(new ArrayChoiceLoader(range(1, 4)), $filter);

        $this->assertEqualsArrayChoiceList(new ArrayChoiceList([1 => 2, 3 => 4]), $loader->loadChoiceList());
    }

    public function testLoadChoiceListWithGr

xtures\ArrayChoiceLoader;

class FilterChoiceLoaderDecoratorTest extends TestCase
{
    use ChoiceListAssertionTrait;

    public function testLoadChoiceList()
    {
        $filter = static fn ($choice) => 0 === $choice % 2;


use Symfony\Component\Form\ChoiceList\View\ChoiceListView;
use Symfony\Component\Form\Extension\Core\Type\FormType;
use Symfony\Component\Form\Tests\ChoiceList\ChoiceListAssertionTrait;
use Symfony\Component\Form\Tests\Fixtures\ArrayChoiceLoader;

/**
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class CachingFactoryDecoratorTest extends TestCase
{
    use ChoiceListAssertionTrait;

    private CachingFactoryDecorator $factory;

    protected function setUp(): void
    {
        $this->factory = n

Choices([]);

        $this->assertSame($list1, $list2);
        self::assertEqualsArrayChoiceList(new ArrayChoiceList([]), $list1);
        self::assertEqualsArrayChoiceList(new ArrayChoiceList([]), $list2);
    }

    public function testCreateFromChoice

ew CachingFactoryDecorator(new DefaultChoiceListFactory());
    }

    public function testCreateFromChoicesEmpty()
    {
        $list1 = $this->factory->createListFromChoices([]);
        $list2 = $this->factory->createListFrom


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures;

class Author
{
    public $firstName;
    private $lastName;
    private $australian;
    public $child;
    private $readPermissions;

    private $privateProperty;

    public function __construct($firstName = null, $lastName = null)

 return $this->lastName;
    }

    private function getPrivateGetter()
    {
        return 'foobar';
    }

    public function setAustralian($australian)
    {
        $this->australian = $australian;
    }

    public function isAustralian()
    {

    {
        $this->firstName = $firstName;
        $this->lastName = $lastName;
    }

    public function setLastName($lastName)
    {
        $this->lastName = $lastName;
    }

    public function getLastName()
    {


ony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures;

use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\OptionsResolver\OptionsResolver;

/**
 * @author Paráda József <joczy.parada@gmail.com>
 */
class ChoiceSubType extends AbstractType
{
    public function configureOptions(OptionsResolver $resolve

nded' => true]);
        $resolver->setNormalizer('choices', fn () => [
            'attr1' => 'Attribute 1',
            'attr2' => 'Attribute 2',
        ]);
    }

    public function getParent(): ?string
    {
        return ChoiceType::class;
    }
}

r): void
    {
        $resolver->setDefaults(['expa


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Fixtures;

/**
 * This class is a hand written simplified version of PHP native `ArrayObject`
 * class, to show that it behaves differently than the PHP native implementation.
 */
class CustomArrayObject implements \ArrayAccess, \IteratorAggregate, \Countable

$this->array);
    }

    public function offsetGet($offset): mixed
    {
        return $this->array[$offset];
    }

    public function offsetSet($offset, $value): void
    {
        if (null === $offset) {
            $this->array[] = $value;
        }

{
    private array $array;

    public function __construct(?array $array = null)
    {
        $this->array = $array ?: [];
    }

    public function offsetExists($offset): bool
    {
        return \array_key_exists($offset,


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Extension\Core\DataTransformer;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\Exception\TransformationFailedException;
use Symfony\Component\Form\Extension\Core\DataTransformer\ValueToDuplicatesTransformer;

class ValueToDuplicatesTransformerTest extends TestCase
{
    private ValueToDuplicatesTransformer $transformer;

'b' => 'Foo',
            'c' => 'Foo',
        ];

        $this->assertSame($output, $this->transformer->transform('Foo'));
    }

    public function testTransformEmpty()
    {
        $output = [
            'a' => null,
            'b' => null,

   protected function setUp(): void
    {
        $this->transformer = new ValueToDuplicatesTransformer(['a', 'b', 'c']);
    }

    public function testTransform()
    {
        $output = [
            'a' => 'Foo',


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Extension\HtmlSanitizer\Type;

use Symfony\Component\DependencyInjection\ServiceLocator;
use Symfony\Component\EventDispatcher\EventDispatcher;
use Symfony\Component\Form\Extension\Core\Type\FormType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\E

erInterface;

class TextTypeHtmlSanitizerExtensionTest extends TypeTestCase
{
    protected function setUp(): void
    {
        $this->dispatcher = new EventDispatcher();

        parent::setUp();
    }

    protected function getExtensions(?ViolationMapp

xtension\HtmlSanitizer\HtmlSanitizerExtension;
use Symfony\Component\Form\Extension\Validator\ViolationMapper\ViolationMapperInterface;
use Symfony\Component\Form\Test\TypeTestCase;
use Symfony\Component\HtmlSanitizer\HtmlSanitiz


buted with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList;

use Symfony\Component\Form\ChoiceList\ArrayChoiceList;
use Symfony\Component\Form\ChoiceList\ChoiceListInterface;

/**
 * @author Bernhard Schussek <bschussek@gmail.com>
 */
class ArrayChoiceListTest extends AbstractChoiceListTestCase
{
    private \stdClass $object;

    protected function setUp(): void
    {
        $this->object = new \stdClass();

        parent::setUp();
    }

    protected function createChoiceList(

unction getValues()
    {
        return ['0', '1', '2', '3', '4', '5', '6', '7', '8'];
    }

    public function testCreateChoiceListWithValueCallback()
    {
        $callback = static fn ($choice) => ':'.$choice;

        $choiceList = new ArrayChoiceL

): ChoiceListInterface
    {
        return new ArrayChoiceList($this->getChoices());
    }

    protected function getChoices()
    {
        return [0, 1, 1.5, '1', 'a', false, true, $this->object, null];
    }

    protected f


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList;

use Symfony\Component\Form\ChoiceList\ArrayChoiceList;
use Symfony\Component\Form\ChoiceList\LazyChoiceList;

trait ChoiceListAssertionTrait
{
    private function assertEqualsArrayChoiceList(ArrayChoiceList $expected, $actual)
    {

lues());
        $this->assertEquals($expected->getOriginalKeys(), $actual->getOriginalKeys());
    }

    private function assertEqualsLazyChoiceList(LazyChoiceList $expected, $actual)
    {
        $this->assertInstanceOf(LazyChoiceList::class, $actual);

        $this->assertInstanceOf(ArrayChoiceList::class, $actual);
        $this->assertEquals($expected->getChoices(), $actual->getChoices());
        $this->assertEquals($expected->getStructuredValues(), $actual->getStructuredVa


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList\Factory\Cache;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\ChoiceList\ArrayChoiceList;
use Symfony\Component\Form\ChoiceList\Factory\Cache\ChoiceLoader;
use Symfony\Component\Form\ChoiceList\Loader\CallbackChoiceLoader;
use Symfony\C

iceListAssertionTrait;

    public function testSameFormTypeUseCachedLoader()
    {
        $choices = ['f' => 'foo', 'b' => 'bar', 'z' => 'baz'];
        $choiceList = new ArrayChoiceList($choices);

        $type = new FormType();
        $decorated = ne

omponent\Form\Extension\Core\Type\FormType;
use Symfony\Component\Form\Tests\ChoiceList\ChoiceListAssertionTrait;
use Symfony\Component\Form\Tests\Fixtures\ArrayChoiceLoader;

class ChoiceLoaderTest extends TestCase
{
    use Cho


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Extension\Core\Type;

use Symfony\Component\EventDispatcher\EventDispatcher;
use Symfony\Component\Form\Extension\Core\Type\PercentType;
use Symfony\Component\Form\Test\TypeTestCase;
use Symfony\Component\Intl\Util\IntlTestHelper;

class PercentTypeTest extends TypeTestCase
{
    publi

d the full
        // implementation
        IntlTestHelper::requireFullIntl($this);

        parent::setUp();

        $this->defaultLocale = \Locale::getDefault();
    }

    protected function tearDown(): void
    {
        if (isset($this->defaultLocal

c const TESTED_TYPE = PercentType::class;

    private string $defaultLocale;

    protected function setUp(): void
    {
        $this->dispatcher = new EventDispatcher();

        // we test against different locales, so we nee


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Extension\DependencyInjection;

use PHPUnit\Framework\TestCase;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\Form\AbstractTypeExtension;
use Symfony\Component\Form\Exception\InvalidArgumentException;
use Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension;
use Symfony\C

tTypeExtension();
        $typeExtension3 = new OtherTypeExtension();
        $typeExtension4 = new MultipleTypesTypeExtension();

        $extensions = [
            'test' => new \ArrayIterator([$typeExtension1, $typeExtension2, $typeExtension4]),

omponent\Form\FormTypeGuesserChain;

class DependencyInjectionExtensionTest extends TestCase
{
    public function testGetTypeExtensions()
    {
        $typeExtension1 = new TestTypeExtension();
        $typeExtension2 = new Tes


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\ChoiceList\Loader;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\ChoiceList\Loader\LazyChoiceLoader;
use Symfony\Component\Form\Tests\Fixtures\ArrayChoiceLoader;

class LazyChoiceLoaderTest extends TestCase
{
    private LazyChoiceLoader $loader;

 $this->loader->loadChoiceList()->getChoices());
    }

    public function testOnDemandChoiceListAfterLoadingValuesForChoices()
    {
        $this->loader->loadValuesForChoices(['A']);
        $this->assertSame(['A' => 'A'], $this->loader->loadChoiceList

    protected function setUp(): void
    {
        $this->loader = new LazyChoiceLoader(new ArrayChoiceLoader(['A', 'B', 'C']));
    }

    public function testInitialEmptyChoiceListLoading()
    {
        $this->assertSame([],


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Form\Tests\Util;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Form\Util\ServerParams;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\RequestStack;

class ServerParamsTest extends TestCase
{
    public fun

(1024, $serverParams->getContentLength());

        unset($_SERVER['CONTENT_LENGTH']);
    }

    public function testGetContentLengthFromRequest()
    {
        $request = Request::create('http://foo', 'GET', [], [], [], ['CONTENT_LENGTH' => 1024]);

ction testGetContentLengthFromSuperglobals()
    {
        $serverParams = new ServerParams();
        $this->assertNull($serverParams->getContentLength());

        $_SERVER['CONTENT_LENGTH'] = 1024;

        $this->assertEquals


enameFilterIterator;
use Symfony\Component\Finder\Iterator\LazyIterator;
use Symfony\Component\Finder\Iterator\SizeRangeFilterIterator;
use Symfony\Component\Finder\Iterator\SortableIterator;

/**
 * Finder allows to build rules to find files and directories.
 *
 * It is a thin wrapper around several specialized iterator classes.
 *
 * All rules may be invoked several times.
 *
 * All methods return the current Finder object to allow chaining:
 *
 *     $finder = Finder::create()->files()->name('*.php')->in

;
    public const IGNORE_DOT_FILES = 2;
    public const IGNORE_VCS_IGNORED_FILES = 4;

    private int $mode = 0;
    private array $names = [];
    private array $notNames = [];
    private array $exclude = [];
    private array $filters = [];
    priva

(__DIR__);
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @implements \IteratorAggregate<non-empty-string, SplFileInfo>
 */
class Finder implements \IteratorAggregate, \Countable
{
    public const IGNORE_VCS_FILES = 1


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Finder\Iterator\MultiplePcreFilterIterator;

class MultiplePcreFilterIteratorTest extends TestCase
{
    #[DataProvider('getIsRegexFixtures')]
    public function testIsReg

tures()
    {
        yield ['foo', false, 'string'];
        yield [' foo ', false, '" " is not a valid delimiter'];
        yield ['\\foo\\', false, '"\\" is not a valid delimiter'];
        yield ['afooa', false, '"a" is not a valid delimiter'];

ex($string, $isRegex, $message)
    {
        $testIterator = new TestMultiplePcreFilterIterator();
        $this->assertEquals($isRegex, $testIterator->isRegex($string), $message);
    }

    public static function getIsRegexFix


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder;

/**
 * Glob matches globbing patterns against text.
 *
 *     if match_glob("foo.*", "foo.bar") echo "matched\n";
 *
 *     // prints foo.bar and foo.baz
 *     $regex = glob_to_regex("foo.*");
 *     for (['foo.bar', 'foo.baz', 'foo', 'bar'] as $t)
 *     {
 *         if (/$regex/) echo "matched: $car\n";
 *     }
 *
 * Glob implements

  Richard Clamp <richardc@unixbeard.net> Perl version
 * @copyright  2004-2005 Fabien Potencier <fabien@symfony.com>
 * @copyright  2002 Richard Clamp <richardc@unixbeard.net>
 */
class Glob
{
    /**
     * Returns a regexp which is the equivalent of the

glob(3) style matching that can be used to match
 * against text, rather than fetching names from a filesystem.
 *
 * Based on the Perl Text::Glob module.
 *
 * @author Fabien Potencier <fabien@symfony.com> PHP port
 * @author


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

/**
 * CustomFilterIterator filters files by applying anonymous functions.
 *
 * The anonymous function receives a \SplFileInfo and must return false
 * to remove files.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @extends \FilterIterator<

                 $filters  An array of PHP callbacks
     *
     * @throws \InvalidArgumentException
     */
    public function __construct(\Iterator $iterator, array $filters)
    {
        foreach ($filters as $filter) {
            if (!\is_callable($f

string, \SplFileInfo>
 */
class CustomFilterIterator extends \FilterIterator
{
    private array $filters = [];

    /**
     * @param \Iterator<string, \SplFileInfo> $iterator The Iterator to filter
     * @param callable[]


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\Comparator\DateComparator;

/**
 * DateRangeFilterIterator filters out files that are not in the given date range (last modified dates).
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @extends \Filter

          $comparators
     */
    public function __construct(\Iterator $iterator, array $comparators)
    {
        $this->comparators = $comparators;

        parent::__construct($iterator);
    }

    /**
     * Filters the iterator values.
     */

Iterator<string, \SplFileInfo>
 */
class DateRangeFilterIterator extends \FilterIterator
{
    private array $comparators = [];

    /**
     * @param \Iterator<string, \SplFileInfo> $iterator
     * @param DateComparator[]


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\SplFileInfo;

/**
 * ExcludeDirectoryFilterIterator filters out directories.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @extends \FilterIterator<string, SplFileInfo>
 *
 * @implements \RecursiveIterator<string, SplFileInfo>
 */
class ExcludeDirectoryFilterIterator extends \FilterIterat

te ?string $excludedPattern = null;
    /** @var list<callable(SplFileInfo):bool> */
    private array $pruneFilters = [];

    /**
     * @param \Iterator<string, SplFileInfo>          $iterator    The Iterator to filter
     * @param list<string|callable

or implements \RecursiveIterator
{
    /** @var \Iterator<string, SplFileInfo> */
    private \Iterator $iterator;
    private bool $isRecursive;
    /** @var array<string, true> */
    private array $excludedDirs = [];
    priva


hp

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\Glob;

/**
 * FilenameFilterIterator filters files by patterns (a regexp, a glob, or a string).
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @extends MultiplePcreFilterIterator<string, \Spl

lename());
    }

    /**
     * Converts glob to regexp.
     *
     * PCRE patterns are left unchanged.
     * Glob strings are transformed with Glob::toRegex().
     *
     * @param string $str Pattern: glob or regexp
     */
    protected function toRe

FileInfo>
 */
class FilenameFilterIterator extends MultiplePcreFilterIterator
{
    /**
     * Filters the iterator values.
     */
    public function accept(): bool
    {
        return $this->isAccepted($this->current()->getFi


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\SplFileInfo;

/**
 * PathFilterIterator filters files by path patterns (e.g. some/special/dir).
 *
 * @author Fabien Potencier  <fabien@symfony.com>
 * @author Włodzimierz Gajda <gajdaw@gajdaw.pl>
 *
 * @extends

this->current()->getRelativePathname();

        if ('\\' === \DIRECTORY_SEPARATOR) {
            $filename = str_replace('\\', '/', $filename);
        }

        return $this->isAccepted($filename);
    }

    /**
     * Converts strings to regexp.

 MultiplePcreFilterIterator<string, SplFileInfo>
 */
class PathFilterIterator extends MultiplePcreFilterIterator
{
    /**
     * Filters the iterator values.
     */
    public function accept(): bool
    {
        $filename = $


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\Exception\AccessDeniedException;
use Symfony\Component\Finder\SplFileInfo;

/**
 * Extends the \RecursiveDirectoryIterator to support relative paths.
 *
 * @author Victor Berchet <victor@suumit.com>
 *
 * @extends \RecursiveDirectoryIterator<string, SplFileInfo>
 */
class RecursiveDirectoryIterator e

terations
    private string $rootPath;
    private string $subPath;
    private string $directorySeparator = '/';

    /**
     * @throws \RuntimeException
     */
    public function __construct(string $path, int $flags, bool $ignoreUnreadableDirs = fals

xtends \RecursiveDirectoryIterator
{
    private bool $ignoreUnreadableDirs;
    private bool $ignoreFirstRewind = true;

    // these 3 properties take part of the performance optimization to avoid redoing the same work in all i


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\Gitignore;

/**
 * @extends \FilterIterator<string, \SplFileInfo>
 */
final class VcsIgnoredFilterIterator extends \FilterIterator
{
    private string $baseDir;

    /**
     * @var array<string, array{0: string, 1: string}|null>
     */
    private array $gitignoreFilesCache = [];

    /**
     * @

   $this->baseDir = $this->normalizePath($baseDir);

        foreach ([$this->baseDir, ...$this->parentDirectoriesUpwards($this->baseDir)] as $directory) {
            if (@is_dir("{$directory}/.git")) {
                $this->baseDir = $directory;

var array<string, bool>
     */
    private array $ignoredPathsCache = [];

    /**
     * @param \Iterator<string, \SplFileInfo> $iterator
     */
    public function __construct(\Iterator $iterator, string $baseDir)
    {


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests;

use PHPUnit\Framework\Attributes\RunInSeparateProcess;
use Symfony\Component\Finder\Finder;

class FinderOpenBasedirTest extends Iterator\RealIteratorTestCase
{
    #[RunInSeparateProcess]
    public function testIgnoreVCSIgnoredWithOpenBasedir()
    {

  $finder = $this->buildFinder();
        $this->assertSame(
            $finder,
            $finder
                ->ignoreVCS(true)
                ->ignoreDotFiles(true)
                ->ignoreVCSIgnored(true)
        );

        $openBaseDir = \dirn

     $this->markTestIncomplete('Test case needs to be refactored so that PHPUnit can run it');

        if (\ini_get('open_basedir')) {
            $this->markTestSkipped('Cannot test when open_basedir is set');
        }


ore::toRegex(implode("\r\n", $gitignoreLines)));
        $this->assertSame($regex, Gitignore::toRegex(implode("\r", $gitignoreLines)));

        foreach ($matchingCases as $matchingCase) {
            $this->assertMatchesRegularExpression(
                $regex,
                $matchingCase,
                \sprintf(
                    "Failed asserting path:\n%s\nmatches gitignore patterns:\n%s",
                    preg_replace('~^~m', '    ', $matchingCase),
                    preg_replace('~^~m', '

se,
                \sprintf("Failed asserting path:\n%s\nNOT matching gitignore patterns:\n%s",
                    preg_replace('~^~m', '    ', $nonMatchingCase),
                    preg_replace('~^~m', '    ', $patterns)
                )
            )

   ', $patterns)
                )
            );
        }

        foreach ($nonMatchingCases as $nonMatchingCase) {
            $this->assertDoesNotMatchRegularExpression(
                $regex,
                $nonMatchingCa


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Comparator\DateComparator;
use Symfony\Component\Finder\Iterator\DateRangeFilterIterator;

class DateRangeFilterIteratorTest extends RealIteratorTestCase
{
    #[DataProvider('getAcceptData')]

er, $size);

        $this->assertIterator($expected, $iterator);
    }

    public static function getAcceptData()
    {
        $since20YearsAgo = [
            '.git',
            'test.py',
            'foo',
            'foo/bar.tmp',
            'tes

public function testAccept($size, $expected)
    {
        $files = self::$files;
        $files[] = static::toAbsolute('doesnotexist');
        $inner = new Iterator($files);

        $iterator = new DateRangeFilterIterator($inn


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Iterator\ExcludeDirectoryFilterIterator;
use Symfony\Component\Finder\Iterator\RecursiveDirectoryIterator;

class ExcludeDirectoryFilterIteratorTest extends RealIteratorTestCase
{
    #[DataProvide

atorIterator::SELF_FIRST);

        $iterator = new ExcludeDirectoryFilterIterator($inner, $directories);

        $this->assertIterator($expected, $iterator);
    }

    public static function getAcceptData()
    {
        $foo = [
            '.bar',

r('getAcceptData')]
    public function testAccept($directories, $expected)
    {
        $inner = new \RecursiveIteratorIterator(new RecursiveDirectoryIterator($this->toAbsolute(), \FilesystemIterator::SKIP_DOTS), \RecursiveIter


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Iterator\FileTypeFilterIterator;

class FileTypeFilterIteratorTest extends RealIteratorTestCase
{
    #[DataProvider('getAcceptData')]
    public function testAccept($mode

cceptData()
    {
        $onlyFiles = [
            'test.py',
            'foo/bar.tmp',
            'test.php',
            '.bar',
            '.foo/.bar',
            '.foo/bar',
            'foo bar',
            'qux/baz_100_1.py',
            'zebu

, $expected)
    {
        $inner = new InnerTypeIterator(self::$files);

        $iterator = new FileTypeFilterIterator($inner, $mode);

        $this->assertIterator($expected, $iterator);
    }

    public static function getA


hp

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

class Iterator implements \Iterator
{
    protected array $values = [];

    public function __construct(array $values = [])
    {
        foreach ($values as $value) {
            $this->attach(new \SplFileInfo($value));

ublic function valid(): bool
    {
        return false !== $this->current();
    }

    public function next(): void
    {
        next($this->values);
    }

    public function current(): mixed
    {
        return current($this->values);
    }

    pub

     }
        $this->rewind();
    }

    public function attach(\SplFileInfo $fileinfo): void
    {
        $this->values[] = $fileinfo;
    }

    public function rewind(): void
    {
        reset($this->values);
    }

    p


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\TestCase;

abstract class IteratorTestCase extends TestCase
{
    protected function assertIterator($expected, \Traversable $iterator)
    {
        // set iterator_to_array $use_key to false to avoid values merge
        // this made FinderTest::testAppendWithAnArray() fail with GnuFinderAdapter

('/', \DIRECTORY_SEPARATOR, $path), $expected);

        sort($values);
        sort($expected);

        $this->assertEquals($expected, array_values($values));
    }

    protected function assertOrderedIterator($expected, \Traversable $iterator)
    {

    $values = array_map(static fn (\SplFileInfo $fileinfo) => str_replace('/', \DIRECTORY_SEPARATOR, $fileinfo->getPathname()), iterator_to_array($iterator, false));

        $expected = array_map(static fn ($path) => str_replace


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder;

/**
 * Gitignore matches against text.
 *
 * @author Michael Voříšek <vorismi3@fel.cvut.cz>
 * @author Ahmed Abdou <mail@ahmd.io>
 */
class Gitignore
{
    /**
     * Returns a regexp which is the equivalent of the gitignore pattern.
     *
     * Format specification: https://git-scm.co

ingNegatedPatterns(string $gitignoreFileContent): string
    {
        return self::buildRegex($gitignoreFileContent, true);
    }

    private static function buildRegex(string $gitignoreFileContent, bool $inverted): string
    {
        $gitignoreFileCon

m/docs/gitignore#_pattern_format
     */
    public static function toRegex(string $gitignoreFileContent): string
    {
        return self::buildRegex($gitignoreFileContent, false);
    }

    public static function toRegexMatch


 part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder;

/**
 * Extends \SplFileInfo to support relative paths.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 */
class SplFileInfo extends \SplFileInfo
{
    /**
     * @param string $file             The file name
     * @param string $relativePath     The relati

parent::__construct($file);
    }

    /**
     * Returns the relative path.
     *
     * This path does not contain the file name.
     */
    public function getRelativePath(): string
    {
        return $this->relativePath;
    }

    /**
     * Retur

ve path
     * @param string $relativePathname The relative path name
     */
    public function __construct(
        string $file,
        private string $relativePath,
        private string $relativePathname,
    ) {


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

/**
 * DepthRangeFilterIterator limits the directory depth.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @template-covariant TKey
 * @template-covariant TValue
 *
 * @extends \FilterIterator<TKey, TValue>
 */
class DepthRangeFi

                                 $minDepth The min depth
     * @param int                                                          $maxDepth The max depth
     */
    public function __construct(\RecursiveIteratorIterator $iterator, int $minDepth = 0, int

lterIterator extends \FilterIterator
{
    private int $minDepth = 0;

    /**
     * @param \RecursiveIteratorIterator<\RecursiveIterator<TKey, TValue>> $iterator The Iterator to filter
     * @param int


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\SplFileInfo;

/**
 * FilecontentFilterIterator filters files by their contents using patterns (regexps or strings).
 *
 * @author Fabien Potencier  <fabien@symfony.com>
 * @author Włodzimierz Gajda <gajdaw@gajda

    {
        if (!$this->matchRegexps && !$this->noMatchRegexps) {
            return true;
        }

        $fileinfo = $this->current();

        if ($fileinfo->isDir() || !$fileinfo->isReadable()) {
            return false;
        }

        $conte

w.pl>
 *
 * @extends MultiplePcreFilterIterator<string, SplFileInfo>
 */
class FilecontentFilterIterator extends MultiplePcreFilterIterator
{
    /**
     * Filters the iterator values.
     */
    public function accept(): bool


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

use Symfony\Component\Finder\Comparator\NumberComparator;

/**
 * SizeRangeFilterIterator filters out files that are not in the given size range.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @extends \FilterIterator<string, \Sp

rs
     */
    public function __construct(\Iterator $iterator, array $comparators)
    {
        $this->comparators = $comparators;

        parent::__construct($iterator);
    }

    /**
     * Filters the iterator values.
     */
    public function acc

lFileInfo>
 */
class SizeRangeFilterIterator extends \FilterIterator
{
    private array $comparators = [];

    /**
     * @param \Iterator<string, \SplFileInfo> $iterator
     * @param NumberComparator[]              $comparato


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

/**
 * SortableIterator applies a sort on a given Iterator.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @implements \IteratorAggregate<string, \SplFileInfo>
 */
class SortableIterator implements \IteratorAggregate
{
    public const SORT_BY_NONE = 0;
    public const SORT_BY_NAME = 1;
    public const SORT_BY_TYPE

;
    public const SORT_BY_NAME_NATURAL_CASE_INSENSITIVE = 8;
    public const SORT_BY_EXTENSION = 9;
    public const SORT_BY_SIZE = 10;

    /** @var \Traversable<string, \SplFileInfo> */
    private \Traversable $iterator;
    private \Closure|int $sort

= 2;
    public const SORT_BY_ACCESSED_TIME = 3;
    public const SORT_BY_CHANGED_TIME = 4;
    public const SORT_BY_MODIFIED_TIME = 5;
    public const SORT_BY_NAME_NATURAL = 6;
    public const SORT_BY_NAME_CASE_INSENSITIVE = 7


/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Iterator\CustomFilterIterator;

class CustomFilterIteratorTest extends IteratorTestCase
{
    public function testWithInvalidFilter()
    {
        $thi

 = new Iterator(['test.php', 'test.py', 'foo.php']);

        $iterator = new CustomFilterIterator($inner, $filters);

        $this->assertIterator($expected, $iterator);
    }

    public static function getAcceptData()
    {
        return [

s->expectException(\InvalidArgumentException::class);
        new CustomFilterIterator(new Iterator(), ['foo']);
    }

    #[DataProvider('getAcceptData')]
    public function testAccept($filters, $expected)
    {
        $inner


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Iterator\FilecontentFilterIterator;

class FilecontentFilterIteratorTest extends IteratorTestCase
{
    public function testAccept()
    {
        $inner = new MockFileListIterator(['test.txt']);

        $iterator = new FilecontentFilterIterator($inner, ['directory'], []);
        $this->assertIterator([], $iterator);
    }

    public function testUnreadableFile()
    {
        $inner = new MockFileListIterator(['file r-']);
        $iterator = ne

       $iterator = new FilecontentFilterIterator($inner, [], []);
        $this->assertIterator(['test.txt'], $iterator);
    }

    public function testDirectory()
    {
        $inner = new MockFileListIterator(['directory']);


/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Finder\Iterator\LazyIterator;

class LazyIteratorTest extends TestCase
{
    public function testLazy()
    {
        new LazyIterator(function () {
            $this->markTe

'bar']));

        $this->assertCount(2, iterator_to_array($iterator));
    }

    public function testInnerDestructedAtTheEnd()
    {
        $count = 0;
        $iterator = new LazyIterator(static function () use (&$count) {
            ++$count;

stFailed('lazyIterator should not be called');
        });

        $this->expectNotToPerformAssertions();
    }

    public function testDelegate()
    {
        $iterator = new LazyIterator(static fn () => new Iterator(['foo',


 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\ErrorHandler\Error;

class ClassNotFoundError extends \Error
{
    public function __construct(string $message, \Throwable $previous)
    {
        parent::__construct($message, $previous->getCode(), $previous->getPrevious());

        foreach ([

previous->getFile(),
            'line' => $previous->getLine(),
            'trace' => $previous->getTrace(),
        ] as $property => $value) {
            $refl = new \ReflectionProperty(\Error::class, $property);
            $refl->setValue($this, $va


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\ErrorHandler\Error;

class FatalError extends \Error
{
    /**
     * @param array $error An array as returned by error_get_last()
     */
    public function __construct(
        string $message,
        int $code,
        private array $error,
        ?int $traceOffset = null,
        bool $tra

nset($frame['args'], $frame['this'], $frame);
                }
            }
        } elseif (null !== $traceOffset) {
            if (\function_exists('xdebug_get_function_stack') && \in_array(\ini_get('xdebug.mode'), ['develop', false], true) && $trace

ceArgs = true,
        ?array $trace = null,
    ) {
        parent::__construct($message, $code);

        if (null !== $trace) {
            if (!$traceArgs) {
                foreach ($trace as &$frame) {
                    u


<?php

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\ErrorHandler\Error;

class UndefinedFunctionError extends \Error
{
    public function __construct(string $message, \Throwable $previous)
    {
        parent::__construct($message, $previous->getCode(), $previous->getPrevious());

        foreac

         'line' => $previous->getLine(),
            'trace' => $previous->getTrace(),
        ] as $property => $value) {
            $refl = new \ReflectionProperty(\Error::class, $property);
            $refl->setValue($this, $value);
        }
    }
}

h ([
            'file' => $previous->getFile(),


 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\ErrorHandler\Error;

class UndefinedMethodError extends \Error
{
    public function __construct(string $message, \Throwable $previous)
    {
        parent::__construct($message, $previous->getCode(), $previous->getPrevious());

        foreach ([

 $previous->getFile(),
            'line' => $previous->getLine(),
            'trace' => $previous->getTrace(),
        ] as $property => $value) {
            $refl = new \ReflectionProperty(\Error::class, $property);
            $refl->setValue($this, $


html>

    <meta charset="<?= $this->charset; ?>" />
    <meta name="robots" content="noindex,nofollow,noarchive" />
    <title>An Error Occurred: <?= $statusText; ?></title>
    <link rel="icon" href="data:image/svg+xml,<svg xmlns=%22http://www.w3.org/2000/svg%22 viewBox=%220 0 128 128%22><text y=%221.2em%22 font-size=%2296%22>❌</text></svg>" />

Oops! An Error Occurred</h1

server returned a "<?= $statusCode; ?> <?= $statusText; ?>".

        Something is broken. Please let us know what you were doing when this error occurred.
        We will fix it as soon as possible. Sorry for any inconvenience caused.
    </p


class="exception-metadata">

                <?php foreach (array_reverse($exception->getAllPrevious(), true) as $index => $previousException) { ?>
                    <a href="#trace-box-<?= $index + 2; ?>"><?= $this->abbrClass($previousException->getClass()); ?>
                    <?= $this->include('assets/images/chevron-right.svg'); ?>
                <?php } ?>
                <a href="#trace-box

/div>

            <h1 class="break-long-words exception-message<?= mb_strlen($exceptionMessage) > 180 ? ' long' : ''; ?>"><?= $this->formatFileFromText(nl2br($exceptionMessage)); ?

-1"><?= $this->abbrClass($exception->getClass()); ?>

                HTTP <?= $statusCode; ?> <?= $statusText; ?>

    <


ionMessage, $statusCode, $statusText); ?> -->
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="<?= $this->charset; ?>" />
        <meta name="robots" content="noindex,nofollow" />
        <meta name="viewport" content="width=device-width,initial-scale=1" />
        <title><?= $_message; ?></title>
        <link rel="icon" type="image/png" href="<?= $this->include('assets/images/favicon.png.base64'); ?>" />
        <style><?= $this->include('assets/css/exception.css'); ?></style>
        <s

(prefers-color-scheme: dark)').matches ? 'theme-dark' : 'theme-light')
            );
        </script>

        <?php if (class_exists(\Composer\InstalledVersions::class) && \Composer\InstalledVersions::isInstalled('symfony/http-kernel')) { ?>

tyle><?= $this->include('assets/css/exception_full.css'); ?></style>
    </head>
    <body>
        <script>
            document.body.classList.add(
                localStorage.getItem('symfony/profiler/theme') || (matchMedia('


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Iterator\PathFilterIterator;

class PathFilterIteratorTest extends IteratorTestCase
{
    #[DataProvider('getTestFilterData')]
    public function testFilter(\Iterator $inner, array $matchPatterns, array $noMatchPatterns, array $resultArray)
    {

leListIterator();

        // PATH:   A/B/C/abc.dat
        $inner[] = new MockSplFileInfo([
            'name' => 'abc.dat',
            'relativePathname' => 'A'.\DIRECTORY_SEPARATOR.'B'.\DIRECTORY_SEPARATOR.'C'.\DIRECTORY_SEPARATOR.'abc.dat',
        ])

        $iterator = new PathFilterIterator($inner, $matchPatterns, $noMatchPatterns);
        $this->assertIterator($resultArray, $iterator);
    }

    public static function getTestFilterData()
    {
        $inner = new MockFi


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\Group;
use Symfony\Component\Finder\Iterator\RecursiveDirectoryIterator;

class RecursiveDirectoryIteratorTest extends IteratorTestCase
{
    protected function setUp(): void
    {
        if (!\in_array('ftp', stream_get_wrappers(), true)

env('INTEGRATION_FTP_URL')) {
            self::markTestSkipped('INTEGRATION_FTP_URL env var is not defined.');
        }

        $i = new RecursiveDirectoryIterator(getenv('INTEGRATION_FTP_URL').\DIRECTORY_SEPARATOR, \RecursiveDirectoryIterator::SKIP_DOT

|| !\ini_get('allow_url_fopen')) {
            $this->markTestSkipped('Unsupported stream "ftp".');
        }
    }

    #[Group('network')]
    #[Group('integration')]
    public function testRewindOnFtp()
    {
        if (!get


buted with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Iterator\SortableIterator;

class SortableIteratorTest extends RealIteratorTestCase
{
    public function testConstructor()
    {
        try {
            new SortableIterator(new Iterator([]), -255);
            $this->fail('__construct() throws an \InvalidArgumentException exception if the mode is not valid');
        } catch (\Exception $e) {

nction testAccept($mode, $expected)
    {
        if (!\is_callable($mode)) {
            switch ($mode) {
                case SortableIterator::SORT_BY_ACCESSED_TIME:
                    touch(self::toAbsolute('.git'));
                    sleep(1);

           $this->assertInstanceOf(\InvalidArgumentException::class, $e, '__construct() throws an \InvalidArgumentException exception if the mode is not valid');
        }
    }

    #[DataProvider('getAcceptData')]
    public fu


buted with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

trait VfsIteratorTestTrait
{
    private static int $vfsNextSchemeIndex = 0;

    /** @var array<string, \Closure(string, 'list_dir_open'|'list_dir_rewind'|'is_dir'): (list<string>|bool)> */
    public static array $vfsProviders;

    protected string $vfsScheme;

    /** @var list<array{string, string, mixed}> */
    protected array $vfsLog = [];

    protected function setUp(): void
    {
        parent::setUp();

t<string>|bool)> */
            public static array $vfsProviders = [];

            /** @var resource */
            public $context;

            private string $scheme;

            private string $dirPath;

            /** @var list<string> */

  $this->vfsScheme = 'symfony-finder-vfs-test-'.++self::$vfsNextSchemeIndex;

        $vfsWrapperClass = \get_class(new class {
            /** @var array<string, \Closure(string, 'list_dir_open'|'list_dir_rewind'|'is_dir'): (lis


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Comparator;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Finder\Comparator\Comparator;

class ComparatorTest extends TestCase
{
    public function testInvalidOperator()
    {
        $this->expectException(\InvalidArgumentExce

tring $target, string $testedValue)
    {
        $c = new Comparator($target, $operator);

        $this->assertSame($target, $c->getTarget());
        $this->assertSame($operator, $c->getOperator());

        $this->assertTrue($c->test($testedValue));

ption::class);
        $this->expectExceptionMessage('Invalid operator "foo".');

        new Comparator('some target', 'foo');
    }

    #[DataProvider('provideMatches')]
    public function testTestSucceeds(string $operator, s


 This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Comparator;

/**
 * DateCompare compiles date comparisons.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 */
class DateComparator extends Comparator
{
    /**
     * @param string $test A comparison string
     *
     * @throws \InvalidArgumentE

InvalidArgumentException(\sprintf('Don\'t understand "%s" as a date test.', $test));
        }

        try {
            $date = new \DateTimeImmutable($matches[2]);
            $target = $date->format('U');
        } catch (\Exception) {
            thro

xception If the test is not understood
     */
    public function __construct(string $test)
    {
        if (!preg_match('#^\s*(==|!=|[<>]=?|after|since|before|until)?\s*(.+?)\s*$#i', $test, $matches)) {
            throw new \


ge.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Comparator;

/**
 * NumberComparator compiles a simple comparison to an anonymous
 * subroutine, which you can call with a value to be tested again.
 *
 * Now this would be very pointless, if NumberCompare didn't understand
 * magnitudes.
 *
 * The target value may use magnitudes of kiloby

umber::Compare module.
 *
 * @author    Fabien Potencier <fabien@symfony.com> PHP port
 * @author    Richard Clamp <richardc@unixbeard.net> Perl version
 * @copyright 2004-2005 Fabien Potencier <fabien@symfony.com>
 * @copyright 2002 Richard Clamp <richard

tes (k, ki),
 * megabytes (m, mi), or gigabytes (g, gi). Those suffixed
 * with an i use the appropriate 2**n version in accordance with the
 * IEC standard: http://physics.nist.gov/cuu/Units/binary.html
 *
 * Based on the Perl N


hp

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\ErrorHandler;

/**
 * Registers all the debug tools.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 */
class Debug
{
    public static function enable(): ErrorHandler
    {
        error_reporting(\E_ALL & ~\E_DEPRECATED & ~\E_USER_DEPRECATED)

    // CLI - display errors only if they're not already logged to STDERR
            ini_set('display_errors', 1);
        }

        @ini_set('zend.assertions', 1);
        ini_set('assert.active', 1);
        ini_set('assert.exception', 1);

        Debu

;

        if (!\in_array(\PHP_SAPI, ['cli', 'phpdbg', 'embed'], true)) {
            ini_set('display_errors', 0);
        } elseif (!filter_var(\ini_get('log_errors'), \FILTER_VALIDATE_BOOL) || \ini_get('error_log')) {


se Symfony\Component\ErrorHandler\ErrorRenderer\CliErrorRenderer;
use Symfony\Component\ErrorHandler\ErrorRenderer\HtmlErrorRenderer;
use Symfony\Component\ErrorHandler\Exception\SilencedErrorContext;

/**
 * A generic ErrorHandler for the PHP engine.
 *
 * Provides five bit fields that control how errors are handled:
 * - thrownErrors: errors thrown as \ErrorException
 * - loggedErrors: logged errors, when not @-silenced
 * - scopedErrors: errors thrown or logged with their local context
 * - tracedErrors:

ogging.
 * Uncaught exceptions are logged as E_ERROR.
 * E_DEPRECATED and E_USER_DEPRECATED levels never throw.
 * E_RECOVERABLE_ERROR and E_USER_ERROR levels always throw.
 * Non catchable errors that can be detected at shutdown time are logged when the s

 errors logged with their stack trace
 * - screamedErrors: never @-silenced errors
 *
 * Each error level can be logged by a dedicated PSR-3 logger object.
 * Screaming only applies to logging.
 * Throwing takes precedence over l


e;
use Symfony\Component\HttpKernel\Exception\HttpExceptionInterface;
use Symfony\Component\VarDumper\Caster\Caster;
use Symfony\Component\VarDumper\Cloner\Data;
use Symfony\Component\VarDumper\Cloner\Stub;
use Symfony\Component\VarDumper\Cloner\VarCloner;

/**
 * FlattenException wraps a PHP Error or Exception to be able to serialize it.
 *
 * Basically, this class removes all objects from the trace.
 *
 * @author Fabien Potencier <fabien@symfony.com>
 */
class FlattenException
{
    private string $messag

 array $headers;
    private string $file;
    private int $line;
    private ?string $asString = null;
    private Data $dataRepresentation;

    public static function create(\Exception $exception, ?int $statusCode = null, array $headers = []): static

e;
    private string|int $code;
    private ?self $previous = null;
    private array $trace;
    private string $traceAsString;
    private string $class;
    private int $statusCode;
    private string $statusText;
    private


buted with this source code.
 */

namespace Symfony\Component\ErrorHandler\ErrorEnhancer;

use Composer\Autoload\ClassLoader;
use Symfony\Component\ErrorHandler\DebugClassLoader;
use Symfony\Component\ErrorHandler\Error\ClassNotFoundError;
use Symfony\Component\ErrorHandler\Error\FatalError;

/**
 * @author Fabien Potencier <fabien@symfony.com>
 */
class ClassNotFoundErrorEnhancer implements ErrorEnhancerInterface
{
    public function enhance(\Throwable $error): ?\Throwable
    {
        // Some specific v

'"]([^\'"]+)[\'"] not found$/', $message, $matches)) {
            return null;
        }
        $typeName = strtolower($matches[1]);
        $fullyQualifiedClassName = $matches[2];

        if (false !== $namespaceSeparatorIndex = strrpos($fullyQualified

ersions of PHP produce a fatal error when extending a not found class.
        $message = !$error instanceof FatalError ? $error->getMessage() : $error->getError()['message'];
        if (!preg_match('/^(Class|Interface|Trait) [\


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\ErrorHandler\ErrorEnhancer;

use Symfony\Component\ErrorHandler\Error\FatalError;
use Symfony\Component\ErrorHandler\Error\UndefinedFunctionError;

/**
 * @author Fabien Potencier <fabien@symfony.com>
 */
class UndefinedFunctionErrorEnhancer implements ErrorEnhancerInterface
{
    public function enhance(\Throwable $error): ?\Throwable
    {

otFoundSuffix);
        if ($notFoundSuffixLen > $messageLen) {
            return null;
        }

        if (0 !== substr_compare($message, $notFoundSuffix, -$notFoundSuffixLen)) {
            return null;
        }

        $prefix = 'Call to undefined

    if ($error instanceof FatalError) {
            return null;
        }

        $message = $error->getMessage();
        $messageLen = \strlen($message);
        $notFoundSuffix = '()';
        $notFoundSuffixLen = \strlen($n


amp' => 'int',
            'diff' => 'DateInterval',
        ],
        'DateTimeImmutable' => [
            '__wakeup' => 'void',
            '__set_state' => 'DateTimeImmutable',
            'createFromFormat' => 'DateTimeImmutable|false',
            'getLastErrors' => 'array|false',
            'format' => 'string',
            'getTimezone' => 'DateTimeZone|false',
            'getOffset' => 'int',
            'getTimestamp' => 'int',
            'diff' => 'DateInterval',
            'modify' => 'DateT

teTimeImmutable',
            'setISODate' => 'DateTimeImmutable',
            'setTimestamp' => 'DateTimeImmutable',
            'createFromMutable' => 'static',
        ],
        'DateTimeZone' => [
            'getName' => 'string',
            'getOff

imeImmutable|false',
            'add' => 'DateTimeImmutable',
            'sub' => 'DateTimeImmutable',
            'setTimezone' => 'DateTimeImmutable',
            'setTime' => 'DateTimeImmutable',
            'setDate' => 'Da


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Iterator;

/**
 * MultiplePcreFilterIterator filters files using patterns (regexps, globs or strings).
 *
 * @author Fabien Potencier <fabien@symfony.com>
 *
 * @template-covariant TKey
 * @template-covariant TValue
 *
 * @extends \FilterIterator<TKey, TValue>
 */
abstract class MultiplePcreFilterIterator extends \FilterIterator
{
    prot

atterns that need to match
     * @param string[]                $noMatchPatterns An array of patterns that need to not match
     */
    public function __construct(\Iterator $iterator, array $matchPatterns, array $noMatchPatterns)
    {
        foreach (

ected array $matchRegexps = [];
    protected array $noMatchRegexps = [];

    /**
     * @param \Iterator<TKey, TValue> $iterator        The Iterator to filter
     * @param string[]                $matchPatterns   An array of p


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests;

use PHPUnit\Framework\TestCase;
use Symfony\Component\Finder\Finder;
use Symfony\Component\Finder\Glob;

class GlobTest extends TestCase
{
    public function testGlobToRegexDelimiters()
    {
        $this->assertEquals('#^(?=[^\.])\#$#', Glob::toRegex('#'));
        $this->assertEquals('#^\.[^/]*$#', Glob::toRegex('.*'));

    $finder = new Finder();
        $finder->ignoreDotFiles(false);
        $regex = Glob::toRegex('/**/*.neon');

        foreach ($finder->in(__DIR__) as $k => $v) {
            $k = str_replace(\DIRECTORY_SEPARATOR, '/', $k);
            if (preg_match(

 $this->assertEquals('^\.[^/]*$', Glob::toRegex('.*', true, true, ''));
        $this->assertEquals('/^\.[^/]*$/', Glob::toRegex('.*', true, true, '/'));
    }

    public function testGlobToRegexDoubleStarStrictDots()
    {


/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use PHPUnit\Framework\Attributes\DataProvider;
use Symfony\Component\Finder\Iterator\FilenameFilterIterator;

class FilenameFilterIteratorTest extends IteratorTestCase
{
    #[DataProvider('getAcceptData')]
    public function t

        $this->assertIterator($expected, $iterator);
    }

    public static function getAcceptData()
    {
        return [
            [['test.*'], [], ['test.php', 'test.py']],
            [[], ['test.*'], ['foo.php']],
            [['*.php'], ['test.*

estAccept($matchPatterns, $noMatchPatterns, $expected)
    {
        $inner = new InnerNameIterator(['test.php', 'test.py', 'foo.php']);

        $iterator = new FilenameFilterIterator($inner, $matchPatterns, $noMatchPatterns);


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Iterator;

use Symfony\Component\Filesystem\Filesystem;
use Symfony\Component\Finder\Tests\FinderTest;

abstract class RealIteratorTestCase extends IteratorTestCase
{
    protected static string $tmpDir;
    protected static array $files;

    public static function setUpBeforeClass(): void
    {
        self::$tmpDir = realpath(sys_

get_temp_dir()).\DIRECTORY_SEPARATOR.'symfony_finder';

        self::$files = [
            '.git/',
            '.foo/',
            '.foo/.bar',
            '.foo/bar',
            '.bar',
            'test.py',
            'f


or\VcsIgnoredFilterIterator;

class VcsIgnoredFilterIteratorTest extends IteratorTestCase
{
    private string $tmpDir;

    protected function setUp(): void
    {
        $this->tmpDir = realpath(sys_get_temp_dir()).\DIRECTORY_SEPARATOR.'symfony_finder_vcs_ignored';
        mkdir($this->tmpDir);
    }

    protected function tearDown(): void
    {
        $this->removeDirectory($this->tmpDir);
    }

    /**
     * @param array<string, string> $gitIgnoreFiles
     */
    #[DataProvider('getAcceptData')]

) {
            if (str_ends_with($path, '/')) {
                mkdir($path);
            } else {
                touch($path);
            }
        }

        foreach ($gitIgnoreFiles as $path => $content) {
            file_put_contents("{$this->tmpDi

  public function testAccept(array $gitIgnoreFiles, array $otherFileNames, array $expectedResult, string $baseDir = '')
    {
        $otherFileNames = $this->toAbsolute($otherFileNames);
        foreach ($otherFileNames as $path


 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\Finder\Tests\Comparator;

use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\Finder\Comparator\NumberComparator;

class NumberComparatorTest extends TestCase
{
    #[DataProvider('getConstructorTestData')]
    public function testConstructor($successes, $failures)
    {
        foreach ($successes

tion if the test expression is not valid.');
            } catch (\Exception $e) {
                $this->assertInstanceOf(\InvalidArgumentException::class, $e, '__construct() throws an \InvalidArgumentException if the test expression is not valid.');

 as $s) {
            new NumberComparator($s);
        }

        foreach ($failures as $f) {
            try {
                new NumberComparator($f);
                $this->fail('__construct() throws an \InvalidArgumentExcep