forked from rectorphp/rector
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathscoper.php
134 lines (108 loc) · 5.4 KB
/
scoper.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
<?php
declare(strict_types=1);
use Nette\Utils\DateTime;
use Nette\Utils\Strings;
use Rector\Compiler\PhpScoper\StaticEasyPrefixer;
use Rector\Compiler\Unprefixer;
use Rector\Compiler\ValueObject\ScoperOption;
require_once __DIR__ . '/vendor/autoload.php';
// [BEWARE] this path is relative to the root and location of this file
$filePathsToRemoveNamespace = [
// @see https://github.com/rectorphp/rector/issues/2852#issuecomment-586315588
'vendor/symfony/deprecation-contracts/function.php',
// it would make polyfill function work only with namespace = brokes
'vendor/symfony/polyfill-ctype/bootstrap.php',
'vendor/symfony/polyfill-intl-normalizer/bootstrap.php',
'vendor/symfony/polyfill-intl-grapheme/bootstrap.php',
'vendor/symfony/polyfill-mbstring/bootstrap.php',
'vendor/symfony/polyfill-php80/bootstrap.php',
'vendor/symfony/polyfill-php74/bootstrap.php',
'vendor/symfony/polyfill-php73/bootstrap.php',
'vendor/symfony/polyfill-php72/bootstrap.php',
'vendor/symfony/polyfill-uuid/bootstrap.php',
];
// remove phpstan, because it is already prefixed in its own scope
$dateTime = DateTime::from('now');
$timestamp = $dateTime->format('Ymd');
// see https://github.com/humbug/php-scoper
return [
ScoperOption::PREFIX => 'RectorPrefix' . $timestamp,
ScoperOption::WHITELIST => StaticEasyPrefixer::getExcludedNamespacesAndClasses(),
ScoperOption::PATCHERS => [
// [BEWARE] $filePath is absolute!
// fixes https://github.com/rectorphp/rector-prefixed/runs/2143717534
function (string $filePath, string $prefix, string $content) use ($filePathsToRemoveNamespace): string {
// @see https://regex101.com/r/0jaVB1/1
$prefixedNamespacePattern = '#^namespace (.*?);$#m';
foreach ($filePathsToRemoveNamespace as $filePathToRemoveNamespace) {
if (Strings::endsWith($filePath, $filePathToRemoveNamespace)) {
return Strings::replace($content, $prefixedNamespacePattern, '');
}
}
return $content;
},
// fixes https://github.com/rectorphp/rector-prefixed/runs/2103759172
// and https://github.com/rectorphp/rector-prefixed/blob/0cc433e746b645df5f905fa038573c3a1a9634f0/vendor/jean85/pretty-package-versions/src/PrettyVersions.php#L6
function (string $filePath, string $prefix, string $content): string {
if (! Strings::endsWith($filePath, 'vendor/jean85/pretty-package-versions/src/PrettyVersions.php')) {
return $content;
}
// see https://regex101.com/r/v8zRMm/1
return Strings::replace($content, '#' . $prefix . '\\\\Composer\\\\InstalledVersions#', 'Composer\InstalledVersions');
},
// fixes https://github.com/rectorphp/rector/issues/6007
function (string $filePath, string $prefix, string $content): string {
if (! Strings::contains($filePath, 'vendor/')) {
return $content;
}
// @see https://regex101.com/r/lBV8IO/2
$fqcnReservedPattern = sprintf('#(\\\\)?%s\\\\(parent|self|static)#m', $prefix);
$matches = Strings::matchAll($content, $fqcnReservedPattern);
if (! $matches) {
return $content;
}
foreach ($matches as $match) {
$content = str_replace($match[0], $match[2], $content);
}
return $content;
},
// fixes https://github.com/rectorphp/rector/issues/6010
function (string $filePath, string $prefix, string $content): string {
// @see https://regex101.com/r/bA1nQa/1
if (! Strings::match($filePath, '#vendor/symfony/polyfill-php\d{2}/Resources/stubs#')) {
return $content;
}
// @see https://regex101.com/r/x5Ukrx/1
$namespace = sprintf('#namespace %s;#m', $prefix);
return Strings::replace($content, $namespace);
},
// unprefix string classes, as they're string on purpose - they have to be checked in original form, not prefixed
function (string $filePath, string $prefix, string $content): string {
// skip vendor, expect rector packages
if (Strings::contains($filePath, 'vendor/') && ! Strings::contains($filePath, 'vendor/rector')) {
return $content;
}
// skip bin/rector.php for composer autoload class
if (Strings::endsWith($filePath, 'bin/rector.php')) {
return $content;
}
// skip scoper-autoload
if (Strings::endsWith($filePath, 'vendor/scoper-autoload.php')) {
return $content;
}
return Unprefixer::unprefixQuoted($content, $prefix);
},
// scoper missed PSR-4 autodiscovery in Symfony
function (string $filePath, string $prefix, string $content): string {
// scoper missed PSR-4 autodiscovery in Symfony
if (! Strings::endsWith($filePath, 'config.php') && ! Strings::endsWith($filePath, 'services.php')) {
return $content;
}
// skip "Rector\\" namespace
if (Strings::contains($content, '$services->load(\'Rector')) {
return $content;
}
return Strings::replace($content, '#services\->load\(\'#', 'services->load(\'' . $prefix . '\\');
},
],
];