Completed
Push — master ( 42c60c...b54121 )
by Chin
01:14
created

MultilingualRegistrar::shouldNotPrefixLocale()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
nc 2
nop 1
dl 0
loc 5
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace ChinLeung\LaravelMultilingualRoutes;
4
5
use Illuminate\Routing\Route;
6
use Illuminate\Routing\RouteCollection;
7
use Illuminate\Routing\Router;
8
use Illuminate\Support\Arr;
9
10
class MultilingualRegistrar
11
{
12
    /**
13
     * The router instance.
14
     *
15
     * @var \Illuminate\Routing\Router
16
     */
17
    protected $router;
18
19
    /**
20
     * Constructor of the class.
21
     *
22
     * @param  \Illuminate\Routing\Router  $router
23
     */
24
    public function __construct(Router $router)
25
    {
26
        $this->router = $router;
27
    }
28
29
    /**
30
     * Register the routes.
31
     *
32
     * @param  string  $key
33
     * @param  mixed  $handle
34
     * @param  array  $locales
35
     * @param  array  $options
36
     * @return \Illuminate\Routing\RouteCollection
37
     */
38
    public function register(string $key, $handle, array $locales, array $options) : RouteCollection
39
    {
40
        $collection = new RouteCollection;
41
42
        foreach ($locales as $locale) {
43
            $collection->add(
44
                $this
45
                    ->registerRoute($key, $handle, $locale, $options)
46
                    ->name($this->generateNameForLocaleFromOptions($locale, $key, $options))
47
            );
48
        }
49
50
        return $collection;
51
    }
52
53
    /**
54
     * Register a single route.
55
     *
56
     * @param  string  $key
57
     * @param  mixed  $handle
58
     * @param  string  $locale
59
     * @param  array  $options
60
     * @return \Illuminate\Routing\Route
61
     */
62
    protected function registerRoute(string $key, $handle, string $locale, array $options) : Route
63
    {
64
        $route = $this->generateRoute($key, $handle, $locale, $options);
65
66
        foreach (Arr::get($options, 'constraints', []) as $name => $expression) {
67
            $route->where($name, $expression);
68
        }
69
70
        if ($prefix = $this->generatePrefixForLocale($key, $locale)) {
71
            $route->setUri("{$prefix}/{$route->uri}");
72
        }
73
74
        return $this->cleanUniqueRegistrationKey($route, $locale);
75
    }
76
77
    /**
78
     * Generate a route.
79
     *
80
     * @param  string  $key
81
     * @param  mixed  $handle
82
     * @param  string  $locale
83
     * @param  array  $options
84
     * @return \Illuminate\Routing\Route
85
     */
86
    protected function generateRoute(string $key, $handle, string $locale, array $options) : Route
87
    {
88
        $route = $this->router->addRoute(
89
            $this->getRequestMethodFromOptions($options),
90
            $this->applyUniqueRegistrationKey(
91
                $this->generateUriFromKey($key, $locale),
92
                $locale
93
            ),
94
            $handle ?: '\Illuminate\Routing\ViewController'
95
        );
96
97
        if (is_null($handle)) {
98
            return $route
99
                ->defaults('view', Arr::get($options, 'view', $key))
100
                ->defaults('data', Arr::get($options, 'data', []));
101
        }
102
103
        return $route;
104
    }
105
106
    /**
107
     * Retrieve the request method from the options.
108
     *
109
     * @param  array  $options
110
     * @return array
111
     */
112
    protected function getRequestMethodFromOptions(array $options) : array
113
    {
114
        $method = $options['method'] ?? 'get';
115
116
        if ($method == 'get') {
117
            return ['GET', 'HEAD'];
118
        }
119
120
        return [strtoupper($method)];
121
    }
122
123
    /**
124
     * Generate the name of the route based on the options.
125
     *
126
     * @param  string  $locale
127
     * @param  string  $key
128
     * @param  array  $options
129
     * @return string
130
     */
131
    protected function generateNameForLocaleFromOptions(string $locale, string $key, array $options) : string
132
    {
133
        if ($name = Arr::get($options, "names.$locale")) {
134
            return "$locale.$name";
135
        }
136
137
        return sprintf(
138
            '%s.%s',
139
            $locale,
140
            Arr::get($options, 'name', $key)
141
        );
142
    }
143
144
    /**
145
     * Generate the prefix of the route based on the options.
146
     *
147
     * @param  string  $key
148
     * @param  string  $locale
149
     * @return string|null
150
     */
151
    protected function generatePrefixForLocale(string $key, string $locale) : ?string
152
    {
153
        if ($key == '/' || $this->shouldNotPrefixLocale($locale)) {
154
            return null;
155
        }
156
157
        return $locale;
158
    }
159
160
    /**
161
     * Generate the route uri from the translation key and locale.
162
     *
163
     * @param  string  $key
164
     * @param  string  $locale
165
     * @return string
166
     */
167
    protected function generateUriFromKey(string $key, string $locale) : string
168
    {
169
        if ($key == '/') {
170
            return $locale == config('laravel-multilingual-routes.default') ? '/' : "/$locale";
171
        }
172
173
        return trans("routes.$key", [], $locale);
174
    }
175
176
    /**
177
     * Apply the unique registration key to make sure the route is registered.
178
     *
179
     * @param  string  $uri
180
     * @param  string  $locale
181
     * @return string
182
     */
183
    protected function applyUniqueRegistrationKey(string $uri, string $locale) : string
184
    {
185
        return "__{$locale}__".$uri;
186
    }
187
188
    /**
189
     * Clean the unique registration key from the route uri after it has been
190
     * registered in the router.
191
     *
192
     * @param  \Illuminate\Routing\Route  $route
193
     * @param  string  $locale
194
     * @return \Illuminate\Routing\Route
195
     */
196
    protected function cleanUniqueRegistrationKey(Route $route, string $locale) : Route
197
    {
198
        return $route->setUri(str_replace("__{$locale}__", '', $route->uri));
199
    }
200
201
    /**
202
     * Verify if we should not prefix the locale.
203
     *
204
     * @param  string  $locale
205
     * @return bool
206
     */
207
    protected function shouldNotPrefixLocale(string $locale) : bool
208
    {
209
        return $locale == config('laravel-multilingual-routes.default')
210
            && ! config('laravel-multilingual-routes.prefix_default');
211
    }
212
}
213