Passed
Pull Request — master (#60)
by Ondřej
02:41
created

provideExcludePattern()   B

Complexity

Conditions 1
Paths 1

Size

Total Lines 36
Code Lines 22

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 36
rs 8.8571
c 0
b 0
f 0
cc 1
eloc 22
nc 1
nop 0
1
<?php
2
3
namespace ComposerRequireCheckerTest\FileLocator;
4
5
use ComposerRequireChecker\FileLocator\LocateComposerPackageSourceFiles;
6
use org\bovigo\vfs\vfsStream;
7
use org\bovigo\vfs\vfsStreamDirectory;
8
use PHPUnit\Framework\TestCase;
9
10
/**
11
 * @covers \ComposerRequireChecker\FileLocator\LocateComposerPackageSourceFiles
12
 */
13
class LocateComposerPackageSourceFilesTest extends TestCase
14
{
15
    /** @var LocateComposerPackageSourceFiles */
16
    private $locator;
17
    /** @var vfsStreamDirectory */
18
    private $root;
19
20
    protected function setUp()
21
    {
22
        parent::setUp();
23
24
        $this->locator = new LocateComposerPackageSourceFiles();
25
        $this->root = vfsStream::setup();
26
    }
27
28
    public function testFromClassmap()
29
    {
30
        vfsStream::create([
31
            'composer.json' => '{"autoload": {"classmap": ["src/MyClassA.php", "MyClassB.php"]}}',
32
            'src' => [
33
                'MyClassA.php' => '<?php class MyClassA {}',
34
            ],
35
            'MyClassB.php' => '<?php class MyClassB {}',
36
        ]);
37
38
        $files = $this->files($this->root->getChild('composer.json')->url());
39
40
        $this->assertCount(2, $files);
41
        $this->assertContains($this->root->getChild('src/MyClassA.php')->url(), $files);
42
        $this->assertContains($this->root->getChild('MyClassB.php')->url(), $files);
43
    }
44
45
    public function testFromFiles()
46
    {
47
        vfsStream::create([
48
            'composer.json' => '{"autoload": {"files": ["foo.php"]}}',
49
            'foo.php' => '<?php class MyClass {}',
50
        ]);
51
52
        $files = $this->files($this->root->getChild('composer.json')->url());
53
54
        $this->assertCount(1, $files);
55
        $this->assertContains($this->root->getChild('foo.php')->url(), $files);
56
    }
57
58
    public function testFromPsr0()
59
    {
60
        vfsStream::create([
61
            'composer.json' => '{"autoload": {"psr-0": ["src"]}}',
62
            'src' => [
63
                'MyNamespace' => [
64
                    'MyClass.php' => '<?php namespace MyNamespace; class MyClass {}',
65
                ],
66
            ],
67
        ]);
68
69
        $files = $this->files($this->root->getChild('composer.json')->url());
70
71
        $this->assertCount(1, $files);
72
    }
73
74
    public function testFromPsr4()
75
    {
76
        vfsStream::create([
77
            'composer.json' => '{"autoload": {"psr-4": {"MyNamespace\\\\": "src"}}}',
78
            'src' => [
79
                'MyClass.php' => '<?php namespace MyNamespace; class MyClass {}',
80
            ],
81
        ]);
82
83
        $files = $this->files($this->root->getChild('composer.json')->url());
84
85
        $this->assertCount(1, $files);
86
    }
87
88
    public function testFromPsr0WithMultipleDirectories()
89
    {
90
        vfsStream::create([
91
            'composer.json' => '{"autoload": {"psr-0": {"MyNamespace\\\\": ["src", "lib"]}}}',
92
            'src' => ['MyNamespace' => ['MyClassA.php' => '<?php namespace MyNamespace; class MyClassA {}']],
93
            'lib' => ['MyNamespace' => ['MyClassB.php' => '<?php namespace MyNamespace; class MyClassB {}']],
94
        ]);
95
96
        $files = $this->files($this->root->getChild('composer.json')->url());
97
98
        $this->assertCount(2, $files);
99
        $this->assertContains($this->root->getChild('src/MyNamespace/MyClassA.php')->url(), $files);
100
        $this->assertContains($this->root->getChild('lib/MyNamespace/MyClassB.php')->url(), $files);
101
    }
102
103
    public function testFromPsr4WithMultipleDirectories()
104
    {
105
        vfsStream::create([
106
            'composer.json' => '{"autoload": {"psr-4": {"MyNamespace\\\\": ["src", "lib"]}}}',
107
            'src' => ['MyClassA.php' => '<?php namespace MyNamespace; class MyClassA {}'],
108
            'lib' => ['MyClassB.php' => '<?php namespace MyNamespace; class MyClassB {}'],
109
        ]);
110
111
        $files = $this->files($this->root->getChild('composer.json')->url());
112
113
        $this->assertCount(2, $files);
114
        $this->assertContains($this->root->getChild('src/MyClassA.php')->url(), $files);
115
        $this->assertContains($this->root->getChild('lib/MyClassB.php')->url(), $files);
116
    }
117
118
    public function testFromPsr4WithNestedDirectory()
119
    {
120
        vfsStream::create([
121
            'composer.json' => '{"autoload": {"psr-4": {"MyNamespace\\\\": ["src/MyNamespace"]}}}',
122
            'src' => [
123
                'MyNamespace' => ['MyClassA.php' => '<?php namespace MyNamespace; class MyClassA {}']
124
            ],
125
        ]);
126
127
        $files = $this->files($this->root->getChild('composer.json')->url());
128
129
        $this->assertCount(1, $files);
130
        $this->assertContains($this->root->getChild('src/MyNamespace/MyClassA.php')->url(), $files);
131
    }
132
133
    public function testFromPsr4WithNestedDirectoryAlternativeDirectorySeparator()
134
    {
135
        vfsStream::create([
136
            'composer.json' => '{"autoload": {"psr-4": {"MyNamespace\\\\": ["src\\\\MyNamespace"]}}}',
137
            'src' => [
138
                'MyNamespace' => ['MyClassA.php' => '<?php namespace MyNamespace; class MyClassA {}']
139
            ],
140
        ]);
141
142
        $files = $this->files($this->root->getChild('composer.json')->url());
143
144
        $this->assertCount(1, $files);
145
        $this->assertContains($this->root->getChild('src/MyNamespace/MyClassA.php')->url(), $files);
146
    }
147
148
    /**
149
     * @dataProvider provideExcludePattern
150
     */
151
    public function testFromPsr4WithExcludeFromClassmap(array $excludedPattern, array $expectedFiles)
152
    {
153
        $excludedPatternJson = json_encode($excludedPattern);
154
155
        vfsStream::create([
156
            'composer.json' => '{"autoload": {"psr-4": {"MyNamespace\\\\": ""}, "exclude-from-classmap": ' . $excludedPatternJson . '}}',
157
            'ClassA.php' => '<?php namespace MyNamespace; class ClassA {}',
158
            'tests' => [
159
                'ATest.php' => '<?php namespace MyNamespace; class ATest {}',
160
            ],
161
            'foo' => [
162
                'Tests' => [
163
                    'BTest.php' => '<?php namespace MyNamespace; class BTest {}',
164
                ],
165
                'src' => [
166
                    'ClassB.php' => '<?php namespace MyNamespace; class ClassB {}',
167
                    'Tests' => [
168
                        'CTest.php' => '<?php namespace MyNamespace; class CTest {}',
169
                    ],
170
                ],
171
            ],
172
        ]);
173
174
        $files = $this->files($this->root->getChild('composer.json')->url());
175
176
        $this->assertCount(count($expectedFiles), $files);
177
        foreach ($expectedFiles as $expectedFile) {
178
            $this->assertContains($this->root->getChild($expectedFile)->url(), $files);
179
        }
180
    }
181
182
    /**
183
     * @return array[]
184
     */
185
    public function provideExcludePattern(): array
186
    {
187
        return [
188
            'No exclude pattern' => [
189
                [],
190
                [
191
                    'ClassA.php',
192
                    'tests/ATest.php',
193
                    'foo/Tests/BTest.php',
194
                    'foo/src/ClassB.php',
195
                    'foo/src/Tests/CTest.php',
196
197
                ],
198
            ],
199
            'Exclude single directory by pattern' => [
200
                ['/tests/'],
201
                [
202
                    'ClassA.php',
203
                    'foo/Tests/BTest.php',
204
                    'foo/src/ClassB.php',
205
                    'foo/src/Tests/CTest.php',
206
                ],
207
            ],
208
            'Exclude all subdirectories by pattern' => [
209
                ['/**Tests/'],
210
                [
211
                    'ClassA.php',
212
                    'tests/ATest.php',
213
                    'foo/src/ClassB.php',
214
                ],
215
            ],
216
            'Combine multiple patterns' => [
217
                ['/tests/', '/**Tests/'],
218
                [
219
                    'ClassA.php',
220
                    'foo/src/ClassB.php',
221
                ],
222
            ],
223
        ];
224
    }
225
226
    /**
227
     * @return string[]
228
     */
229
    private function files(string $composerJson): array
230
    {
231
        $files = [];
232
        $filesGenerator = ($this->locator)($composerJson);
233
        foreach ($filesGenerator as $file) {
234
            $files[] = $file;
235
        }
236
        return $files;
237
    }
238
}
239