PluginProbe
Yatra – Travel Booking & Tour Operator Software / 3.0.9
Yatra – Travel Booking & Tour Operator Software v3.0.9
3.0.15 3.0.14 3.0.14.1 3.0.14.2 3.0.12 3.0.13 3.0.11 3.0.10 3.0.9 3.0.8 3.0.7 3.0.6 3.0.5 3.0.5.1 3.0.4 3.0.3 3.0.2.9 3.0.2.7 3.0.2.8 3.0.2.6 trunk 1.0.0 2.0.0 2.0.1 2.0.10 All 83 releases
yatra / app / Core / Container.php

Container.php in Yatra – Travel Booking & Tour Operator Software 3.0.9, at app/Core/Container.php

122 lines 2.9 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 declare(strict_types=1);
4
5 namespace Yatra\Core;
6
7 /**
8 * Simple Dependency Injection Container
9 */
10 class Container
11 {
12 /**
13 * @var array
14 */
15 private array $bindings = [];
16
17 /**
18 * @var array
19 */
20 private array $instances = [];
21
22 /**
23 * Bind a class or closure to the container
24 */
25 public function bind(string $abstract, $concrete): void
26 {
27 $this->bindings[$abstract] = $concrete;
28 }
29
30 /**
31 * Bind a singleton instance
32 */
33 public function singleton(string $abstract, $concrete): void
34 {
35 $this->bind($abstract, $concrete);
36 $this->instances[$abstract] = null;
37 }
38
39 /**
40 * Resolve a class from the container
41 */
42 public function make(string $abstract)
43 {
44 // Return if already resolved as singleton
45 if (isset($this->instances[$abstract]) && $this->instances[$abstract] !== null) {
46 return $this->instances[$abstract];
47 }
48
49 // Get concrete implementation
50 $concrete = $this->bindings[$abstract] ?? $abstract;
51
52 // If concrete is a closure, call it
53 if (is_callable($concrete) && !is_string($concrete)) {
54 $instance = $concrete($this);
55 } else {
56 $instance = $this->build($concrete);
57 }
58
59 // Store singleton instance
60 if (isset($this->instances[$abstract])) {
61 $this->instances[$abstract] = $instance;
62 }
63
64 return $instance;
65 }
66
67 /**
68 * Build an instance of a class
69 */
70 private function build(string $class)
71 {
72 $reflection = new \ReflectionClass($class);
73
74 if (!$reflection->isInstantiable()) {
75 throw new \Exception("Class {$class} is not instantiable");
76 }
77
78 $constructor = $reflection->getConstructor();
79
80 if ($constructor === null) {
81 return new $class();
82 }
83
84 $parameters = $constructor->getParameters();
85 $dependencies = [];
86
87 foreach ($parameters as $parameter) {
88 $type = $parameter->getType();
89
90 if ($type === null || $type->isBuiltin()) {
91 if ($parameter->isDefaultValueAvailable()) {
92 $dependencies[] = $parameter->getDefaultValue();
93 } else {
94 throw new \Exception("Cannot resolve dependency {$parameter->getName()}");
95 }
96 } else {
97 $dependency = $type->getName();
98 $dependencies[] = $this->make($dependency);
99 }
100 }
101
102 return $reflection->newInstanceArgs($dependencies);
103 }
104
105 /**
106 * Check if abstract is bound
107 */
108 public function has(string $abstract): bool
109 {
110 return isset($this->bindings[$abstract]);
111 }
112
113 /**
114 * Get an instance (alias for make)
115 */
116 public function get(string $abstract)
117 {
118 return $this->make($abstract);
119 }
120 }
121
122