1 | <?php |
||||||
2 | |||||||
3 | namespace Translation\Services; |
||||||
4 | |||||||
5 | use ErrorException; |
||||||
6 | use Illuminate\Contracts\Foundation\Application; |
||||||
7 | use Illuminate\Database\Eloquent\Model; |
||||||
8 | use InvalidArgumentException; |
||||||
9 | use Translation\Contracts\Client as ClientInterface; |
||||||
10 | use Translation\Contracts\Translation as TranslationInterface; |
||||||
11 | use UnexpectedValueException; |
||||||
12 | use Exception; |
||||||
13 | use Carbon\Carbon; |
||||||
14 | use Illuminate\Support\Facades\Schema; |
||||||
15 | use Translation\Models\Language; |
||||||
16 | use Illuminate\Support\Facades\Auth; |
||||||
17 | use Muleta\Utils\Modificators\ArrayModificator; |
||||||
18 | use Illuminate\Support\Facades\Cache; |
||||||
19 | use Translation\Repositories\LangRepository; |
||||||
20 | use Translation\Repositories\LangResourcesRepository; |
||||||
21 | |||||||
22 | class Translation implements TranslationInterface |
||||||
23 | { |
||||||
24 | /** |
||||||
25 | * Holds the application locale. |
||||||
26 | * |
||||||
27 | * @var string |
||||||
28 | */ |
||||||
29 | protected $locale = ''; |
||||||
30 | |||||||
31 | /** |
||||||
32 | * Holds the locale model. |
||||||
33 | * |
||||||
34 | * @var Model |
||||||
35 | */ |
||||||
36 | protected $localeModel; |
||||||
37 | |||||||
38 | /** |
||||||
39 | * Holds the translation model. |
||||||
40 | * |
||||||
41 | * @var Model |
||||||
42 | */ |
||||||
43 | protected $translationModel; |
||||||
44 | |||||||
45 | /** |
||||||
46 | * Holds the translation client. |
||||||
47 | * |
||||||
48 | * @var ClientInterface |
||||||
49 | */ |
||||||
50 | protected $client; |
||||||
51 | |||||||
52 | /** |
||||||
53 | * Holds the current cache instance. |
||||||
54 | * |
||||||
55 | * @var \Illuminate\Cache\CacheManager |
||||||
0 ignored issues
–
show
|
|||||||
56 | */ |
||||||
57 | protected $cache; |
||||||
58 | |||||||
59 | /** |
||||||
60 | * Holds the current config instance. |
||||||
61 | * |
||||||
62 | * @var \Illuminate\Config\Repository |
||||||
0 ignored issues
–
show
The type
Illuminate\Config\Repository was not found. Maybe you did not declare it correctly or list all dependencies?
The issue could also be caused by a filter entry in the build configuration.
If the path has been excluded in your configuration, e.g. filter:
dependency_paths: ["lib/*"]
For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths ![]() |
|||||||
63 | */ |
||||||
64 | protected $config; |
||||||
65 | |||||||
66 | /** |
||||||
67 | * Holds the current request instance. |
||||||
68 | * |
||||||
69 | * @var \Illuminate\Http\Request |
||||||
0 ignored issues
–
show
The type
Illuminate\Http\Request was not found. Maybe you did not declare it correctly or list all dependencies?
The issue could also be caused by a filter entry in the build configuration.
If the path has been excluded in your configuration, e.g. filter:
dependency_paths: ["lib/*"]
For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths ![]() |
|||||||
70 | */ |
||||||
71 | protected $request; |
||||||
72 | |||||||
73 | /** |
||||||
74 | * The default amount of time (minutes) to store the cached translations. |
||||||
75 | * |
||||||
76 | * @var int |
||||||
77 | */ |
||||||
78 | private $cacheTime = 30; |
||||||
79 | |||||||
80 | /** |
||||||
81 | * {@inheritdoc} |
||||||
82 | */ |
||||||
83 | public function __construct(Application $app) |
||||||
84 | { |
||||||
85 | $this->config = $app->make('config'); |
||||||
86 | $this->cache = $app->make('cache'); |
||||||
87 | $this->request = $app->make('request'); |
||||||
88 | |||||||
89 | $this->localeModel = $app->make($this->getConfigLocaleModel()); |
||||||
90 | $this->translationModel = $app->make($this->getConfigTranslationModel()); |
||||||
91 | $this->client = $app->make($this->getConfigClient()); |
||||||
92 | |||||||
93 | // Set the default locale to the current application locale |
||||||
94 | $this->setLocale($this->getConfigDefaultLocale()); |
||||||
95 | |||||||
96 | // Set the cache time from the configuration |
||||||
97 | $this->setCacheTime($this->getConfigCacheTime()); |
||||||
0 ignored issues
–
show
It seems like
$this->getConfigCacheTime() can also be of type string ; however, parameter $time of Translation\Services\Translation::setCacheTime() does only seem to accept integer , maybe add an additional type check?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
98 | } |
||||||
99 | |||||||
100 | /** |
||||||
101 | * Pega um code e retorna corretamente translation e pais |
||||||
102 | * |
||||||
103 | * @return void |
||||||
104 | */ |
||||||
105 | public function getCode($locale = null) |
||||||
106 | { |
||||||
107 | if (!is_null($locale)) { |
||||||
108 | return $locale; |
||||||
109 | } |
||||||
110 | return $this->getActualLanguageCode(); |
||||||
111 | } |
||||||
112 | public function getLanguageCode($locale = null) |
||||||
113 | { |
||||||
114 | return ArrayModificator::multiExplode( |
||||||
115 | [ |
||||||
116 | '|', |
||||||
117 | '_', |
||||||
118 | '-' |
||||||
119 | ], |
||||||
120 | $this->getCode($locale) |
||||||
0 ignored issues
–
show
Are you sure the usage of
$this->getCode($locale) targeting Translation\Services\Translation::getCode() seems to always return null.
This check looks for function or method calls that always return null and whose return value is used. class A
{
function getObject()
{
return null;
}
}
$a = new A();
if ($a->getObject()) {
The method The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes. ![]() $this->getCode($locale) of type void is incompatible with the type string expected by parameter $stringToArray of Muleta\Utils\Modificator...ficator::multiExplode() .
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
121 | )[0]; |
||||||
122 | } |
||||||
123 | |||||||
124 | /** |
||||||
125 | * |
||||||
126 | */ |
||||||
127 | public function getCountryCode($locale = null) |
||||||
128 | { |
||||||
129 | $explodeCode = ArrayModificator::multiExplode( |
||||||
130 | [ |
||||||
131 | '|', |
||||||
132 | '_', |
||||||
133 | '-' |
||||||
134 | ], |
||||||
135 | $this->getCode($locale) |
||||||
0 ignored issues
–
show
Are you sure the usage of
$this->getCode($locale) targeting Translation\Services\Translation::getCode() seems to always return null.
This check looks for function or method calls that always return null and whose return value is used. class A
{
function getObject()
{
return null;
}
}
$a = new A();
if ($a->getObject()) {
The method The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes. ![]() $this->getCode($locale) of type void is incompatible with the type string expected by parameter $stringToArray of Muleta\Utils\Modificator...ficator::multiExplode() .
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
136 | ); |
||||||
137 | if (!isset($explodeCode[1])) { |
||||||
138 | return null; |
||||||
139 | } |
||||||
140 | return $explodeCode[1]; |
||||||
141 | } |
||||||
142 | |||||||
143 | /** |
||||||
144 | * {@inheritdoc} |
||||||
145 | */ |
||||||
146 | public function translate($text = '', $replacements = [], $toLocale = '', bool $runOnce = false) |
||||||
147 | { |
||||||
148 | try { |
||||||
149 | // Make sure $text is actually a string and not and object / int |
||||||
150 | $this->validateText($text); |
||||||
151 | |||||||
152 | // Get the default translation text. This will insert the translation |
||||||
153 | // and the default application locale if they don't |
||||||
154 | // exist using firstOrCreate |
||||||
155 | $defaultTranslation = $this->getDefaultTranslation($text); |
||||||
156 | |||||||
157 | // If there are replacements inside the array we need to convert them |
||||||
158 | // into google translate safe placeholders. ex :name to __name__ |
||||||
159 | if (count($replacements) > 0) { |
||||||
160 | $defaultTranslation->translation = $this->makeTranslationSafePlaceholders($text, $replacements); |
||||||
161 | } |
||||||
162 | |||||||
163 | // If a toLocale has been provided, we're only translating a single string, so |
||||||
164 | // we won't call the getLocale method as it retrieves and sets the default |
||||||
165 | // session locale. If it has not been provided, we'll get the |
||||||
166 | // default locale, and set it on the current session. |
||||||
167 | if ($toLocale != '') { |
||||||
168 | $toLocale = $this->firstOrCreateLocale($toLocale); |
||||||
169 | } else { |
||||||
170 | $toLocale = $this->firstOrCreateLocale($this->getLocale()); |
||||||
171 | } |
||||||
172 | |||||||
173 | // Check if translation is requested for default locale. |
||||||
174 | // If it is default locale we can just return default translation. |
||||||
175 | if ($defaultTranslation->getAttribute($this->localeModel->getForeignKey()) == $toLocale->getKey()) { |
||||||
176 | return $this->makeReplacements($defaultTranslation->translation, $replacements); |
||||||
0 ignored issues
–
show
It seems like
$defaultTranslation->translation can also be of type Illuminate\Database\Eloq...uent\Relations\Relation and Illuminate\Database\Eloquent\Relations\Relation ; however, parameter $text of Translation\Services\Tra...ion::makeReplacements() does only seem to accept string , maybe add an additional type check?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
177 | } |
||||||
178 | |||||||
179 | // Since we are not on default translation locale, we will have to |
||||||
180 | // create (or get first) translation for provided locale where |
||||||
181 | // parent translation is our default translation. |
||||||
182 | $translation = $this->firstOrCreateTranslation( |
||||||
183 | $toLocale, |
||||||
184 | $defaultTranslation->translation, |
||||||
0 ignored issues
–
show
It seems like
$defaultTranslation->translation can also be of type Illuminate\Database\Eloq...uent\Relations\Relation and Illuminate\Database\Eloquent\Relations\Relation ; however, parameter $text of Translation\Services\Tra...stOrCreateTranslation() does only seem to accept string , maybe add an additional type check?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
185 | $defaultTranslation |
||||||
186 | ); |
||||||
187 | |||||||
188 | return $this->makeReplacements($translation->translation, $replacements); |
||||||
189 | } catch (\Illuminate\Database\QueryException $e) { |
||||||
190 | // If foreign key integrity constrains fail, we have a caching issue |
||||||
191 | if ($runOnce || !is_object($toLocale)) { |
||||||
192 | return $text; |
||||||
193 | } |
||||||
194 | |||||||
195 | $this->removeCacheLocale($toLocale->code); |
||||||
196 | |||||||
197 | // Burst translation cache |
||||||
198 | $this->removeCacheTranslation( |
||||||
199 | $this->translationModel->firstOrNew( |
||||||
200 | [ |
||||||
201 | $toLocale->getForeignKey() => $toLocale->getKey(), |
||||||
202 | 'translation' => $text, |
||||||
203 | ] |
||||||
204 | ) |
||||||
205 | ); |
||||||
206 | |||||||
207 | // Attempt translation 1 more time |
||||||
208 | return $this->translate($text, $replacements, $toLocale->code, $runOnce = true); |
||||||
209 | } |
||||||
210 | } |
||||||
211 | |||||||
212 | /** |
||||||
213 | * {@inheritdoc} |
||||||
214 | */ |
||||||
215 | public function getAppLocale() |
||||||
216 | { |
||||||
217 | return $this->config->get('app.locale'); |
||||||
218 | } |
||||||
219 | |||||||
220 | /** |
||||||
221 | * {@inheritdoc} |
||||||
222 | */ |
||||||
223 | public function getRoutePrefix() |
||||||
224 | { |
||||||
225 | $locale = $this->request->segment($this->getConfigRequestSegment()); |
||||||
226 | |||||||
227 | $locales = $this->getConfigLocales(); |
||||||
228 | |||||||
229 | if (is_array($locales) && in_array($locale, array_keys($locales))) { |
||||||
230 | return $locale; |
||||||
231 | } |
||||||
232 | } |
||||||
233 | |||||||
234 | /** |
||||||
235 | * {@inheritdoc} |
||||||
236 | */ |
||||||
237 | public function getLocale() |
||||||
238 | { |
||||||
239 | try { |
||||||
240 | return app()->getLocale(); |
||||||
0 ignored issues
–
show
The function
app was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
241 | } catch (Exception $e) { |
||||||
242 | if($this->request->request->has('locale')) { |
||||||
243 | return strtolower($this->request->input('locale')); |
||||||
244 | } |
||||||
245 | if ($this->request->hasHeader('locale')) { |
||||||
246 | return strtolower($this->request->header('locale')); |
||||||
247 | } |
||||||
248 | if ($this->request->hasCookie('locale')) { |
||||||
249 | return $this->request->cookie('locale'); |
||||||
250 | } |
||||||
251 | if ($this->request->hasSession() and $this->request->session()->has('locale')) { |
||||||
252 | return $this->request->session()->get('locale'); |
||||||
253 | } |
||||||
254 | if ($locale = substr($this->request->server('HTTP_ACCEPT_LANGUAGE'), 0, 2) and in_array($locale, \Illuminate\Support\Facades\Config::get('translation.locales'))) { |
||||||
255 | return $locale; |
||||||
256 | } |
||||||
257 | return $this->getConfigDefaultLocale(); |
||||||
258 | } |
||||||
259 | } |
||||||
260 | |||||||
261 | public function setLanguage($locale) |
||||||
262 | { |
||||||
263 | $repository = app(LangResourcesRepository::class); |
||||||
0 ignored issues
–
show
The function
app was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
264 | if (!$repository->hasLangExist($locale)) { |
||||||
265 | dd('Lang Dont Exist Translation'); |
||||||
0 ignored issues
–
show
The function
dd was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
266 | } |
||||||
267 | |||||||
268 | Cache::set('language', $locale); |
||||||
269 | $this->request->cookies->set('locale', $locale); |
||||||
270 | $this->request->session()->put('locale', $locale); |
||||||
271 | // CacheService::get('language', $locale); |
||||||
272 | if ($user = Auth::user()) { |
||||||
273 | $user->language_code = $locale; |
||||||
0 ignored issues
–
show
|
|||||||
274 | $user->save(); |
||||||
0 ignored issues
–
show
The method
save() does not exist on Illuminate\Contracts\Auth\Authenticatable .
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces. This is most likely a typographical error or the method has been renamed. ![]() |
|||||||
275 | } |
||||||
276 | |||||||
277 | return true; |
||||||
278 | } |
||||||
279 | |||||||
280 | public function getActualLanguage() |
||||||
281 | { |
||||||
282 | return $this->getActualLanguageCode(); |
||||||
283 | } |
||||||
284 | |||||||
285 | private function getActualLanguageCode() |
||||||
286 | { |
||||||
287 | return config('app.locale'); |
||||||
0 ignored issues
–
show
The call to
config() has too few arguments starting with defaultValue .
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
This check compares calls to functions or methods with their respective definitions. If the call has less arguments than are defined, it raises an issue. If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress. Please note the @ignore annotation hint above. ![]() |
|||||||
288 | } |
||||||
289 | |||||||
290 | public function getAllLanguages() |
||||||
291 | { |
||||||
292 | return Language::all(); |
||||||
293 | } |
||||||
294 | |||||||
295 | /** |
||||||
296 | * {@inheritdoc} |
||||||
297 | */ |
||||||
298 | public function setLocale($code = '') |
||||||
299 | { |
||||||
300 | $this->locale = $code; |
||||||
301 | } |
||||||
302 | |||||||
303 | /** |
||||||
304 | * {@inheritdoc} |
||||||
305 | */ |
||||||
306 | public function getDefaultTranslation($text) |
||||||
307 | { |
||||||
308 | $locale = $this->firstOrCreateLocale($this->getConfigDefaultLocale()); |
||||||
309 | |||||||
310 | return $this->firstOrCreateTranslation($locale, $text); |
||||||
311 | } |
||||||
312 | |||||||
313 | /** |
||||||
314 | * Replaces laravel translation placeholders with google |
||||||
315 | * translate safe placeholders. Ex:. |
||||||
316 | * |
||||||
317 | * Converts: |
||||||
318 | * :name |
||||||
319 | * |
||||||
320 | * Into: |
||||||
321 | * __name__ |
||||||
322 | * |
||||||
323 | * @param string $text |
||||||
324 | * @param array $replace |
||||||
325 | * |
||||||
326 | * @return mixed |
||||||
327 | */ |
||||||
328 | protected function makeTranslationSafePlaceholders($text, array $replace = []) |
||||||
329 | { |
||||||
330 | if (count($replace) > 0) { |
||||||
331 | foreach ($replace as $key => $value) { |
||||||
332 | // Search for :key |
||||||
333 | $search = ':'.$key; |
||||||
334 | |||||||
335 | // Replace it with __key__ |
||||||
336 | $replace = $this->makeTranslationSafePlaceholder($key); |
||||||
337 | |||||||
338 | // Perform the replacements |
||||||
339 | $text = str_replace($search, $replace, $text); |
||||||
340 | } |
||||||
341 | } |
||||||
342 | |||||||
343 | return $text; |
||||||
344 | } |
||||||
345 | |||||||
346 | /** |
||||||
347 | * Makes a placeholder by the specified key. |
||||||
348 | * |
||||||
349 | * @param string $key |
||||||
350 | * |
||||||
351 | * @return string |
||||||
352 | */ |
||||||
353 | protected function makeTranslationSafePlaceholder($key = '') |
||||||
354 | { |
||||||
355 | return '___'.strtolower($key).'___'; |
||||||
356 | } |
||||||
357 | |||||||
358 | /** |
||||||
359 | * Make the place-holder replacements on the specified text. |
||||||
360 | * |
||||||
361 | * @param string $text |
||||||
362 | * @param array $replacements |
||||||
363 | * |
||||||
364 | * @return string |
||||||
365 | */ |
||||||
366 | protected function makeReplacements($text, array $replacements) |
||||||
367 | { |
||||||
368 | if (count($replacements) > 0) { |
||||||
369 | foreach ($replacements as $key => $value) { |
||||||
370 | $replace = $this->makeTranslationSafePlaceholder($key); |
||||||
371 | |||||||
372 | $text = str_ireplace($replace, $value, $text); |
||||||
373 | } |
||||||
374 | } |
||||||
375 | |||||||
376 | return $text; |
||||||
377 | } |
||||||
378 | |||||||
379 | /** |
||||||
380 | * Retrieves or creates a locale from the specified code. |
||||||
381 | * |
||||||
382 | * @param string $code |
||||||
383 | * |
||||||
384 | * @return Model |
||||||
385 | */ |
||||||
386 | protected function firstOrCreateLocale($code) |
||||||
387 | { |
||||||
388 | $cachedLocale = $this->getCacheLocale($code); |
||||||
389 | |||||||
390 | if ($cachedLocale) { |
||||||
391 | return $cachedLocale; |
||||||
392 | } |
||||||
393 | |||||||
394 | $name = $this->getConfigLocaleByCode($code); |
||||||
395 | |||||||
396 | $locale = $this->localeModel->firstOrCreate( |
||||||
397 | [ |
||||||
398 | 'code' => $code, |
||||||
399 | 'name' => $name, |
||||||
400 | ] |
||||||
401 | ); |
||||||
402 | |||||||
403 | $this->setCacheLocale($locale); |
||||||
404 | |||||||
405 | return $locale; |
||||||
406 | } |
||||||
407 | |||||||
408 | /** |
||||||
409 | * Creates a translation. |
||||||
410 | * |
||||||
411 | * @param Model $locale |
||||||
412 | * @param string $text |
||||||
413 | * @param Model $parentTranslation |
||||||
414 | * |
||||||
415 | * @return Model |
||||||
416 | */ |
||||||
417 | protected function firstOrCreateTranslation(Model $locale, $text, $parentTranslation = null) |
||||||
418 | { |
||||||
419 | // We'll check to see if there's a cached translation |
||||||
420 | // first before we try and hit the database. |
||||||
421 | $cachedTranslation = $this->getCacheTranslation($locale, $text); |
||||||
422 | |||||||
423 | if ($cachedTranslation instanceof Model) { |
||||||
424 | return $cachedTranslation; |
||||||
425 | } |
||||||
426 | |||||||
427 | // Check if auto translation is enabled. If so we'll run |
||||||
428 | // the text through google translate and |
||||||
429 | // save it, then cache it. |
||||||
430 | if ($parentTranslation && $this->autoTranslateEnabled()) { |
||||||
431 | $this->client->setSource($parentTranslation->locale->code); |
||||||
0 ignored issues
–
show
It seems like
$parentTranslation->locale->code can also be of type DateTimeZone and Illuminate\Support\HigherOrderCollectionProxy ; however, parameter $source of Translation\Contracts\Client::setSource() does only seem to accept string , maybe add an additional type check?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
432 | $this->client->setTarget($locale->code); |
||||||
0 ignored issues
–
show
It seems like
$locale->code can also be of type Illuminate\Database\Eloq...uent\Relations\Relation and Illuminate\Database\Eloquent\Relations\Relation ; however, parameter $target of Translation\Contracts\Client::setTarget() does only seem to accept string , maybe add an additional type check?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
433 | |||||||
434 | try { |
||||||
435 | $text = $this->client->translate($text); |
||||||
436 | } catch (ErrorException $e) { |
||||||
437 | // Request to translate failed, set the text |
||||||
438 | // to the parent translation. |
||||||
439 | $text = $parentTranslation->translation; |
||||||
440 | } catch (UnexpectedValueException $e) { |
||||||
441 | // Looks like something other than text was passed in, |
||||||
442 | // we'll set the text to the parent translation |
||||||
443 | // for this exception as well. |
||||||
444 | $text = $parentTranslation->translation; |
||||||
445 | } |
||||||
446 | } |
||||||
447 | |||||||
448 | if ($parentTranslation) { |
||||||
449 | // If a parent translation is given we're looking for it's child translation. |
||||||
450 | $translation = $this->translationModel->firstOrNew( |
||||||
451 | [ |
||||||
452 | $locale->getForeignKey() => $locale->getKey(), |
||||||
453 | $this->translationModel->getForeignKey() => $parentTranslation->getKey(), |
||||||
454 | ] |
||||||
455 | ); |
||||||
456 | } else { |
||||||
457 | // Otherwise we're creating the parent translation. |
||||||
458 | $translation = $this->translationModel->firstOrNew( |
||||||
459 | [ |
||||||
460 | $locale->getForeignKey() => $locale->getKey(), |
||||||
461 | 'translation' => $text, |
||||||
462 | ] |
||||||
463 | ); |
||||||
464 | } |
||||||
465 | |||||||
466 | if (empty($translation->getAttribute('translation'))) { |
||||||
467 | // We need to make sure we don't overwrite the translation |
||||||
468 | // if it exists already in case it was modified. |
||||||
469 | $translation->setAttribute('translation', $text); |
||||||
470 | } |
||||||
471 | |||||||
472 | if ($translation->isDirty()) { |
||||||
473 | $translation->save(); |
||||||
474 | } |
||||||
475 | |||||||
476 | // Cache the translation so it's retrieved faster next time |
||||||
477 | $this->setCacheTranslation($translation); |
||||||
478 | |||||||
479 | return $translation; |
||||||
480 | } |
||||||
481 | |||||||
482 | /** |
||||||
483 | * Sets a cache key to the specified locale and text. |
||||||
484 | * |
||||||
485 | * @param Model $translation |
||||||
486 | */ |
||||||
487 | protected function setCacheTranslation(Model $translation) |
||||||
488 | { |
||||||
489 | if ($translation->parent instanceof Model) { |
||||||
490 | $id = $this->getTranslationCacheId($translation->locale, $translation->parent->translation); |
||||||
491 | } else { |
||||||
492 | $id = $this->getTranslationCacheId($translation->locale, $translation->translation); |
||||||
493 | } |
||||||
494 | |||||||
495 | if (!$this->cache->has($id)) { |
||||||
496 | $this->cache->put($id, $translation, $this->cacheTime); |
||||||
497 | } |
||||||
498 | } |
||||||
499 | |||||||
500 | /** |
||||||
501 | * Remove the translation from the cache manually. |
||||||
502 | * |
||||||
503 | * @param Model $translation |
||||||
504 | */ |
||||||
505 | public function removeCacheTranslation(Model $translation) |
||||||
506 | { |
||||||
507 | $id = $this->getTranslationCacheId($translation->locale, $translation->translation); |
||||||
508 | |||||||
509 | if ($this->cache->has($id)) { |
||||||
510 | $this->cache->forget($id); |
||||||
511 | } |
||||||
512 | } |
||||||
513 | |||||||
514 | /** |
||||||
515 | * Retrieves the cached translation from the specified locale |
||||||
516 | * and text. |
||||||
517 | * |
||||||
518 | * @param Model $locale |
||||||
519 | * @param string $text |
||||||
520 | * |
||||||
521 | * @return bool|Model |
||||||
522 | */ |
||||||
523 | protected function getCacheTranslation(Model $locale, $text) |
||||||
524 | { |
||||||
525 | $id = $this->getTranslationCacheId($locale, $text); |
||||||
526 | |||||||
527 | $cachedTranslation = $this->cache->get($id); |
||||||
528 | |||||||
529 | if ($cachedTranslation instanceof Model) { |
||||||
530 | return $cachedTranslation; |
||||||
531 | } |
||||||
532 | |||||||
533 | // Cached translation wasn't found, let's return |
||||||
534 | // false so we know to generate one. |
||||||
535 | return false; |
||||||
536 | } |
||||||
537 | |||||||
538 | /** |
||||||
539 | * Sets a cache key to the specified locale. |
||||||
540 | * |
||||||
541 | * @param Model $locale |
||||||
542 | */ |
||||||
543 | protected function setCacheLocale(Model $locale) |
||||||
544 | { |
||||||
545 | if (!$this->cache->has($locale->code)) { |
||||||
546 | $id = sprintf('translation.%s', $locale->code); |
||||||
0 ignored issues
–
show
It seems like
$locale->code can also be of type Illuminate\Database\Eloq...uent\Relations\Relation and Illuminate\Database\Eloquent\Relations\Relation ; however, parameter $values of sprintf() does only seem to accept double|integer|string , maybe add an additional type check?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
547 | |||||||
548 | $this->cache->put($id, $locale, $this->cacheTime); |
||||||
549 | } |
||||||
550 | } |
||||||
551 | |||||||
552 | /** |
||||||
553 | * Retrieves a cached locale from the specified locale code. |
||||||
554 | * |
||||||
555 | * @param string $code |
||||||
556 | * |
||||||
557 | * @return bool |
||||||
558 | */ |
||||||
559 | protected function getCacheLocale($code) |
||||||
560 | { |
||||||
561 | $id = sprintf('translation.%s', $code); |
||||||
562 | |||||||
563 | if ($this->cache->has($id)) { |
||||||
564 | return $this->cache->get($id); |
||||||
565 | } |
||||||
566 | |||||||
567 | return false; |
||||||
568 | } |
||||||
569 | |||||||
570 | /** |
||||||
571 | * Remove a locale from the cache. |
||||||
572 | * |
||||||
573 | * @param string $code |
||||||
574 | */ |
||||||
575 | protected function removeCacheLocale($code) |
||||||
576 | { |
||||||
577 | $id = sprintf('translation.%s', $code); |
||||||
578 | |||||||
579 | if ($this->cache->has($id)) { |
||||||
580 | $this->cache->forget($id); |
||||||
581 | } |
||||||
582 | } |
||||||
583 | |||||||
584 | /** |
||||||
585 | * Returns a unique translation code by compressing the text |
||||||
586 | * using a PHP compression function. |
||||||
587 | * |
||||||
588 | * @param Model $locale |
||||||
589 | * @param string $text |
||||||
590 | * |
||||||
591 | * @return string |
||||||
592 | */ |
||||||
593 | protected function getTranslationCacheId(Model $locale, $text) |
||||||
594 | { |
||||||
595 | $compressed = $this->compressString($text); |
||||||
596 | |||||||
597 | return sprintf('translation.%s.%s', $locale->code, $compressed); |
||||||
0 ignored issues
–
show
It seems like
$locale->code can also be of type Illuminate\Database\Eloq...uent\Relations\Relation and Illuminate\Database\Eloquent\Relations\Relation ; however, parameter $values of sprintf() does only seem to accept double|integer|string , maybe add an additional type check?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
598 | } |
||||||
599 | |||||||
600 | /** |
||||||
601 | * Returns a the english name of the locale code entered from the config file. |
||||||
602 | * |
||||||
603 | * @param string $code |
||||||
604 | * |
||||||
605 | * @return string |
||||||
606 | */ |
||||||
607 | protected function getConfigLocaleByCode($code) |
||||||
608 | { |
||||||
609 | $locales = $this->getConfigLocales(); |
||||||
610 | |||||||
611 | if (is_array($locales) && array_key_exists($code, $locales)) { |
||||||
612 | return $locales[$code]; |
||||||
613 | } |
||||||
614 | |||||||
615 | return $code; |
||||||
616 | } |
||||||
617 | |||||||
618 | /** |
||||||
619 | * Sets the time to store the translations and locales in cache. |
||||||
620 | * |
||||||
621 | * @param int $time |
||||||
622 | */ |
||||||
623 | protected function setCacheTime($time) |
||||||
624 | { |
||||||
625 | if (is_numeric($time)) { |
||||||
0 ignored issues
–
show
|
|||||||
626 | $this->cacheTime = $time; |
||||||
627 | } |
||||||
628 | } |
||||||
629 | |||||||
630 | /** |
||||||
631 | * Returns the default locale from the configuration. |
||||||
632 | * |
||||||
633 | * @return string |
||||||
634 | */ |
||||||
635 | protected function getConfigDefaultLocale() |
||||||
636 | { |
||||||
637 | return $this->config->get('translation.default_locale', 'en'); |
||||||
638 | } |
||||||
639 | |||||||
640 | /** |
||||||
641 | * Returns the locale model from the configuration. |
||||||
642 | * |
||||||
643 | * @return string |
||||||
644 | */ |
||||||
645 | protected function getConfigLocaleModel() |
||||||
646 | { |
||||||
647 | return $this->config->get('translation.models.locale', Models\Locale::class); |
||||||
0 ignored issues
–
show
The type
Translation\Services\Models\Locale was not found. Maybe you did not declare it correctly or list all dependencies?
The issue could also be caused by a filter entry in the build configuration.
If the path has been excluded in your configuration, e.g. filter:
dependency_paths: ["lib/*"]
For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths ![]() |
|||||||
648 | } |
||||||
649 | |||||||
650 | /** |
||||||
651 | * Returns the translation model from the configuration. |
||||||
652 | * |
||||||
653 | * @return string |
||||||
654 | */ |
||||||
655 | protected function getConfigTranslationModel() |
||||||
656 | { |
||||||
657 | return $this->config->get('translation.models.translation', Models\Translation::class); |
||||||
0 ignored issues
–
show
The type
Translation\Services\Models\Translation was not found. Maybe you did not declare it correctly or list all dependencies?
The issue could also be caused by a filter entry in the build configuration.
If the path has been excluded in your configuration, e.g. filter:
dependency_paths: ["lib/*"]
For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths ![]() |
|||||||
658 | } |
||||||
659 | |||||||
660 | /** |
||||||
661 | * Returns the translation client from the configuration. |
||||||
662 | * |
||||||
663 | * @return string |
||||||
664 | */ |
||||||
665 | protected function getConfigClient() |
||||||
666 | { |
||||||
667 | return $this->config->get('translation.clients.client', Clients\GoogleTranslate::class); |
||||||
0 ignored issues
–
show
The type
Translation\Services\Clients\GoogleTranslate was not found. Maybe you did not declare it correctly or list all dependencies?
The issue could also be caused by a filter entry in the build configuration.
If the path has been excluded in your configuration, e.g. filter:
dependency_paths: ["lib/*"]
For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths ![]() |
|||||||
668 | } |
||||||
669 | |||||||
670 | /** |
||||||
671 | * Returns the request segment to retrieve the locale from. |
||||||
672 | * |
||||||
673 | * @return int |
||||||
674 | */ |
||||||
675 | protected function getConfigRequestSegment() |
||||||
676 | { |
||||||
677 | return $this->config->get('translation.request_segment', 1); |
||||||
678 | } |
||||||
679 | |||||||
680 | /** |
||||||
681 | * Returns the array of configuration locales. |
||||||
682 | * |
||||||
683 | * @return array |
||||||
684 | */ |
||||||
685 | protected function getConfigLocales() |
||||||
686 | { |
||||||
687 | return $this->config->get('translation.locales'); |
||||||
688 | } |
||||||
689 | |||||||
690 | /** |
||||||
691 | * Returns the cache time set from the configuration file. |
||||||
692 | * |
||||||
693 | * @return string|int |
||||||
694 | */ |
||||||
695 | protected function getConfigCacheTime() |
||||||
696 | { |
||||||
697 | return $this->config->get('translation.cache_time', $this->cacheTime); |
||||||
698 | } |
||||||
699 | |||||||
700 | /** |
||||||
701 | * Returns the auto translate configuration option. |
||||||
702 | * |
||||||
703 | * @return bool |
||||||
704 | */ |
||||||
705 | protected function autoTranslateEnabled() |
||||||
706 | { |
||||||
707 | return $this->config->get('translation.auto_translate', true); |
||||||
708 | } |
||||||
709 | |||||||
710 | /** |
||||||
711 | * Calculates the md5 hash of a string. |
||||||
712 | * |
||||||
713 | * Used for storing cache keys for translations. |
||||||
714 | * |
||||||
715 | * @param $string |
||||||
716 | * |
||||||
717 | * @return string |
||||||
718 | */ |
||||||
719 | protected function compressString(string $string) |
||||||
720 | { |
||||||
721 | return md5($string); |
||||||
722 | } |
||||||
723 | |||||||
724 | /** |
||||||
725 | * Validates the inserted text to make sure it's a string. |
||||||
726 | * |
||||||
727 | * @param $text |
||||||
728 | * |
||||||
729 | * @throws InvalidArgumentException |
||||||
730 | * |
||||||
731 | * @return bool |
||||||
732 | */ |
||||||
733 | protected function validateText(string $text) |
||||||
734 | { |
||||||
735 | if (!is_string($text)) { |
||||||
0 ignored issues
–
show
|
|||||||
736 | $message = 'Invalid Argument. You must supply a string to be translated.'; |
||||||
737 | |||||||
738 | throw new InvalidArgumentException($message); |
||||||
739 | } |
||||||
740 | |||||||
741 | return true; |
||||||
742 | } |
||||||
743 | |||||||
744 | /** |
||||||
745 | * Detects the Default Locale Based on |
||||||
746 | */ |
||||||
747 | |||||||
748 | public function detectLocale($request) |
||||||
749 | { |
||||||
750 | if (!$request->hasCookie('locale')) { |
||||||
751 | $locale = substr($request->server('HTTP_ACCEPT_LANGUAGE'), 0, 2); |
||||||
752 | |||||||
753 | if (in_array($locale, \Illuminate\Support\Facades\Config::get('translation.locales'))) { |
||||||
754 | $request->cookies->set('locale', $locale); |
||||||
755 | } |
||||||
756 | } else { |
||||||
757 | $locale = $request->cookie('locale'); |
||||||
758 | } |
||||||
759 | |||||||
760 | $this->setLocale($locale); |
||||||
761 | |||||||
762 | return $locale; |
||||||
763 | } |
||||||
764 | |||||||
765 | |||||||
766 | |||||||
767 | /** |
||||||
768 | * Eu trouxe de Fora @todo |
||||||
769 | */ |
||||||
770 | public function getMenuLanguage() |
||||||
771 | { |
||||||
772 | $actual = $this->getActualLanguage(); |
||||||
773 | $languages = $this->getAllLanguages(); |
||||||
774 | if (empty($languages) || count($languages)<=1) { |
||||||
775 | return ''; |
||||||
776 | } |
||||||
777 | |||||||
778 | $activeHtml = config('app.locale'); |
||||||
0 ignored issues
–
show
The call to
config() has too few arguments starting with defaultValue .
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
This check compares calls to functions or methods with their respective definitions. If the call has less arguments than are defined, it raises an issue. If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress. Please note the @ignore annotation hint above. ![]() |
|||||||
779 | |||||||
780 | $html = '<div class="dropdown-menu dropdown-menu-right" aria-labelledby="languages">'; |
||||||
781 | foreach ($languages as $language) { |
||||||
782 | $active = ''; |
||||||
783 | if ($language->code == $actual) { |
||||||
784 | $active = ' active'; |
||||||
785 | $activeHtml = $language->code; |
||||||
786 | } |
||||||
787 | $html .= '<a class="dropdown-item'.$active.'" href="'.route('language.set', ['language' => $language->code]).'">'.$language->name.'</a>'; |
||||||
0 ignored issues
–
show
The function
route was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
788 | } |
||||||
789 | $html .= '</div>'; |
||||||
790 | |||||||
791 | return '<li class="nav-item dropdown">'. |
||||||
792 | '<a class="nav-item nav-link dropdown-toggle mr-md-2" href="#" id="languages" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">'. |
||||||
793 | $activeHtml. |
||||||
794 | '</a>'.$html.'</li>'; |
||||||
795 | } |
||||||
796 | |||||||
797 | public function getCurrent() |
||||||
798 | { |
||||||
799 | return LangRepository::getCurrent(); |
||||||
800 | } |
||||||
801 | public function getOptionsLocales() |
||||||
802 | { |
||||||
803 | return LangRepository::get(); |
||||||
804 | } |
||||||
805 | |||||||
806 | /** |
||||||
807 | * From FAcilitador LangServiceTrait |
||||||
808 | */ |
||||||
809 | |||||||
810 | |||||||
811 | /** |
||||||
812 | * Return menu for translation |
||||||
813 | * |
||||||
814 | * @return string |
||||||
815 | */ |
||||||
816 | public function menu_lang() |
||||||
817 | { |
||||||
818 | $langs = $this->getOptionsLocales(); |
||||||
819 | |||||||
820 | if (!$langs || empty($langs)) { |
||||||
0 ignored issues
–
show
The expression
$langs of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.
This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent. Consider making the comparison explicit by using ![]() |
|||||||
821 | return ''; |
||||||
822 | } |
||||||
823 | |||||||
824 | $current = $this->getCurrent(); |
||||||
825 | |||||||
826 | $response = '<li>'; |
||||||
827 | $response .= '<a href=""><span class="'.$current['class'].'"></span></a>'; |
||||||
828 | $response .= '<ul class="sub-menu clearfix">'; |
||||||
829 | $response .= '<li class=\'no-translation menu-item current-lang \'><a href="'.url('language/set/'.$current['locale']).'"><span class="'.$current['class'].'"></span></a></li>'; |
||||||
0 ignored issues
–
show
The function
url was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
830 | |||||||
831 | foreach ($langs as $lang) { |
||||||
832 | if ($lang['locale'] !== $current['locale']) { |
||||||
833 | $response .= '<li class=\'no-translation menu-item\'><a href="'.url('language/set/'.$lang['locale']).'"><span class="'.$lang['class'].'"></span></a></li>'; |
||||||
834 | } |
||||||
835 | } |
||||||
836 | |||||||
837 | $response .= '</ul></li>'; |
||||||
838 | |||||||
839 | return $response; |
||||||
840 | } |
||||||
841 | |||||||
842 | /** |
||||||
843 | * Build Menu para o componente de menu do Laravel Support |
||||||
844 | * |
||||||
845 | * @return void |
||||||
846 | */ |
||||||
847 | public function menuAdminLte() |
||||||
848 | { |
||||||
849 | $langs = $this->getOptionsLocales(); |
||||||
850 | |||||||
851 | if (!$langs || empty($langs)) { |
||||||
0 ignored issues
–
show
The expression
$langs of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.
This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent. Consider making the comparison explicit by using ![]() |
|||||||
852 | return ''; |
||||||
853 | } |
||||||
854 | |||||||
855 | $current = $this->getCurrent(); |
||||||
856 | |||||||
857 | $response = ''; |
||||||
858 | $response .= '<li class="nav-item dropdown"> |
||||||
859 | <a class="nav-link" data-toggle="dropdown" href="#" aria-expanded="false"> |
||||||
860 | <i class="'.$current['class'].'"></i> |
||||||
861 | </a> |
||||||
862 | <div class="dropdown-menu dropdown-menu-right p-0"> |
||||||
863 | <a href="#" class="dropdown-item active"> |
||||||
864 | <i class="'.$current['class'].' mr-2"></i> '.$current['locale'].' |
||||||
865 | </a>'; |
||||||
866 | |||||||
867 | // @todo |
||||||
868 | // '.route('translation.language.change', [$lang['locale']]).' |
||||||
869 | foreach ($langs as $lang) { |
||||||
870 | if ($lang['locale'] !== $current['locale']) { |
||||||
871 | $response .= '<a href="'.url('language/set/'.$lang['locale']).'" class="dropdown-item"> |
||||||
0 ignored issues
–
show
The function
url was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
872 | <i class="'.$lang['class'].' mr-2"></i> '.$lang['locale'].' |
||||||
873 | </a>'; |
||||||
874 | } |
||||||
875 | } |
||||||
876 | |||||||
877 | $response .= '</div> |
||||||
878 | </li>'; |
||||||
879 | return $response; |
||||||
880 | } |
||||||
881 | |||||||
882 | /** |
||||||
883 | * Build Menu para o componente de menu do Laravel Support |
||||||
884 | * |
||||||
885 | * @return void |
||||||
886 | */ |
||||||
887 | public function menuBuilder() |
||||||
888 | { |
||||||
889 | |||||||
890 | $langs = LangRepository::get(); |
||||||
891 | |||||||
892 | if (!$langs || empty($langs)) { |
||||||
0 ignored issues
–
show
The expression
$langs of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.
This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent. Consider making the comparison explicit by using ![]() |
|||||||
893 | return []; |
||||||
894 | } |
||||||
895 | $current = LangRepository::getCurrent(); |
||||||
896 | |||||||
897 | $array = [ |
||||||
898 | [ |
||||||
899 | 'text' => $current['locale'], |
||||||
900 | 'url' => url('sitec/language/set/'.$current['locale']), |
||||||
0 ignored issues
–
show
The function
url was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
901 | 'icon' => $current['class'], |
||||||
902 | // 'topnav' => true, |
||||||
903 | // 'topnav_user' => true, |
||||||
904 | 'topnav_right' => true, |
||||||
905 | // 'access' => \Porteiro\Models\Role::$ADMIN |
||||||
906 | ], |
||||||
907 | $current['locale'] => [ |
||||||
908 | |||||||
909 | ], |
||||||
910 | ]; |
||||||
911 | |||||||
912 | foreach ($langs as $lang) { |
||||||
913 | |||||||
914 | if ($lang['locale'] !== $current['locale']) { |
||||||
915 | $array[$current['locale']][] = [ |
||||||
916 | 'text' => $lang['locale'], |
||||||
917 | 'url' => url('sitec/language/set/'.$lang['locale']), |
||||||
918 | 'icon' => $lang['class'], |
||||||
919 | 'topnav_right' => true, |
||||||
920 | // 'level' => 3, // 0 (Public), 1, 2 (Admin) , 3 (Root) |
||||||
921 | ]; |
||||||
922 | } |
||||||
923 | } |
||||||
924 | |||||||
925 | return $array; |
||||||
926 | |||||||
927 | } |
||||||
928 | |||||||
929 | /** |
||||||
930 | * Get a especific image for current Lang. |
||||||
931 | * |
||||||
932 | * @param string $img_path |
||||||
933 | * |
||||||
934 | * @return string |
||||||
935 | */ |
||||||
936 | public function img_lang($img_path) |
||||||
937 | { |
||||||
938 | $public_path = public_path(); |
||||||
0 ignored issues
–
show
The function
public_path was not found. Maybe you did not declare it correctly or list all dependencies?
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||||
939 | |||||||
940 | $current = LangRepository::getCurrent(); |
||||||
941 | $min_lang = explode('-', $current['locale']); |
||||||
942 | |||||||
943 | $break_path = explode('.', $img_path); |
||||||
944 | |||||||
945 | $extensao = array_pop($break_path); |
||||||
946 | |||||||
947 | if (file_exists($public_path.'/'.implode('.', $break_path).'-'.$current['locale'].'.'.$extensao)) { |
||||||
948 | return implode('.', $break_path).'-'.$current['locale'].'.'.$extensao; |
||||||
949 | } |
||||||
950 | |||||||
951 | if (file_exists($public_path.'/'.implode('.', $break_path).'-'.$min_lang[0].'.'.$extensao)) { |
||||||
952 | return implode('.', $break_path).'-'.$min_lang[0].'.'.$extensao; |
||||||
953 | } |
||||||
954 | |||||||
955 | return $img_path; |
||||||
956 | } |
||||||
957 | } |
||||||
958 |
The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g.
excluded_paths: ["lib/*"]
, you can move it to the dependency path list as follows:For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths