Passed
Push — master ( d927fb...4715fc )
by Alexander
02:46
created

Translator   A

Complexity

Total Complexity 12

Size/Duplication

Total Lines 100
Duplicated Lines 0 %

Test Coverage

Coverage 100%

Importance

Changes 0
Metric Value
wmc 12
eloc 35
c 0
b 0
f 0
dl 0
loc 100
ccs 37
cts 37
cp 1
rs 10

5 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 12 1
A setLocale() 0 3 1
A addCategorySource() 0 3 1
B translate() 0 43 8
A getLocale() 0 3 1
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Translator;
6
7
use Psr\EventDispatcher\EventDispatcherInterface;
8
use Yiisoft\I18n\Locale;
9
use Yiisoft\Translator\Event\MissingTranslationCategoryEvent;
10
use Yiisoft\Translator\Event\MissingTranslationEvent;
11
12
/**
13
 * Translator translates a message into the specified language.
14
 */
15
class Translator implements TranslatorInterface
16
{
17
    private string $defaultCategory;
18
    private string $locale;
19
    private ?EventDispatcherInterface $eventDispatcher;
20
    private ?string $fallbackLocale;
21
    /**
22
     * @var Category[]
23
     */
24
    private array $categories = [];
25
26
    /**
27
     * @param Category $defaultCategory Default category to use if category is not specified explicitly.
28
     * @param string $locale Default locale to use if locale is not specified explicitly.
29
     * @param string|null $fallbackLocale Locale to use if message for the locale specified was not found. Null for none.
30
     * @param EventDispatcherInterface|null $eventDispatcher Event dispatcher for translation events. Null for none.
31
     */
32 34
    public function __construct(
33
        Category $defaultCategory,
34
        string $locale,
35
        ?string $fallbackLocale = null,
36
        ?EventDispatcherInterface $eventDispatcher = null
37
    ) {
38 34
        $this->defaultCategory = $defaultCategory->getName();
39 34
        $this->eventDispatcher = $eventDispatcher;
40 34
        $this->locale = $locale;
41 34
        $this->fallbackLocale = $fallbackLocale;
42
43 34
        $this->addCategorySource($defaultCategory);
44 34
    }
45
46
    /**
47
     * @param Category $category Add category.
48
     */
49 34
    public function addCategorySource(Category $category): void
50
    {
51 34
        $this->categories[$category->getName()] = $category;
52 34
    }
53
54
    /**
55
     * Set the default locale.
56
     *
57
     * @param string $locale
58
     */
59 2
    public function setLocale(string $locale): void
60
    {
61 2
        $this->locale = $locale;
62 2
    }
63
64
    /**
65
     * @return string Default locale.
66
     */
67 2
    public function getLocale(): string
68
    {
69 2
        return $this->locale;
70
    }
71
72 34
    public function translate(
73
        string $id,
74
        array $parameters = [],
75
        string $category = null,
76
        string $locale = null
77
    ): string {
78 34
        $locale = $locale ?? $this->locale;
79
80 34
        $category = $category ?? $this->defaultCategory;
81
82 34
        if (empty($this->categories[$category])) {
83 1
            if ($this->eventDispatcher !== null) {
84 1
                $this->eventDispatcher->dispatch(new MissingTranslationCategoryEvent($category));
85
            }
86 1
            return $id;
87
        }
88
89 33
        $sourceCategory = $this->categories[$category];
90 33
        $message = $sourceCategory->getMessage($id, $locale, $parameters);
91
92 33
        if ($message === null) {
93 18
            if ($this->eventDispatcher !== null) {
94 12
                $this->eventDispatcher->dispatch(new MissingTranslationEvent($sourceCategory->getName(), $locale, $id));
95
            }
96
97 18
            $localeObject = new Locale($locale);
98 18
            $fallback = $localeObject->fallbackLocale();
99
100 18
            if ($fallback->asString() !== $localeObject->asString()) {
101 11
                return $this->translate($id, $parameters, $category, $fallback->asString());
102
            }
103
104 12
            if (!empty($this->fallbackLocale)) {
105 3
                $fallbackLocaleObject = (new Locale($this->fallbackLocale))->fallbackLocale();
106 3
                if ($fallbackLocaleObject->asString() !== $localeObject->asString()) {
107 3
                    return $this->translate($id, $parameters, $category, $fallbackLocaleObject->asString());
108
                }
109
            }
110
111 9
            $message = $id;
112
        }
113
114 33
        return $sourceCategory->format($message, $parameters, $locale);
115
    }
116
}
117