1 | <?php |
||
16 | abstract class FileLoader extends Loader |
||
17 | { |
||
18 | /** @var array to track circular references */ |
||
19 | protected static $loading = []; |
||
20 | |||
21 | /** @var FileLocatorInterface */ |
||
22 | private $locator; |
||
23 | /** @var string */ |
||
24 | private $currentDir; |
||
25 | |||
26 | 8 | public function __construct(FileLocatorInterface $locator) |
|
30 | |||
31 | /** |
||
32 | * @param string $currentDir |
||
33 | */ |
||
34 | 8 | public function setCurrentDir($currentDir) |
|
35 | { |
||
36 | 8 | $this->currentDir = $currentDir; |
|
37 | 8 | } |
|
38 | |||
39 | /** |
||
40 | * Imports a resource. |
||
41 | * |
||
42 | * @param mixed $resource A Resource |
||
43 | * @param string|null $type The resource type or null if unknown |
||
44 | * @param bool $ignoreErrors Whether to ignore import errors or not |
||
45 | * @param string|null $sourceResource The original resource importing the new resource |
||
46 | * |
||
47 | * @return mixed |
||
48 | * @throws FileLoaderException |
||
49 | */ |
||
50 | 8 | public function import($resource, $type = null, $ignoreErrors = false, $sourceResource = null) |
|
51 | { |
||
52 | try { |
||
53 | 8 | $loader = $this->resolve($resource, $type); |
|
54 | |||
55 | 8 | if ($loader instanceof self && null !== $this->currentDir) { |
|
56 | $resource = $loader->getLocator()->locate($resource, $this->currentDir, false); |
||
57 | } |
||
58 | |||
59 | 8 | $resources = is_array($resource) ? $resource : [$resource]; |
|
60 | 8 | for ($i = 0; $i < $resourcesCount = count($resources); ++$i) { |
|
61 | 8 | if (isset(self::$loading[$resources[$i]])) { |
|
62 | if ($i == $resourcesCount - 1) { |
||
63 | throw CircularReferenceLoaderException::fromPaths(array_keys(self::$loading)); |
||
64 | } |
||
65 | } else { |
||
66 | 8 | $resource = $resources[$i]; |
|
67 | 8 | break; |
|
68 | } |
||
69 | } |
||
70 | 8 | self::$loading[$resource] = true; |
|
71 | |||
72 | try { |
||
73 | 8 | $ret = $loader->load($resource, $type); |
|
74 | 8 | } finally { |
|
75 | 8 | unset(self::$loading[$resource]); |
|
76 | } |
||
77 | |||
78 | 8 | return $ret; |
|
79 | } catch (CircularReferenceLoaderException $e) { |
||
80 | throw $e; |
||
81 | } catch (\Exception $e) { |
||
82 | if (!$ignoreErrors) { |
||
83 | // prevent embedded imports from nesting multiple exceptions |
||
84 | if ($e instanceof FileLoaderException) { |
||
85 | throw $e; |
||
86 | } |
||
87 | |||
88 | throw new FileLoaderLoadException($resource, $sourceResource, null, $e); |
||
89 | } |
||
90 | } |
||
91 | |||
92 | return null; |
||
93 | } |
||
94 | |||
95 | /** |
||
96 | * @return FileLocatorInterface |
||
97 | */ |
||
98 | 8 | public function getLocator() |
|
102 | } |
||
103 |