diff vendor/doctrine/common/lib/Doctrine/Common/Proxy/ProxyGenerator.php @ 12:7a779792577d

Update Drupal core to v8.4.5 (via Composer)
author Chris Cannam
date Fri, 23 Feb 2018 15:52:07 +0000
parents 4c8ae668cc8c
children
line wrap: on
line diff
--- a/vendor/doctrine/common/lib/Doctrine/Common/Proxy/ProxyGenerator.php	Fri Feb 23 15:51:18 2018 +0000
+++ b/vendor/doctrine/common/lib/Doctrine/Common/Proxy/ProxyGenerator.php	Fri Feb 23 15:52:07 2018 +0000
@@ -37,7 +37,7 @@
      * Used to match very simple id methods that don't need
      * to be decorated since the identifier is known.
      */
-    const PATTERN_MATCH_ID_METHOD = '((public\s+)?(function\s+%s\s*\(\)\s*)\s*{\s*return\s*\$this->%s;\s*})i';
+    const PATTERN_MATCH_ID_METHOD = '((public\s+)?(function\s+%s\s*\(\)\s*)\s*(?::\s*\??\s*\\\\?[a-z_\x7f-\xff][\w\x7f-\xff]*(?:\\\\[a-z_\x7f-\xff][\w\x7f-\xff]*)*\s*)?{\s*return\s*\$this->%s;\s*})i';
 
     /**
      * The namespace that contains all proxy classes.
@@ -787,7 +787,9 @@
                 $cast       = in_array($fieldType, ['integer', 'smallint']) ? '(int) ' : '';
 
                 $methods .= '        if ($this->__isInitialized__ === false) {' . "\n";
-                $methods .= '            return ' . $cast . ' parent::' . $method->getName() . "();\n";
+                $methods .= '            ';
+                $methods .= $this->shouldProxiedMethodReturn($method) ? 'return ' : '';
+                $methods .= $cast . ' parent::' . $method->getName() . "();\n";
                 $methods .= '        }' . "\n\n";
             }
 
@@ -797,7 +799,9 @@
             $methods .= "\n        \$this->__initializer__ "
                 . "&& \$this->__initializer__->__invoke(\$this, " . var_export($name, true)
                 . ", [" . $invokeParamsString . "]);"
-                . "\n\n        return parent::" . $name . '(' . $callParamsString . ');'
+                . "\n\n        "
+                . ($this->shouldProxiedMethodReturn($method) ? 'return ' : '')
+                . "parent::" . $name . '(' . $callParamsString . ');'
                 . "\n" . '    }' . "\n";
         }
 
@@ -935,8 +939,15 @@
      */
     private function getParameterType(ClassMetadata $class, \ReflectionMethod $method, \ReflectionParameter $parameter)
     {
+        if (method_exists($parameter, 'hasType')) {
+            if ( ! $parameter->hasType()) {
+                return '';
+            }
 
-        // We need to pick the type hint class too
+            return $this->formatType($parameter->getType(), $parameter->getDeclaringFunction(), $parameter);
+        }
+
+        // For PHP 5.x, we need to pick the type hint in the old way (to be removed for PHP 7.0+)
         if ($parameter->isArray()) {
             return 'array';
         }
@@ -945,10 +956,6 @@
             return 'callable';
         }
 
-        if (method_exists($parameter, 'hasType') && $parameter->hasType() && $parameter->getType()->isBuiltin()) {
-            return (string) $parameter->getType();
-        }
-
         try {
             $parameterClass = $parameter->getClass();
 
@@ -1012,26 +1019,75 @@
      */
     private function getMethodReturnType(\ReflectionMethod $method)
     {
-        if (! (method_exists($method, 'hasReturnType') && $method->hasReturnType())) {
+        if ( ! method_exists($method, 'hasReturnType') || ! $method->hasReturnType()) {
             return '';
         }
 
-        $returnType = $method->getReturnType();
+        return ': ' . $this->formatType($method->getReturnType(), $method);
+    }
 
-        if ($returnType->isBuiltin()) {
-            return ': ' . $returnType;
+    /**
+     * @param \ReflectionMethod $method
+     *
+     * @return bool
+     */
+    private function shouldProxiedMethodReturn(\ReflectionMethod $method)
+    {
+        if ( ! method_exists($method, 'hasReturnType') || ! $method->hasReturnType()) {
+            return true;
         }
 
-        $nameLower = strtolower((string) $returnType);
+        return 'void' !== strtolower($this->formatType($method->getReturnType(), $method));
+    }
+
+    /**
+     * @param \ReflectionType $type
+     * @param \ReflectionMethod $method
+     * @param \ReflectionParameter|null $parameter
+     *
+     * @return string
+     */
+    private function formatType(
+        \ReflectionType $type,
+        \ReflectionMethod $method,
+        \ReflectionParameter $parameter = null
+    ) {
+        $name = method_exists($type, 'getName') ? $type->getName() : (string) $type;
+        $nameLower = strtolower($name);
 
         if ('self' === $nameLower) {
-            return ': \\' . $method->getDeclaringClass()->getName();
+            $name = $method->getDeclaringClass()->getName();
         }
 
         if ('parent' === $nameLower) {
-            return ': \\' . $method->getDeclaringClass()->getParentClass()->getName();
+            $name = $method->getDeclaringClass()->getParentClass()->getName();
         }
 
-        return ': \\' . (string) $returnType;
+        if ( ! $type->isBuiltin() && ! class_exists($name) && ! interface_exists($name)) {
+            if (null !== $parameter) {
+                throw UnexpectedValueException::invalidParameterTypeHint(
+                    $method->getDeclaringClass()->getName(),
+                    $method->getName(),
+                    $parameter->getName()
+                );
+            }
+
+            throw UnexpectedValueException::invalidReturnTypeHint(
+                $method->getDeclaringClass()->getName(),
+                $method->getName()
+            );
+        }
+
+        if ( ! $type->isBuiltin()) {
+            $name = '\\' . $name;
+        }
+
+        if ($type->allowsNull()
+            && (null === $parameter || ! $parameter->isDefaultValueAvailable() || null !== $parameter->getDefaultValue())
+        ) {
+            $name = '?' . $name;
+        }
+
+        return $name;
     }
 }