Passed
Push — master ( d12f46...58955b )
by Ben
01:03
created

Detect::setApplicationLocale()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 6
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 4
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 3
nc 1
nop 0
dl 0
loc 6
ccs 4
cts 4
cp 1
crap 1
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
namespace Thinktomorrow\Locale;
4
5
use Illuminate\Http\Request;
6
use Thinktomorrow\Locale\Detectors\FallbackDetector;
7
use Thinktomorrow\Locale\Detectors\HiddenSegmentDetector;
8
use Thinktomorrow\Locale\Detectors\QueryDetector;
9
use Thinktomorrow\Locale\Detectors\SegmentDetector;
10
use Thinktomorrow\Locale\Values\ApplicationLocale;
11
use Thinktomorrow\Locale\Values\Config;
12
use Thinktomorrow\Locale\Values\Locale;
13
14
final class Detect
15
{
16
    /**
17
     * @var Request
18
     */
19
    private $request;
20
21
    /**
22
     * @var Config
23
     */
24
    private $config;
25
26
    /**
27
     * @var Locale
28
     */
29
    private $locale;
30
31
    /**
32
     * Current scope of locales.
33
     *
34
     * @var Scope
35
     */
36
    private $scope;
37
38 71
    public function __construct(Request $request, Config $config)
0 ignored issues
show
Bug introduced by
You have injected the Request via parameter $request. This is generally not recommended as there might be multiple instances during a request cycle (f.e. when using sub-requests). Instead, it is recommended to inject the RequestStack and retrieve the current request each time you need it via getCurrentRequest().
Loading history...
39
    {
40 71
        $this->request = $request;
41 71
        $this->config = $config;
42 71
    }
43
44
    /**
45
     * Detect the locale from current request url.
46
     * Once the locale has been determined, it will be set as the application locale.
47
     * A locale is only validated if it is present within the current locale scope.
48
     *
49
     * Detection honours following priority:
50
     * 1) If locale is found in request as query parameter e.g. ?locale=fr,
51
     * 2) If locale is found in request url, either from host or segment eg. nl.example.com, example.nl or example.com/nl
52
     * 3) Otherwise set locale to our fallback language (app.locale)
53
     */
54 68
    public function detectLocale(): self
55
    {
56 68
        $locale = null;
57
58
        $detectors = [
59 68
            FallbackDetector::class,
60
            HiddenSegmentDetector::class,
61
            SegmentDetector::class,
62
            QueryDetector::class,
63
        ];
64
65 68
        foreach ($detectors as $detector) {
66 68
            $locale = app($detector)->get($this->getScope(), $this->config) ?? $locale;
67
        }
68
69 68
        $this->locale = $locale;
70
71 68
        Scope::setActiveLocale($locale);
72
73 68
        $this->setApplicationLocale();
74
75 68
        return $this;
76
    }
77
78 68
    public function getLocale(): Locale
79
    {
80 68
        if (!$this->locale) {
81 68
            $this->detectLocale();
82
        }
83
84 68
        return $this->locale;
85
    }
86
87 71
    public function getScope(): Scope
88
    {
89 71
        if (!$this->scope) {
90 70
            $this->detectScope();
91
        }
92
93 71
        return $this->scope;
94
    }
95
96
    /**
97
     * This is handy for setting allowed scope via other source than config file.
98
     * this can be configurable from a cms.
99
     *
100
     * @param Scope|null $scope
101
     *
102
     * @return $this
103
     */
104 2
    public function setScope(Scope $scope = null)
105
    {
106 2
        if ($scope) {
107 2
            $this->scope = $scope;
108
        }
109
110 2
        return $this;
111
    }
112
113 70
    private function detectScope()
114
    {
115 70
        $this->scope = ScopeCollection::fromConfig($this->config)->findByRoot($this->request->root());
116 70
    }
117
118 68
    private function setApplicationLocale()
119
    {
120 68
        $applicationLocale = ApplicationLocale::from($this->locale);
121
122 68
        app()->setLocale($applicationLocale->__toString());
123 68
    }
124
}
125