Mercurial > hg > isophonics-drupal-site
comparison vendor/symfony/dependency-injection/Loader/FileLoader.php @ 14:1fec387a4317
Update Drupal core to 8.5.2 via Composer
author | Chris Cannam |
---|---|
date | Mon, 23 Apr 2018 09:46:53 +0100 |
parents | 4c8ae668cc8c |
children | 129ea1e6d783 |
comparison
equal
deleted
inserted
replaced
13:5fb285c0d0e3 | 14:1fec387a4317 |
---|---|
9 * file that was distributed with this source code. | 9 * file that was distributed with this source code. |
10 */ | 10 */ |
11 | 11 |
12 namespace Symfony\Component\DependencyInjection\Loader; | 12 namespace Symfony\Component\DependencyInjection\Loader; |
13 | 13 |
14 use Symfony\Component\DependencyInjection\ChildDefinition; | |
14 use Symfony\Component\DependencyInjection\ContainerBuilder; | 15 use Symfony\Component\DependencyInjection\ContainerBuilder; |
16 use Symfony\Component\DependencyInjection\Definition; | |
17 use Symfony\Component\DependencyInjection\Exception\InvalidArgumentException; | |
15 use Symfony\Component\Config\Loader\FileLoader as BaseFileLoader; | 18 use Symfony\Component\Config\Loader\FileLoader as BaseFileLoader; |
16 use Symfony\Component\Config\FileLocatorInterface; | 19 use Symfony\Component\Config\FileLocatorInterface; |
20 use Symfony\Component\Config\Resource\GlobResource; | |
17 | 21 |
18 /** | 22 /** |
19 * FileLoader is the abstract class used by all built-in loaders that are file based. | 23 * FileLoader is the abstract class used by all built-in loaders that are file based. |
20 * | 24 * |
21 * @author Fabien Potencier <fabien@symfony.com> | 25 * @author Fabien Potencier <fabien@symfony.com> |
22 */ | 26 */ |
23 abstract class FileLoader extends BaseFileLoader | 27 abstract class FileLoader extends BaseFileLoader |
24 { | 28 { |
25 protected $container; | 29 protected $container; |
30 protected $isLoadingInstanceof = false; | |
31 protected $instanceof = array(); | |
26 | 32 |
27 /** | |
28 * @param ContainerBuilder $container A ContainerBuilder instance | |
29 * @param FileLocatorInterface $locator A FileLocator instance | |
30 */ | |
31 public function __construct(ContainerBuilder $container, FileLocatorInterface $locator) | 33 public function __construct(ContainerBuilder $container, FileLocatorInterface $locator) |
32 { | 34 { |
33 $this->container = $container; | 35 $this->container = $container; |
34 | 36 |
35 parent::__construct($locator); | 37 parent::__construct($locator); |
36 } | 38 } |
39 | |
40 /** | |
41 * Registers a set of classes as services using PSR-4 for discovery. | |
42 * | |
43 * @param Definition $prototype A definition to use as template | |
44 * @param string $namespace The namespace prefix of classes in the scanned directory | |
45 * @param string $resource The directory to look for classes, glob-patterns allowed | |
46 * @param string $exclude A globed path of files to exclude | |
47 */ | |
48 public function registerClasses(Definition $prototype, $namespace, $resource, $exclude = null) | |
49 { | |
50 if ('\\' !== substr($namespace, -1)) { | |
51 throw new InvalidArgumentException(sprintf('Namespace prefix must end with a "\\": %s.', $namespace)); | |
52 } | |
53 if (!preg_match('/^(?:[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*+\\\\)++$/', $namespace)) { | |
54 throw new InvalidArgumentException(sprintf('Namespace is not a valid PSR-4 prefix: %s.', $namespace)); | |
55 } | |
56 | |
57 $classes = $this->findClasses($namespace, $resource, $exclude); | |
58 // prepare for deep cloning | |
59 $serializedPrototype = serialize($prototype); | |
60 $interfaces = array(); | |
61 $singlyImplemented = array(); | |
62 | |
63 foreach ($classes as $class => $errorMessage) { | |
64 if (interface_exists($class, false)) { | |
65 $interfaces[] = $class; | |
66 } else { | |
67 $this->setDefinition($class, $definition = unserialize($serializedPrototype)); | |
68 if (null !== $errorMessage) { | |
69 $definition->addError($errorMessage); | |
70 | |
71 continue; | |
72 } | |
73 foreach (class_implements($class, false) as $interface) { | |
74 $singlyImplemented[$interface] = isset($singlyImplemented[$interface]) ? false : $class; | |
75 } | |
76 } | |
77 } | |
78 foreach ($interfaces as $interface) { | |
79 if (!empty($singlyImplemented[$interface])) { | |
80 $this->container->setAlias($interface, $singlyImplemented[$interface]) | |
81 ->setPublic(false); | |
82 } | |
83 } | |
84 } | |
85 | |
86 /** | |
87 * Registers a definition in the container with its instanceof-conditionals. | |
88 * | |
89 * @param string $id | |
90 * @param Definition $definition | |
91 */ | |
92 protected function setDefinition($id, Definition $definition) | |
93 { | |
94 if ($this->isLoadingInstanceof) { | |
95 if (!$definition instanceof ChildDefinition) { | |
96 throw new InvalidArgumentException(sprintf('Invalid type definition "%s": ChildDefinition expected, "%s" given.', $id, get_class($definition))); | |
97 } | |
98 $this->instanceof[$id] = $definition; | |
99 } else { | |
100 $this->container->setDefinition($id, $definition instanceof ChildDefinition ? $definition : $definition->setInstanceofConditionals($this->instanceof)); | |
101 } | |
102 } | |
103 | |
104 private function findClasses($namespace, $pattern, $excludePattern) | |
105 { | |
106 $parameterBag = $this->container->getParameterBag(); | |
107 | |
108 $excludePaths = array(); | |
109 $excludePrefix = null; | |
110 if ($excludePattern) { | |
111 $excludePattern = $parameterBag->unescapeValue($parameterBag->resolveValue($excludePattern)); | |
112 foreach ($this->glob($excludePattern, true, $resource) as $path => $info) { | |
113 if (null === $excludePrefix) { | |
114 $excludePrefix = $resource->getPrefix(); | |
115 } | |
116 | |
117 // normalize Windows slashes | |
118 $excludePaths[str_replace('\\', '/', $path)] = true; | |
119 } | |
120 } | |
121 | |
122 $pattern = $parameterBag->unescapeValue($parameterBag->resolveValue($pattern)); | |
123 $classes = array(); | |
124 $extRegexp = defined('HHVM_VERSION') ? '/\\.(?:php|hh)$/' : '/\\.php$/'; | |
125 $prefixLen = null; | |
126 foreach ($this->glob($pattern, true, $resource) as $path => $info) { | |
127 if (null === $prefixLen) { | |
128 $prefixLen = strlen($resource->getPrefix()); | |
129 | |
130 if ($excludePrefix && 0 !== strpos($excludePrefix, $resource->getPrefix())) { | |
131 throw new InvalidArgumentException(sprintf('Invalid "exclude" pattern when importing classes for "%s": make sure your "exclude" pattern (%s) is a subset of the "resource" pattern (%s)', $namespace, $excludePattern, $pattern)); | |
132 } | |
133 } | |
134 | |
135 if (isset($excludePaths[str_replace('\\', '/', $path)])) { | |
136 continue; | |
137 } | |
138 | |
139 if (!preg_match($extRegexp, $path, $m) || !$info->isReadable()) { | |
140 continue; | |
141 } | |
142 $class = $namespace.ltrim(str_replace('/', '\\', substr($path, $prefixLen, -strlen($m[0]))), '\\'); | |
143 | |
144 if (!preg_match('/^[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*+(?:\\\\[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*+)*+$/', $class)) { | |
145 continue; | |
146 } | |
147 | |
148 try { | |
149 $r = $this->container->getReflectionClass($class); | |
150 } catch (\ReflectionException $e) { | |
151 $classes[$class] = sprintf( | |
152 'While discovering services from namespace "%s", an error was thrown when processing the class "%s": "%s".', | |
153 $namespace, | |
154 $class, | |
155 $e->getMessage() | |
156 ); | |
157 continue; | |
158 } | |
159 // check to make sure the expected class exists | |
160 if (!$r) { | |
161 throw new InvalidArgumentException(sprintf('Expected to find class "%s" in file "%s" while importing services from resource "%s", but it was not found! Check the namespace prefix used with the resource.', $class, $path, $pattern)); | |
162 } | |
163 | |
164 if ($r->isInstantiable() || $r->isInterface()) { | |
165 $classes[$class] = null; | |
166 } | |
167 } | |
168 | |
169 // track only for new & removed files | |
170 if ($resource instanceof GlobResource) { | |
171 $this->container->addResource($resource); | |
172 } else { | |
173 foreach ($resource as $path) { | |
174 $this->container->fileExists($path, false); | |
175 } | |
176 } | |
177 | |
178 return $classes; | |
179 } | |
37 } | 180 } |