Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
75.00% covered (warning)
75.00%
12 / 16
50.00% covered (danger)
50.00%
2 / 4
CRAP
0.00% covered (danger)
0.00%
0 / 1
Runtime
75.00% covered (warning)
75.00%
12 / 16
50.00% covered (danger)
50.00%
2 / 4
6.56
0.00% covered (danger)
0.00%
0 / 1
 __construct
100.00% covered (success)
100.00%
8 / 8
100.00% covered (success)
100.00%
1 / 1
1
 __destruct
0.00% covered (danger)
0.00%
0 / 3
0.00% covered (danger)
0.00%
0 / 1
6
 get
75.00% covered (warning)
75.00%
3 / 4
0.00% covered (danger)
0.00%
0 / 1
2.06
 context
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
1<?php
2
3declare(strict_types=1);
4
5namespace Cosray\Console;
6
7use Celema\Container\Container;
8use Celema\Core\Factory\Factory;
9use Celema\Quma\Database;
10use Celema\Verba\Translator;
11use Celema\Verba\Verba;
12use Cosray\App;
13use Cosray\Cms;
14use Cosray\Config;
15use Cosray\Context;
16use Cosray\Locales;
17use Cosray\Node\Writer;
18use UnexpectedValueException;
19
20/**
21 * Lazily resolved services for one console invocation.
22 *
23 * @internal
24 */
25final class Runtime
26{
27    private readonly Container $container;
28    private readonly ?Translator $previousTranslator;
29
30    public function __construct(App $app)
31    {
32        $app->boot();
33        $this->container = $app->container()->scope();
34        $this->container->add(Context::class, self::context(...))->scoped();
35        $this->container->add(Cms::class)->scoped();
36        $this->container->add(Writer::class)->scoped();
37        $context = $this->container->get(Context::class);
38        assert($context instanceof Context, 'The console context must be available');
39        $this->previousTranslator = Verba::translator();
40        Verba::activate($context->translator());
41    }
42
43    public function __destruct()
44    {
45        if ($this->previousTranslator !== null) {
46            Verba::activate($this->previousTranslator);
47        } else {
48            Verba::deactivate();
49        }
50    }
51
52    /** @param class-string $class */
53    public function get(string $class): object
54    {
55        $command = $this->container->get($class);
56
57        if (!is_object($command)) {
58            throw new UnexpectedValueException("Console runtime must resolve {$class} to an object");
59        }
60
61        return $command;
62    }
63
64    private static function context(
65        Database $db,
66        Config $config,
67        Container $container,
68        Factory $factory,
69        Locales $locales,
70    ): Context {
71        return Context::console($db, $config, $container, $factory, $locales);
72    }
73}