From cefa73a5e3fa727c864206fc7f50157091decd73 Mon Sep 17 00:00:00 2001 From: Phil Davis Date: Thu, 25 Apr 2024 12:46:23 +0545 Subject: [PATCH 1/6] test(Finder): add multi-level unit test items for Finder tests --- .../Component/Finder/Tests/FinderTest.php | 103 +++++++++++++++++- .../Iterator/DateRangeFilterIteratorTest.php | 6 + .../Iterator/DepthRangeFilterIteratorTest.php | 17 ++- .../ExcludeDirectoryFilterIteratorTest.php | 7 ++ .../Iterator/FileTypeFilterIteratorTest.php | 3 + .../Tests/Iterator/RealIteratorTestCase.php | 3 + .../Iterator/SizeRangeFilterIteratorTest.php | 2 + .../Tests/Iterator/SortableIteratorTest.php | 21 ++++ 8 files changed, 153 insertions(+), 9 deletions(-) diff --git a/src/Symfony/Component/Finder/Tests/FinderTest.php b/src/Symfony/Component/Finder/Tests/FinderTest.php index 1ca2e783adcec..f4822473fa040 100644 --- a/src/Symfony/Component/Finder/Tests/FinderTest.php +++ b/src/Symfony/Component/Finder/Tests/FinderTest.php @@ -27,13 +27,13 @@ public function testDirectories() { $finder = $this->buildFinder(); $this->assertSame($finder, $finder->directories()); - $this->assertIterator($this->toAbsolute(['foo', 'qux', 'toto']), $finder->in(self::$tmpDir)->getIterator()); + $this->assertIterator($this->toAbsolute(['foo', 'qux', 'top', 'top/foo', 'toto']), $finder->in(self::$tmpDir)->getIterator()); $finder = $this->buildFinder(); $finder->directories(); $finder->files(); $finder->directories(); - $this->assertIterator($this->toAbsolute(['foo', 'qux', 'toto']), $finder->in(self::$tmpDir)->getIterator()); + $this->assertIterator($this->toAbsolute(['foo', 'qux', 'top', 'top/foo', 'toto']), $finder->in(self::$tmpDir)->getIterator()); } public function testFiles() @@ -52,6 +52,7 @@ public function testFiles() 'qux_10_2.php', 'qux_12_0.php', 'qux_2_0.php', + 'top/foo/file.tmp', 'zebulon.php', 'Zephire.php', ]), $finder->in(self::$tmpDir)->getIterator()); @@ -72,6 +73,7 @@ public function testFiles() 'qux_10_2.php', 'qux_12_0.php', 'qux_2_0.php', + 'top/foo/file.tmp', 'zebulon.php', 'Zephire.php', ]), $finder->in(self::$tmpDir)->getIterator()); @@ -94,6 +96,7 @@ public function testRemoveTrailingSlash() 'qux_10_2.php', 'qux_12_0.php', 'qux_2_0.php', + 'top/foo/file.tmp', 'zebulon.php', 'Zephire.php', ]); @@ -138,6 +141,7 @@ public function testDepth() $this->assertIterator($this->toAbsolute(['foo', 'test.php', 'test.py', + 'top', 'toto', 'foo bar', 'qux', @@ -156,6 +160,7 @@ public function testDepth() $this->assertIterator($this->toAbsolute(['foo', 'test.php', 'test.py', + 'top', 'toto', 'foo bar', 'qux', @@ -175,6 +180,8 @@ public function testDepth() 'foo/bar.tmp', 'qux/baz_100_1.py', 'qux/baz_1_2.py', + 'top/foo', + 'top/foo/file.tmp', ]), $finder->in(self::$tmpDir)->getIterator()); $finder = $this->buildFinder(); @@ -190,6 +197,7 @@ public function testDepthWithArrayParam() 'foo/bar.tmp', 'qux/baz_100_1.py', 'qux/baz_1_2.py', + 'top/foo', ]), $finder->in(self::$tmpDir)->getIterator()); } @@ -252,6 +260,9 @@ public function testNotName() 'foo', 'foo/bar.tmp', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'foo bar', 'qux', @@ -265,6 +276,9 @@ public function testNotName() $this->assertIterator($this->toAbsolute([ 'foo', 'foo/bar.tmp', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'foo bar', 'qux', @@ -291,6 +305,9 @@ public function testNotNameWithArrayParam() $this->assertIterator($this->toAbsolute([ 'foo', 'foo/bar.tmp', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'foo bar', 'qux', @@ -345,6 +362,7 @@ public function testExclude() $this->assertIterator($this->toAbsolute([ 'test.php', 'test.py', + 'top', 'toto', 'foo bar', 'qux', @@ -371,6 +389,9 @@ public function testIgnoreVCS() 'foo/bar.tmp', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', '.bar', @@ -399,6 +420,9 @@ public function testIgnoreVCS() 'foo/bar.tmp', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', '.bar', @@ -426,6 +450,9 @@ public function testIgnoreVCS() 'foo/bar.tmp', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', '.bar', '.foo', @@ -506,6 +533,9 @@ public function testIgnoreVCSCanBeDisabledAfterFirstIteration() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', '.bar', '.foo', @@ -532,6 +562,9 @@ public function testIgnoreVCSCanBeDisabledAfterFirstIteration() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', '.bar', @@ -556,6 +589,9 @@ public function testIgnoreDotFiles() 'foo/bar.tmp', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'foo bar', @@ -584,6 +620,9 @@ public function testIgnoreDotFiles() 'foo/bar.tmp', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'foo bar', @@ -607,6 +646,9 @@ public function testIgnoreDotFiles() 'foo/bar.tmp', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'foo bar', 'qux', @@ -644,6 +686,9 @@ public function testIgnoreDotFilesCanBeDisabledAfterFirstIteration() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'foo bar', ]), $finder->getIterator()); @@ -665,6 +710,9 @@ public function testIgnoreDotFilesCanBeDisabledAfterFirstIteration() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', '.bar', '.foo', @@ -694,6 +742,9 @@ public function testSortByName() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'zebulon.php', ]), $finder->in(self::$tmpDir)->getIterator()); @@ -706,6 +757,8 @@ public function testSortByType() $this->assertOrderedIterator($this->toAbsolute([ 'foo', 'qux', + 'top', + 'top/foo', 'toto', 'Zephire.php', 'foo bar', @@ -720,6 +773,7 @@ public function testSortByType() 'qux_2_0.php', 'test.php', 'test.py', + 'top/foo/file.tmp', 'zebulon.php', ]), $finder->in(self::$tmpDir)->getIterator()); } @@ -731,6 +785,9 @@ public function testSortByAccessedTime() $this->assertIterator($this->toAbsolute([ 'foo/bar.tmp', 'test.php', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'test.py', 'foo', @@ -754,6 +811,9 @@ public function testSortByChangedTime() $finder = $this->buildFinder(); $this->assertSame($finder, $finder->sortByChangedTime()); $this->assertIterator($this->toAbsolute([ + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'test.py', 'test.php', @@ -781,6 +841,9 @@ public function testSortByModifiedTime() $this->assertIterator($this->toAbsolute([ 'foo/bar.tmp', 'test.php', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'test.py', 'foo', @@ -807,6 +870,9 @@ public function testReverseSorting() $this->assertOrderedIteratorInForeach($this->toAbsolute([ 'zebulon.php', 'toto', + 'top/foo/file.tmp', + 'top/foo', + 'top', 'test.py', 'test.php', 'qux_2_0.php', @@ -845,6 +911,9 @@ public function testSortByNameNatural() 'qux_1002_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'zebulon.php', ]), $finder->in(self::$tmpDir)->getIterator()); @@ -867,6 +936,9 @@ public function testSortByNameNatural() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'zebulon.php', ]), $finder->in(self::$tmpDir)->getIterator()); @@ -899,6 +971,9 @@ public function testSortByNameCaseInsensitive() 'qux_1002_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'zebulon.php', 'Zephire.php', @@ -922,6 +997,9 @@ public function testSortByNameCaseInsensitive() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'zebulon.php', 'Zephire.php', @@ -948,6 +1026,9 @@ public function testSort() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'zebulon.php', ]), $finder->in(self::$tmpDir)->getIterator()); @@ -1070,6 +1151,9 @@ public function testFollowLinks() 'foo/bar.tmp', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'foo bar', 'qux', @@ -1166,7 +1250,7 @@ public function testGetIterator() $dirs[] = (string) $dir; } - $expected = $this->toAbsolute(['foo', 'qux', 'toto']); + $expected = $this->toAbsolute(['foo', 'qux', 'top', 'top/foo', 'toto']); sort($dirs); sort($expected); @@ -1174,7 +1258,7 @@ public function testGetIterator() $this->assertEquals($expected, $dirs, 'implements the \IteratorAggregate interface'); $finder = $this->buildFinder(); - $this->assertEquals(3, iterator_count($finder->directories()->in(self::$tmpDir)), 'implements the \IteratorAggregate interface'); + $this->assertEquals(5, iterator_count($finder->directories()->in(self::$tmpDir)), 'implements the \IteratorAggregate interface'); $finder = $this->buildFinder(); $a = iterator_to_array($finder->directories()->in(self::$tmpDir)); @@ -1193,7 +1277,7 @@ public function testRelativePath() $paths[] = $file->getRelativePath(); } - $ref = ['', '', '', '', '', '', '', '', '', '', '', '', '', 'foo', 'qux', 'qux', '']; + $ref = ['', '', '', '', '', '', '', '', '', '', '', '', '', '', '', 'foo', 'qux', 'qux', 'top', 'top'.\DIRECTORY_SEPARATOR.'foo']; sort($ref); sort($paths); @@ -1214,6 +1298,9 @@ public function testRelativePathname() $ref = [ 'Zephire.php', 'test.php', + 'top', + 'top'.\DIRECTORY_SEPARATOR.'foo', + 'top'.\DIRECTORY_SEPARATOR.'foo'.\DIRECTORY_SEPARATOR.'file.tmp', 'toto', 'test.py', 'foo', @@ -1250,8 +1337,11 @@ public function testGetFilenameWithoutExtension() $ref = [ 'Zephire', 'test', + 'top', 'toto', 'test', + 'file', + 'foo', 'foo', 'bar', 'foo bar', @@ -1283,7 +1373,7 @@ public function testAppendWithAFinder() $finder = $finder->append($finder1); - $this->assertIterator($this->toAbsolute(['foo', 'foo/bar.tmp', 'qux', 'toto']), $finder->getIterator()); + $this->assertIterator($this->toAbsolute(['foo', 'foo/bar.tmp', 'qux', 'top', 'top/foo', 'toto']), $finder->getIterator()); } public function testAppendWithAnArray() @@ -1638,6 +1728,7 @@ public function testIgnoredAccessDeniedException() 'test.php', 'test.py', 'qux/baz_100_1.py', + 'top/foo/file.tmp', 'zebulon.php', 'Zephire.php', 'qux/baz_1_2.py', diff --git a/src/Symfony/Component/Finder/Tests/Iterator/DateRangeFilterIteratorTest.php b/src/Symfony/Component/Finder/Tests/Iterator/DateRangeFilterIteratorTest.php index f4985dfab9906..1abbcc763e1cf 100644 --- a/src/Symfony/Component/Finder/Tests/Iterator/DateRangeFilterIteratorTest.php +++ b/src/Symfony/Component/Finder/Tests/Iterator/DateRangeFilterIteratorTest.php @@ -38,6 +38,9 @@ public static function getAcceptData() 'foo', 'foo/bar.tmp', 'test.php', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', '.bar', @@ -62,6 +65,9 @@ public static function getAcceptData() '.git', 'test.py', 'foo', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', '.bar', diff --git a/src/Symfony/Component/Finder/Tests/Iterator/DepthRangeFilterIteratorTest.php b/src/Symfony/Component/Finder/Tests/Iterator/DepthRangeFilterIteratorTest.php index 3a4d67902a18d..24f70f038eafc 100644 --- a/src/Symfony/Component/Finder/Tests/Iterator/DepthRangeFilterIteratorTest.php +++ b/src/Symfony/Component/Finder/Tests/Iterator/DepthRangeFilterIteratorTest.php @@ -37,6 +37,7 @@ public static function getAcceptData() 'test.py', 'foo', 'test.php', + 'top', 'toto', '.foo', '.bar', @@ -57,6 +58,8 @@ public static function getAcceptData() 'foo', 'foo/bar.tmp', 'test.php', + 'top', + 'top/foo', 'toto', 'toto/.git', '.foo', @@ -76,7 +79,13 @@ public static function getAcceptData() 'zebulon.php', 'Zephire.php', ]; - $graterThanOrEqualTo1 = [ + $greaterThanOrEqualTo2 = [ + 'top/foo/file.tmp', + ]; + + $greaterThanOrEqualTo1 = [ + 'top/foo', + 'top/foo/file.tmp', 'toto/.git', 'foo/bar.tmp', '.foo/.bar', @@ -86,6 +95,7 @@ public static function getAcceptData() ]; $equalTo1 = [ + 'top/foo', 'toto/.git', 'foo/bar.tmp', '.foo/.bar', @@ -97,8 +107,9 @@ public static function getAcceptData() return [ [0, 0, self::toAbsolute($lessThan1)], [0, 1, self::toAbsolute($lessThanOrEqualTo1)], - [2, \PHP_INT_MAX, []], - [1, \PHP_INT_MAX, self::toAbsolute($graterThanOrEqualTo1)], + [3, \PHP_INT_MAX, []], + [2, \PHP_INT_MAX, self::toAbsolute($greaterThanOrEqualTo2)], + [1, \PHP_INT_MAX, self::toAbsolute($greaterThanOrEqualTo1)], [1, 1, self::toAbsolute($equalTo1)], ]; } diff --git a/src/Symfony/Component/Finder/Tests/Iterator/ExcludeDirectoryFilterIteratorTest.php b/src/Symfony/Component/Finder/Tests/Iterator/ExcludeDirectoryFilterIteratorTest.php index 728b783108eb6..05d35dcc3960d 100644 --- a/src/Symfony/Component/Finder/Tests/Iterator/ExcludeDirectoryFilterIteratorTest.php +++ b/src/Symfony/Component/Finder/Tests/Iterator/ExcludeDirectoryFilterIteratorTest.php @@ -38,6 +38,7 @@ public static function getAcceptData() '.git', 'test.py', 'test.php', + 'top', 'toto', 'toto/.git', 'foo bar', @@ -64,6 +65,9 @@ public static function getAcceptData() 'foo', 'foo/bar.tmp', 'test.php', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'foo bar', @@ -93,6 +97,9 @@ public static function getAcceptData() 'foo bar', 'qux', 'qux/baz_100_1.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'zebulon.php', 'Zephire.php', 'qux/baz_1_2.py', diff --git a/src/Symfony/Component/Finder/Tests/Iterator/FileTypeFilterIteratorTest.php b/src/Symfony/Component/Finder/Tests/Iterator/FileTypeFilterIteratorTest.php index e349fc74ac991..0ca274288a336 100644 --- a/src/Symfony/Component/Finder/Tests/Iterator/FileTypeFilterIteratorTest.php +++ b/src/Symfony/Component/Finder/Tests/Iterator/FileTypeFilterIteratorTest.php @@ -38,6 +38,7 @@ public static function getAcceptData() '.foo/bar', 'foo bar', 'qux/baz_100_1.py', + 'top/foo/file.tmp', 'zebulon.php', 'Zephire.php', 'qux/baz_1_2.py', @@ -53,6 +54,8 @@ public static function getAcceptData() '.git', 'foo', 'qux', + 'top', + 'top/foo', 'toto', 'toto/.git', '.foo', diff --git a/src/Symfony/Component/Finder/Tests/Iterator/RealIteratorTestCase.php b/src/Symfony/Component/Finder/Tests/Iterator/RealIteratorTestCase.php index 943c9ad0b389e..3d50c35b2984c 100644 --- a/src/Symfony/Component/Finder/Tests/Iterator/RealIteratorTestCase.php +++ b/src/Symfony/Component/Finder/Tests/Iterator/RealIteratorTestCase.php @@ -32,6 +32,9 @@ public static function setUpBeforeClass(): void 'test.py', 'foo/', 'foo/bar.tmp', + 'top/', + 'top/foo/', + 'top/foo/file.tmp', 'test.php', 'toto/', 'toto/.git/', diff --git a/src/Symfony/Component/Finder/Tests/Iterator/SizeRangeFilterIteratorTest.php b/src/Symfony/Component/Finder/Tests/Iterator/SizeRangeFilterIteratorTest.php index e5f3b6a1ddebb..3e7c088e2fcdc 100644 --- a/src/Symfony/Component/Finder/Tests/Iterator/SizeRangeFilterIteratorTest.php +++ b/src/Symfony/Component/Finder/Tests/Iterator/SizeRangeFilterIteratorTest.php @@ -36,6 +36,8 @@ public static function getAcceptData() 'foo', 'qux', 'test.php', + 'top', + 'top/foo', 'toto', 'toto/.git', ]; diff --git a/src/Symfony/Component/Finder/Tests/Iterator/SortableIteratorTest.php b/src/Symfony/Component/Finder/Tests/Iterator/SortableIteratorTest.php index 32b1a396f8439..38e383c0c4f15 100644 --- a/src/Symfony/Component/Finder/Tests/Iterator/SortableIteratorTest.php +++ b/src/Symfony/Component/Finder/Tests/Iterator/SortableIteratorTest.php @@ -91,6 +91,9 @@ public static function getAcceptData() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'zebulon.php', @@ -101,6 +104,8 @@ public static function getAcceptData() '.git', 'foo', 'qux', + 'top', + 'top/foo', 'toto', 'toto/.git', '.bar', @@ -119,6 +124,7 @@ public static function getAcceptData() 'qux_2_0.php', 'test.php', 'test.py', + 'top/foo/file.tmp', 'zebulon.php', ]; @@ -134,6 +140,9 @@ public static function getAcceptData() 'test.py', 'Zephire.php', 'foo', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'foo bar', @@ -162,6 +171,9 @@ public static function getAcceptData() 'Zephire.php', 'foo', 'foo/bar.tmp', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'foo bar', @@ -190,6 +202,9 @@ public static function getAcceptData() 'Zephire.php', 'foo', 'foo/bar.tmp', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'foo bar', @@ -229,6 +244,9 @@ public static function getAcceptData() 'qux_1002_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'zebulon.php', @@ -255,6 +273,9 @@ public static function getAcceptData() 'qux_2_0.php', 'test.php', 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', 'toto', 'toto/.git', 'zebulon.php', From cc4352071378233fcbc91b65d7a7bd01aefefd96 Mon Sep 17 00:00:00 2001 From: Phil Davis Date: Sat, 27 Apr 2024 22:11:51 +0545 Subject: [PATCH 2/6] docs(Finder): add more comments about finder exclude --- src/Symfony/Component/Finder/Finder.php | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/Symfony/Component/Finder/Finder.php b/src/Symfony/Component/Finder/Finder.php index 80bf6a793f2ae..3c18c94669fe5 100644 --- a/src/Symfony/Component/Finder/Finder.php +++ b/src/Symfony/Component/Finder/Finder.php @@ -320,6 +320,10 @@ public function size(string|int|array $sizes): static * * $finder->in(__DIR__)->exclude('ruby'); * + * If the directory is preceded by '/' then it is only excluded at the top level. For example: + * + * $finder->in(__DIR__)->exclude('/vendor'); + * * @param string|array $dirs A directory path or an array of directories * * @return $this From 35210cfff4422b78c20cb5d8ec14a05fd1e9651d Mon Sep 17 00:00:00 2001 From: Phil Davis Date: Sat, 27 Apr 2024 22:12:35 +0545 Subject: [PATCH 3/6] test(Finder): add test for root-level finder exclude --- .../Component/Finder/Tests/FinderTest.php | 26 +++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/src/Symfony/Component/Finder/Tests/FinderTest.php b/src/Symfony/Component/Finder/Tests/FinderTest.php index f4822473fa040..c90b31d4c4d55 100644 --- a/src/Symfony/Component/Finder/Tests/FinderTest.php +++ b/src/Symfony/Component/Finder/Tests/FinderTest.php @@ -379,6 +379,32 @@ public function testExclude() ]), $finder->in(self::$tmpDir)->getIterator()); } + public function testExcludeTopLevelOnly() + { + $finder = $this->buildFinder(); + $this->assertSame($finder, $finder->exclude('/foo')); + $this->assertIterator($this->toAbsolute([ + 'test.php', + 'test.py', + 'top', + 'top/foo', + 'top/foo/file.tmp', + 'toto', + 'foo bar', + 'qux', + 'qux/baz_100_1.py', + 'zebulon.php', + 'Zephire.php', + 'qux/baz_1_2.py', + 'qux_0_1.php', + 'qux_1000_1.php', + 'qux_1002_0.php', + 'qux_10_2.php', + 'qux_12_0.php', + 'qux_2_0.php', + ]), $finder->in(self::$tmpDir)->getIterator()); + } + public function testIgnoreVCS() { $finder = $this->buildFinder(); From cf6121ea5819f0502d2db2cf90841b9d880ab30f Mon Sep 17 00:00:00 2001 From: Josh Date: Fri, 26 Apr 2024 17:01:03 -0400 Subject: [PATCH 4/6] fix(Finder): ExcludeDirectoryFilterIterator relative to "root" if `/` Fixes #28158 Fixes #47431 Related: #26396 Related: #9158 Related: #28410 --- .../ExcludeDirectoryFilterIterator.php | 24 +++++++++++++++---- 1 file changed, 20 insertions(+), 4 deletions(-) diff --git a/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php b/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php index ebbc76ec7bc46..3d08d5c2d6657 100644 --- a/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php +++ b/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php @@ -30,6 +30,7 @@ class ExcludeDirectoryFilterIterator extends \FilterIterator implements \Recursi /** @var array */ private array $excludedDirs = []; private ?string $excludedPattern = null; + private ?string $excludedPatternAbsolute = null; /** @var list */ private array $pruneFilters = []; @@ -42,6 +43,7 @@ public function __construct(\Iterator $iterator, array $directories) $this->iterator = $iterator; $this->isRecursive = $iterator instanceof \RecursiveIterator; $patterns = []; + $patternsAbsolute = []; foreach ($directories as $directory) { if (!\is_string($directory)) { if (!\is_callable($directory)) { @@ -54,7 +56,13 @@ public function __construct(\Iterator $iterator, array $directories) } $directory = rtrim($directory, '/'); - if (!$this->isRecursive || str_contains($directory, '/')) { + $slashPos = strpos($directory, '/'); + if (false !== $slashPos && \strlen($directory) - 1 !== $slashPos) { + if (0 === $slashPos) { + $directory = substr($directory, 1); + } + $patternsAbsolute[] = preg_quote($directory, '#'); + } elseif (!$this->isRecursive || str_contains($directory, '/')) { $patterns[] = preg_quote($directory, '#'); } else { $this->excludedDirs[$directory] = true; @@ -64,6 +72,10 @@ public function __construct(\Iterator $iterator, array $directories) $this->excludedPattern = '#(?:^|/)(?:'.implode('|', $patterns).')(?:/|$)#'; } + if ($patternsAbsolute) { + $this->excludedPatternAbsolute = '#^('.implode('|', $patternsAbsolute).')$#'; + } + parent::__construct($iterator); } @@ -76,11 +88,15 @@ public function accept(): bool return false; } - if ($this->excludedPattern) { + if ($this->excludedPattern || $this->excludedPatternAbsolute) { $path = $this->isDir() ? $this->current()->getRelativePathname() : $this->current()->getRelativePath(); $path = str_replace('\\', '/', $path); - - return !preg_match($this->excludedPattern, $path); + } + if ($this->excludedPattern && preg_match($this->excludedPattern, $path)) { + return false; + } + if ($this->excludedPatternAbsolute && preg_match($this->excludedPatternAbsolute, $path)) { + return false; } if ($this->pruneFilters && $this->hasChildren()) { From f429cf68eb832af0caf75591d54b3a82985f106e Mon Sep 17 00:00:00 2001 From: Josh Richards Date: Wed, 8 May 2024 16:40:25 -0400 Subject: [PATCH 5/6] coding standards update Signed-off-by: Josh Richards --- .../Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php b/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php index 3d08d5c2d6657..069eab8a54c78 100644 --- a/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php +++ b/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php @@ -92,6 +92,7 @@ public function accept(): bool $path = $this->isDir() ? $this->current()->getRelativePathname() : $this->current()->getRelativePath(); $path = str_replace('\\', '/', $path); } + if ($this->excludedPattern && preg_match($this->excludedPattern, $path)) { return false; } From f1849f0afd26380bd67d9efbc55fa8ae4104a784 Mon Sep 17 00:00:00 2001 From: Josh Date: Mon, 29 Apr 2024 10:49:58 -0400 Subject: [PATCH 6/6] Spacing Co-authored-by: Oskar Stark --- .../Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php b/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php index 069eab8a54c78..9b92f5763cd12 100644 --- a/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php +++ b/src/Symfony/Component/Finder/Iterator/ExcludeDirectoryFilterIterator.php @@ -96,6 +96,7 @@ public function accept(): bool if ($this->excludedPattern && preg_match($this->excludedPattern, $path)) { return false; } + if ($this->excludedPatternAbsolute && preg_match($this->excludedPatternAbsolute, $path)) { return false; }