Upgrade 1-11.38

This commit is contained in:
xesmyd
2026-03-30 14:10:30 +02:00
parent f2a7e6d1fc
commit ac648ef29d
24665 changed files with 69682 additions and 2205004 deletions
+105 -22
View File
@@ -11,6 +11,10 @@
namespace Symfony\Component\Debug;
use PHPUnit\Framework\MockObject\Matcher\StatelessInvocation;
@trigger_error(sprintf('The "%s" class is deprecated since Symfony 4.4, use "%s" instead.', DebugClassLoader::class, \Symfony\Component\ErrorHandler\DebugClassLoader::class), \E_USER_DEPRECATED);
/**
* Autoloader checking if the class is really defined in the file found.
*
@@ -21,6 +25,9 @@ namespace Symfony\Component\Debug;
* @author Fabien Potencier <fabien@symfony.com>
* @author Christophe Coevoet <stof@notk.org>
* @author Nicolas Grekas <p@tchwork.com>
* @author Guilhem Niot <guilhem.niot@gmail.com>
*
* @deprecated since Symfony 4.4, use Symfony\Component\ErrorHandler\DebugClassLoader instead.
*/
class DebugClassLoader
{
@@ -34,8 +41,9 @@ class DebugClassLoader
private static $deprecated = [];
private static $internal = [];
private static $internalMethods = [];
private static $php7Reserved = ['int' => 1, 'float' => 1, 'bool' => 1, 'string' => 1, 'true' => 1, 'false' => 1, 'null' => 1];
private static $annotatedParameters = [];
private static $darwinCache = ['/' => ['/', []]];
private static $method = [];
public function __construct(callable $classLoader)
{
@@ -82,8 +90,8 @@ class DebugClassLoader
public static function enable()
{
// Ensures we don't hit https://bugs.php.net/42098
class_exists('Symfony\Component\Debug\ErrorHandler');
class_exists('Psr\Log\LogLevel');
class_exists(\Symfony\Component\Debug\ErrorHandler::class);
class_exists(\Psr\Log\LogLevel::class);
if (!\is_array($functions = spl_autoload_functions())) {
return;
@@ -156,7 +164,7 @@ class DebugClassLoader
return;
}
} else {
\call_user_func($this->classLoader, $class);
($this->classLoader)($class);
$file = false;
}
} finally {
@@ -166,7 +174,7 @@ class DebugClassLoader
$this->checkClass($class, $file);
}
private function checkClass($class, $file = null)
private function checkClass(string $class, string $file = null)
{
$exists = null === $file || class_exists($class, false) || interface_exists($class, false) || trait_exists($class, false);
@@ -192,10 +200,6 @@ class DebugClassLoader
$deprecations = $this->checkAnnotations($refl, $name);
if (isset(self::$php7Reserved[strtolower($refl->getShortName())])) {
$deprecations[] = sprintf('The "%s" class uses the reserved name "%s", it will break on PHP 7 and higher', $name, $refl->getShortName());
}
foreach ($deprecations as $message) {
@trigger_error($message, \E_USER_DEPRECATED);
}
@@ -237,10 +241,28 @@ class DebugClassLoader
self::${$annotation}[$class] = isset($notice[1]) ? preg_replace('#\.?\r?\n( \*)? *(?= |\r?\n|$)#', '', $notice[1]) : '';
}
}
if ($refl->isInterface() && false !== strpos($doc, 'method') && preg_match_all('#\n \* @method\s+(static\s+)?+(?:[\w\|&\[\]\\\]+\s+)?(\w+(?:\s*\([^\)]*\))?)+(.+?([[:punct:]]\s*)?)?(?=\r?\n \*(?: @|/$|\r?\n))#', $doc, $notice, \PREG_SET_ORDER)) {
foreach ($notice as $method) {
$static = '' !== $method[1];
$name = $method[2];
$description = $method[3] ?? null;
if (false === strpos($name, '(')) {
$name .= '()';
}
if (null !== $description) {
$description = trim($description);
if (!isset($method[4])) {
$description .= '.';
}
}
self::$method[$class][] = [$class, $name, $static, $description];
}
}
}
$parent = get_parent_class($class);
$parentAndOwnInterfaces = $this->getOwnInterfaces($class, $parent);
$parentAndOwnInterfaces = $this->getOwnInterfaces($class, $parent ?: null);
if ($parent) {
$parentAndOwnInterfaces[$parent] = $parent;
@@ -267,17 +289,40 @@ class DebugClassLoader
if (isset(self::$internal[$use]) && strncmp($ns, str_replace('_', '\\', $use), $len)) {
$deprecations[] = sprintf('The "%s" %s is considered internal%s. It may change without further notice. You should not use it from "%s".', $use, class_exists($use, false) ? 'class' : (interface_exists($use, false) ? 'interface' : 'trait'), self::$internal[$use], $class);
}
if (isset(self::$method[$use])) {
if ($refl->isAbstract()) {
if (isset(self::$method[$class])) {
self::$method[$class] = array_merge(self::$method[$class], self::$method[$use]);
} else {
self::$method[$class] = self::$method[$use];
}
} elseif (!$refl->isInterface()) {
$hasCall = $refl->hasMethod('__call');
$hasStaticCall = $refl->hasMethod('__callStatic');
foreach (self::$method[$use] as $method) {
[$interface, $name, $static, $description] = $method;
if ($static ? $hasStaticCall : $hasCall) {
continue;
}
$realName = substr($name, 0, strpos($name, '('));
if (!$refl->hasMethod($realName) || !($methodRefl = $refl->getMethod($realName))->isPublic() || ($static && !$methodRefl->isStatic()) || (!$static && $methodRefl->isStatic())) {
$deprecations[] = sprintf('Class "%s" should implement method "%s::%s"%s', $class, ($static ? 'static ' : '').$interface, $name, null == $description ? '.' : ': '.$description);
}
}
}
}
}
if (trait_exists($class)) {
return $deprecations;
}
// Inherit @final and @internal annotations for methods
// Inherit @final, @internal and @param annotations for methods
self::$finalMethods[$class] = [];
self::$internalMethods[$class] = [];
self::$annotatedParameters[$class] = [];
foreach ($parentAndOwnInterfaces as $use) {
foreach (['finalMethods', 'internalMethods'] as $property) {
foreach (['finalMethods', 'internalMethods', 'annotatedParameters'] as $property) {
if (isset(self::${$property}[$use])) {
self::${$property}[$class] = self::${$property}[$class] ? self::${$property}[$use] + self::${$property}[$class] : self::${$property}[$use];
}
@@ -290,26 +335,63 @@ class DebugClassLoader
}
if ($parent && isset(self::$finalMethods[$parent][$method->name])) {
list($declaringClass, $message) = self::$finalMethods[$parent][$method->name];
[$declaringClass, $message] = self::$finalMethods[$parent][$method->name];
$deprecations[] = sprintf('The "%s::%s()" method is considered final%s. It may change without further notice as of its next major version. You should not extend it from "%s".', $declaringClass, $method->name, $message, $class);
}
if (isset(self::$internalMethods[$class][$method->name])) {
list($declaringClass, $message) = self::$internalMethods[$class][$method->name];
[$declaringClass, $message] = self::$internalMethods[$class][$method->name];
if (strncmp($ns, $declaringClass, $len)) {
$deprecations[] = sprintf('The "%s::%s()" method is considered internal%s. It may change without further notice. You should not extend it from "%s".', $declaringClass, $method->name, $message, $class);
}
}
// Detect method annotations
if (false === $doc = $method->getDocComment()) {
// To read method annotations
$doc = $method->getDocComment();
if (isset(self::$annotatedParameters[$class][$method->name])) {
$definedParameters = [];
foreach ($method->getParameters() as $parameter) {
$definedParameters[$parameter->name] = true;
}
foreach (self::$annotatedParameters[$class][$method->name] as $parameterName => $deprecation) {
if (!isset($definedParameters[$parameterName]) && !($doc && preg_match("/\\n\\s+\\* @param +((?(?!callable *\().*?|callable *\(.*\).*?))(?<= )\\\${$parameterName}\\b/", $doc))) {
$deprecations[] = sprintf($deprecation, $class);
}
}
}
if (!$doc) {
continue;
}
$finalOrInternal = false;
foreach (['final', 'internal'] as $annotation) {
if (false !== strpos($doc, $annotation) && preg_match('#\n\s+\* @'.$annotation.'(?:( .+?)\.?)?\r?\n\s+\*(?: @|/$|\r?\n)#s', $doc, $notice)) {
$message = isset($notice[1]) ? preg_replace('#\.?\r?\n( \*)? *(?= |\r?\n|$)#', '', $notice[1]) : '';
self::${$annotation.'Methods'}[$class][$method->name] = [$class, $message];
$finalOrInternal = true;
}
}
if ($finalOrInternal || $method->isConstructor() || false === strpos($doc, '@param') || StatelessInvocation::class === $class) {
continue;
}
if (!preg_match_all('#\n\s+\* @param +((?(?!callable *\().*?|callable *\(.*\).*?))(?<= )\$([a-zA-Z0-9_\x7f-\xff]++)#', $doc, $matches, \PREG_SET_ORDER)) {
continue;
}
if (!isset(self::$annotatedParameters[$class][$method->name])) {
$definedParameters = [];
foreach ($method->getParameters() as $parameter) {
$definedParameters[$parameter->name] = true;
}
}
foreach ($matches as [, $parameterType, $parameterName]) {
if (!isset($definedParameters[$parameterName])) {
$parameterType = trim($parameterType);
self::$annotatedParameters[$class][$method->name][$parameterName] = sprintf('The "%%s::%s()" method will require a new "%s$%s" argument in the next major version of its %s "%s", not defining it is deprecated.', $method->name, $parameterType ? $parameterType.' ' : '', $parameterName, interface_exists($class) ? 'interface' : 'parent class', $method->class);
}
}
}
@@ -362,7 +444,7 @@ class DebugClassLoader
/**
* `realpath` on MacOSX doesn't normalize the case of characters.
*/
private function darwinRealpath($real)
private function darwinRealpath(string $real): string
{
$i = 1 + strrpos($real, '/');
$file = substr($real, $i);
@@ -377,7 +459,11 @@ class DebugClassLoader
$real = self::$darwinCache[$kDir][0];
} else {
$dir = getcwd();
chdir($real);
if (!@chdir($real)) {
return $real.$file;
}
$real = getcwd().'/';
chdir($dir);
@@ -429,12 +515,9 @@ class DebugClassLoader
/**
* `class_implements` includes interfaces from the parents so we have to manually exclude them.
*
* @param string $class
* @param string|false $parent
*
* @return string[]
*/
private function getOwnInterfaces($class, $parent)
private function getOwnInterfaces(string $class, ?string $parent): array
{
$ownInterfaces = class_implements($class, false);