Test Failed
Push — feat/contextual-bindings ( c2fffd )
by Chema
05:29
created

test_contextual_binding_with_multiple_classes()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 18
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 1
Metric Value
cc 1
eloc 12
c 1
b 0
f 1
nc 1
nop 0
dl 0
loc 18
rs 9.8666
1
<?php
2
3
declare(strict_types=1);
4
5
namespace GacelaTest\Integration\Framework\Container;
6
7
use Gacela\Framework\Bootstrap\GacelaConfig;
8
use Gacela\Framework\Container\Container;
9
use Gacela\Framework\Gacela;
10
use PHPUnit\Framework\TestCase;
11
use ReflectionClass;
12
use stdClass;
13
14
final class ContextualBindingsTest extends TestCase
15
{
16
    protected function tearDown(): void
17
    {
18
        $reflection = new ReflectionClass(Gacela::class);
19
        $method = $reflection->getMethod('resetCache');
20
        $method->invoke(null);
21
    }
22
23
    public function test_contextual_binding_resolves_based_on_requesting_class(): void
24
    {
25
        Gacela::bootstrap(__DIR__, static function (GacelaConfig $config): void {
26
            $config->addBinding('LoggerInterface', 'DefaultLogger');
27
            $config->when(stdClass::class)
28
                ->needs('LoggerInterface')
29
                ->give('SpecificLogger');
30
        });
31
32
        Container::withConfig(\Gacela\Framework\Config\Config::getInstance());
33
34
        // Verify the contextual binding was registered
35
        $contextualBindings = \Gacela\Framework\Config\Config::getInstance()
36
            ->getSetupGacela()
37
            ->getContextualBindings();
38
39
        self::assertArrayHasKey(stdClass::class, $contextualBindings);
40
        self::assertSame('SpecificLogger', $contextualBindings[stdClass::class]['LoggerInterface']);
41
    }
42
43
    public function test_contextual_binding_with_callable(): void
44
    {
45
        $callable = static fn (): stdClass => new stdClass();
46
47
        Gacela::bootstrap(__DIR__, static function (GacelaConfig $config) use ($callable): void {
48
            $config->when('UserController')
49
                ->needs('LoggerInterface')
50
                ->give($callable);
51
        });
52
53
        Container::withConfig(\Gacela\Framework\Config\Config::getInstance());
54
55
        $contextualBindings = \Gacela\Framework\Config\Config::getInstance()
56
            ->getSetupGacela()
57
            ->getContextualBindings();
58
59
        self::assertArrayHasKey('UserController', $contextualBindings);
60
        self::assertSame($callable, $contextualBindings['UserController']['LoggerInterface']);
61
    }
62
63
    public function test_multiple_contextual_bindings_for_same_class(): void
64
    {
65
        Gacela::bootstrap(__DIR__, static function (GacelaConfig $config): void {
66
            $config->when(stdClass::class)
67
                ->needs('LoggerInterface')
68
                ->give('FileLogger');
69
70
            $config->when(stdClass::class)
71
                ->needs('CacheInterface')
72
                ->give('RedisCache');
73
        });
74
75
        Container::withConfig(\Gacela\Framework\Config\Config::getInstance());
76
77
        $contextualBindings = \Gacela\Framework\Config\Config::getInstance()
78
            ->getSetupGacela()
79
            ->getContextualBindings();
80
81
        self::assertArrayHasKey(stdClass::class, $contextualBindings);
82
        self::assertCount(2, $contextualBindings[stdClass::class]);
83
        self::assertSame('FileLogger', $contextualBindings[stdClass::class]['LoggerInterface']);
84
        self::assertSame('RedisCache', $contextualBindings[stdClass::class]['CacheInterface']);
85
    }
86
87
    public function test_contextual_binding_with_multiple_classes(): void
88
    {
89
        Gacela::bootstrap(__DIR__, static function (GacelaConfig $config): void {
90
            $config->when([stdClass::class, 'OtherClass'])
91
                ->needs('LoggerInterface')
92
                ->give('SharedLogger');
93
        });
94
95
        Container::withConfig(\Gacela\Framework\Config\Config::getInstance());
96
97
        $contextualBindings = \Gacela\Framework\Config\Config::getInstance()
98
            ->getSetupGacela()
99
            ->getContextualBindings();
100
101
        self::assertArrayHasKey(stdClass::class, $contextualBindings);
102
        self::assertArrayHasKey('OtherClass', $contextualBindings);
103
        self::assertSame('SharedLogger', $contextualBindings[stdClass::class]['LoggerInterface']);
104
        self::assertSame('SharedLogger', $contextualBindings['OtherClass']['LoggerInterface']);
105
    }
106
107
    public function test_contextual_bindings_merge_with_gacela_php_file(): void
108
    {
109
        // Create a temporary gacela.php file
110
        $tempDir = sys_get_temp_dir() . '/gacela_test_' . uniqid();
111
        mkdir($tempDir);
112
113
        $gacelaPhpContent = <<<'PHP'
114
<?php
115
use Gacela\Framework\Bootstrap\GacelaConfig;
116
117
return static function (GacelaConfig $config): void {
118
    $config->when('FromFile')
119
        ->needs('LoggerInterface')
120
        ->give('FileLogger');
121
};
122
PHP;
123
124
        file_put_contents($tempDir . '/gacela.php', $gacelaPhpContent);
125
126
        Gacela::bootstrap($tempDir, static function (GacelaConfig $config): void {
127
            $config->when('FromBootstrap')
128
                ->needs('CacheInterface')
129
                ->give('RedisCache');
130
        });
131
132
        Container::withConfig(\Gacela\Framework\Config\Config::getInstance());
133
134
        $contextualBindings = \Gacela\Framework\Config\Config::getInstance()
135
            ->getSetupGacela()
136
            ->getContextualBindings();
137
138
        // Both bindings should be present
139
        self::assertArrayHasKey('FromFile', $contextualBindings);
140
        self::assertArrayHasKey('FromBootstrap', $contextualBindings);
141
        self::assertSame('FileLogger', $contextualBindings['FromFile']['LoggerInterface']);
142
        self::assertSame('RedisCache', $contextualBindings['FromBootstrap']['CacheInterface']);
143
144
        // Cleanup
145
        unlink($tempDir . '/gacela.php');
146
        rmdir($tempDir);
147
    }
148
}
149