GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.

AbstractPosition::getVersion()   A
last analyzed

Complexity

Conditions 2
Paths 2

Size

Total Lines 12
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 6
nc 2
nop 1
dl 0
loc 12
rs 10
c 0
b 0
f 0
1
<?php
2
/**
3
 * This file is part of the O2System Framework package.
4
 *
5
 * For the full copyright and license information, please view the LICENSE
6
 * file that was distributed with this source code.
7
 *
8
 * @author         Steeve Andrian Salim
9
 * @copyright      Copyright (c) Steeve Andrian Salim
10
 */
11
12
// ------------------------------------------------------------------------
13
14
namespace O2System\Framework\Http\Presenter\Assets\Positions\Abstracts;
15
16
// ------------------------------------------------------------------------
17
18
use MatthiasMullie\Minify\CSS;
19
use MatthiasMullie\Minify\JS;
20
use O2System\Kernel\Http\Message\Uri;
21
22
/**
23
 * Class AbstractPosition
24
 *
25
 * @package O2System\Framework\Http\Presenter\Assets\Positions\Abstracts
26
 */
27
abstract class AbstractPosition
28
{
29
    /**
30
     * AbstractPosition::__get
31
     *
32
     * @param string $property
33
     *
34
     * @return \O2System\Framework\Http\Presenter\Assets\Collections\Css|\O2System\Framework\Http\Presenter\Assets\Collections\Font|\O2System\Framework\Http\Presenter\Assets\Collections\Javascript|null
0 ignored issues
show
Bug introduced by
The type O2System\Framework\Http\...\Assets\Collections\Css 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. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
35
     */
36
    public function __get($property)
37
    {
38
        return isset($this->{$property}) ? $this->{$property} : null;
39
    }
40
41
    // ------------------------------------------------------------------------
42
43
    /**
44
     * AbstractPosition::getUrl
45
     *
46
     * @param string $realPath
47
     *
48
     * @return string
49
     */
50
    public function getUrl($realPath)
51
    {
52
        if (strpos($realPath, 'http') !== false) {
53
            return $realPath;
54
        }
55
56
        return (new Uri())
57
            ->withQuery(null)
58
            ->withSegments(
59
                new Uri\Segments(
60
                    str_replace(
61
                        [PATH_PUBLIC, DIRECTORY_SEPARATOR],
62
                        ['', '/'],
63
                        $realPath
64
                    )
65
                )
66
            )
67
            ->__toString();
68
    }
69
70
    // ------------------------------------------------------------------------
71
72
    /**
73
     * AbstractPosition::loadCollections
74
     *
75
     * @param array $collections
76
     */
77
    public function loadCollections(array $collections)
78
    {
79
        foreach ($collections as $subDir => $files) {
80
            if (is_array($files) and count($files)) {
81
82
                // normalize the subDirectory with a trailing separator
83
                $subDir = str_replace(['/', '\\'], DIRECTORY_SEPARATOR, $subDir);
84
                $subDir = rtrim($subDir, DIRECTORY_SEPARATOR) . DIRECTORY_SEPARATOR;
85
86
                foreach ($files as $file) {
87
                    if (strpos($file, 'http') !== false) {
88
                        $this->loadUrl($file, $subDir);
89
                    } else {
90
                        $this->loadFile($file, $subDir);
91
                    }
92
                }
93
            } elseif (is_string($files)) {
94
                $this->loadFile($files);
95
            }
96
        }
97
    }
98
99
    // ------------------------------------------------------------------------
100
101
    /**
102
     * AbstractPosition::loadUrl
103
     *
104
     * @param string      $url
105
     * @param string|null $subDir
106
     *
107
     * @return bool
108
     */
109
    public function loadUrl($url, $subDir = null)
110
    {
111
        $property = is_null($subDir) ? 'css' : null;
112
113
        if (is_null($property)) {
114
            switch ($subDir) {
115
                default:
116
                case 'css/':
117
                    $property = 'css';
118
                    break;
119
                case 'font/':
120
                case 'fonts/':
121
                    $property = 'font';
122
                    break;
123
                case 'js/':
124
                    $property = 'javascript';
125
                    break;
126
            }
127
        }
128
129
        if (property_exists($this, $property)) {
130
            if ( ! call_user_func_array([$this->{$property}, 'has'], [$url])) {
131
                $this->{$property}->append($url);
132
133
                return true;
134
            }
135
        }
136
137
        return false;
138
    }
139
140
    // ------------------------------------------------------------------------
141
142
    /**
143
     * AbstractPosition::loadFile
144
     *
145
     * @param string      $filename
146
     * @param string|null $subDir
147
     *
148
     * @return void
149
     */
150
    abstract public function loadFile($filename, $subDir = null);
151
152
    // ------------------------------------------------------------------------
153
154
    /**
155
     * AbstractPosition::publishFile
156
     *
157
     * @param $filePath
158
     *
159
     * @return array
160
     */
161
    protected function publishFile($filePath)
162
    {
163
        $publicFilePath = str_replace(PATH_RESOURCES, PATH_PUBLIC, $filePath);
164
        $publicFileDir = dirname($publicFilePath) . DIRECTORY_SEPARATOR;
165
166
        $extension = pathinfo($filePath, PATHINFO_EXTENSION);
167
168
        $publicMinifyFilePath = str_replace('.' . $extension, '.min.' . $extension, $publicFilePath);
169
170
        $fileContent = file_get_contents($filePath);
171
        $fileVersion = $this->getVersion($fileContent);
172
173
        if (is_file($mapFilePath = $publicFilePath . '.map')) {
174
            $mapMetadata = json_decode(file_get_contents($mapFilePath), true);
175
            // if the file version is changed delete it first
176
            if ( ! hash_equals($fileVersion, $mapMetadata[ 'version' ])) {
177
                unlink($publicFilePath);
178
                unlink($publicMinifyFilePath);
179
                unlink($mapFilePath);
180
            }
181
        }
182
183
        if ( ! is_file($mapFilePath)) {
184
            if ( ! empty($fileContent)) {
185
                $mapMetadata = [
186
                    'version'        => $fileVersion,
187
                    'sources'        => [
188
                        str_replace([
189
                            PATH_ROOT,
0 ignored issues
show
Bug introduced by
The constant O2System\Framework\Http\...ons\Abstracts\PATH_ROOT was not found. Maybe you did not declare it correctly or list all dependencies?
Loading history...
190
                            '\\',
191
                            '/',
192
                            DIRECTORY_SEPARATOR,
193
                        ], [
194
                            '',
195
                            '/',
196
                            '/',
197
                            '/',
198
                        ], $filePath),
199
                    ],
200
                    'names'          => [],
201
                    'mappings'       => [],
202
                    'file'           => pathinfo($publicMinifyFilePath, PATHINFO_BASENAME),
203
                    'sourcesContent' => [
204
                        $fileContent,
205
                    ],
206
                    'sourceRoot'     => '',
207
                ];
208
209
                if ( ! is_dir($publicFileDir)) {
210
                    @mkdir($publicFileDir, 0777, true);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition for mkdir(). This can introduce security issues, and is generally not recommended. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unhandled  annotation

210
                    /** @scrutinizer ignore-unhandled */ @mkdir($publicFileDir, 0777, true);

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
211
                }
212
213
                if (is_writable($publicFileDir)) {
214
                    if ($fileStream = @fopen($publicFilePath, 'ab')) {
215
                        flock($fileStream, LOCK_EX);
216
                        fwrite($fileStream, $fileContent);
217
                        flock($fileStream, LOCK_UN);
218
                        fclose($fileStream);
219
220
                        // File Map
221
                        if ($fileStream = @fopen($mapFilePath, 'ab')) {
222
                            flock($fileStream, LOCK_EX);
223
224
                            fwrite($fileStream, json_encode($mapMetadata));
225
226
                            flock($fileStream, LOCK_UN);
227
                            fclose($fileStream);
228
                        }
229
230
                        switch ($extension) {
231
                            case 'min.css':
232
                            case 'css':
233
                                $minifyStyleHandler = new CSS($publicFilePath);
234
                                $minifyStyleHandler->minify($publicMinifyFilePath);
235
                                break;
236
237
                            case 'min.js':
238
                            case 'js':
239
                                $minifyJavascriptHandler = new JS($publicFilePath);
240
                                $minifyJavascriptHandler->minify($publicMinifyFilePath);
241
                                break;
242
                        }
243
244
                    }
245
                }
246
            }
247
        }
248
249
        return [
250
            'filePath' => $publicFilePath,
251
            'url'      => $this->getUrl($publicFilePath),
252
            'minify'   => [
253
                'filePath' => $publicMinifyFilePath,
254
                'url'      => $this->getUrl($publicMinifyFilePath),
255
            ],
256
            'version'  => $fileVersion,
257
        ];
258
    }
259
260
    // ------------------------------------------------------------------------
261
262
    /**
263
     * AbstractPosition::bundleFile
264
     *
265
     * @param string $filename
266
     * @param array  $sources
267
     *
268
     * @return array
269
     */
270
    protected function bundleFile($filename, array $sources)
271
    {
272
        $sourcesContent = [];
273
        foreach ($sources as $key => $source) {
274
            $content = file_get_contents($source);
275
276
            if ( ! empty($content)) {
277
                $sourcesContent[] = $content;
278
            } else {
279
                unset($sources[ $key ]);
280
            }
281
        }
282
283
        $fileContent = implode(PHP_EOL, $sourcesContent);
284
        $fileVersion = $this->getVersion($fileContent);
285
286
        $publicFilePath = PATH_PUBLIC . $filename;
287
        $filename = pathinfo($publicFilePath, PATHINFO_BASENAME);
288
289
        $publicFileDir = dirname($publicFilePath) . DIRECTORY_SEPARATOR . 'bundled' . DIRECTORY_SEPARATOR;
290
        $publicFilePath = $publicFileDir . $filename;
291
292
        $extension = pathinfo($publicFilePath, PATHINFO_EXTENSION);
293
294
        $publicMinifyFilePath = str_replace('.' . $extension, '.min.' . $extension, $publicFilePath);
295
296
        if ( ! empty($sourcesContent)) {
297
            if (is_file($mapFilePath = $publicFilePath . '.map')) {
298
                $mapMetadata = json_decode(file_get_contents($mapFilePath), true);
299
                // if the file version is changed delete it first
300
                if ( ! hash_equals($fileVersion, $mapMetadata[ 'version' ])) {
301
                    unlink($publicFilePath);
302
                    unlink($publicMinifyFilePath);
303
                    unlink($mapFilePath);
304
                }
305
            }
306
307
            if ( ! is_file($mapFilePath)) {
308
                if ( ! empty($fileContent)) {
309
                    $mapMetadata = [
310
                        'version'        => $fileVersion,
311
                        'sources'        => $sources,
312
                        'names'          => [],
313
                        'mappings'       => [],
314
                        'file'           => pathinfo($publicMinifyFilePath, PATHINFO_BASENAME),
315
                        'sourcesContent' => $sourcesContent,
316
                        'sourceRoot'     => '',
317
                    ];
318
319
                    if ( ! is_writable($publicFileDir)) {
320
                        @mkdir($publicFileDir, 0777, true);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition for mkdir(). This can introduce security issues, and is generally not recommended. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unhandled  annotation

320
                        /** @scrutinizer ignore-unhandled */ @mkdir($publicFileDir, 0777, true);

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
321
                    }
322
323
                    if (is_writable($publicFileDir)) {
324
                        if ($fileStream = @fopen($publicFilePath, 'ab')) {
325
                            flock($fileStream, LOCK_EX);
326
                            fwrite($fileStream, $fileContent);
327
                            flock($fileStream, LOCK_UN);
328
                            fclose($fileStream);
329
330
                            // File Map
331
                            if ($fileStream = @fopen($mapFilePath, 'ab')) {
332
                                flock($fileStream, LOCK_EX);
333
334
                                fwrite($fileStream, json_encode($mapMetadata));
335
336
                                flock($fileStream, LOCK_UN);
337
                                fclose($fileStream);
338
                            }
339
340
                            switch ($extension) {
341
                                case 'min.css':
342
                                case 'css':
343
                                    $minifyStyleHandler = new CSS($publicFilePath);
344
                                    $minifyStyleHandler->minify($publicMinifyFilePath);
345
                                    break;
346
347
                                case 'min.js':
348
                                case 'js':
349
                                    $minifyJavascriptHandler = new JS($publicFilePath);
350
                                    $minifyJavascriptHandler->minify($publicMinifyFilePath);
351
                                    break;
352
                            }
353
354
                        }
355
                    }
356
                }
357
            }
358
        }
359
360
        return [
361
            'filePath' => $publicFilePath,
362
            'url'      => $this->getUrl($publicFilePath),
363
            'minify'   => [
364
                'filePath' => $publicMinifyFilePath,
365
                'url'      => $this->getUrl($publicMinifyFilePath),
366
            ],
367
            'version'  => $fileVersion,
368
        ];
369
    }
370
371
    // ------------------------------------------------------------------------
372
373
    /**
374
     * AbstractPosition::getFilePath
375
     *
376
     * @param string      $filename
377
     * @param string|null $subDir
378
     *
379
     * @return string
380
     */
381
    protected function getFilePath($filename, $subDir = null)
382
    {
383
        $directories = presenter()->assets->getFilePaths();
384
385
        foreach ($directories as $directory) {
386
            if (strpos($filename, 'app') !== false) {
387
                if ($app = modules()->getActiveApp()) {
0 ignored issues
show
Bug introduced by
The method getActiveApp() does not exist on O2System\Framework\Conta...s\DataStructures\Module. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

387
                if ($app = modules()->/** @scrutinizer ignore-call */ getActiveApp()) {

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.

Loading history...
388
                    $directory = $app->getResourcesDir();
389
                }
390
            }
391
392
            /**
393
             * Try with sub directory
394
             * find from public directory first then resource directory
395
             */
396
            if (isset($subDir)) {
397
                $subDir = str_replace(['\\', '/'], DIRECTORY_SEPARATOR, $subDir);
398
399
                if (is_file($filePath = str_replace(PATH_RESOURCES, PATH_PUBLIC,
400
                        $directory) . $subDir . $filename)) {
401
                    return $filePath;
402
                    break;
0 ignored issues
show
Unused Code introduced by
break is not strictly necessary here and could be removed.

The break statement is not necessary if it is preceded for example by a return statement:

switch ($x) {
    case 1:
        return 'foo';
        break; // This break is not necessary and can be left off.
}

If you would like to keep this construct to be consistent with other case statements, you can safely mark this issue as a false-positive.

Loading history...
403
                } elseif (is_file($filePath = str_replace(PATH_RESOURCES, PATH_PUBLIC . 'assets' . DIRECTORY_SEPARATOR,
404
                        $directory) . $subDir . $filename)) {
405
                    return $filePath;
406
                    break;
407
                } elseif (is_file($filePath = $directory . $subDir . $filename)) {
408
                    return $filePath;
409
                    break;
410
                }
411
            }
412
413
            /**
414
             * Try without sub directory
415
             * find from public directory first then resource directory
416
             */
417
            if (is_file($filePath = str_replace(PATH_RESOURCES, PATH_PUBLIC, $directory) . $filename)) {
418
                return $filePath;
419
                break;
420
            } elseif (is_file($filePath = str_replace(PATH_RESOURCES, PATH_PUBLIC . 'assets' . DIRECTORY_SEPARATOR,
421
                    $directory) . $filename)) {
422
                return $filePath;
423
                break;
424
            } elseif (is_file($filePath = $directory . $filename)) {
425
                return $filePath;
426
                break;
427
            }
428
        }
429
430
        return false;
0 ignored issues
show
Bug Best Practice introduced by
The expression return false returns the type false which is incompatible with the documented return type string.
Loading history...
431
    }
432
433
    // ------------------------------------------------------------------------
434
435
    /**
436
     * AbstractPosition::getVersion
437
     *
438
     * @param string $code
439
     *
440
     * @return string
441
     */
442
    public function getVersion($codeSerialize)
443
    {
444
        $codeMd5 = md5($codeSerialize);
445
446
        $strSplit = str_split($codeMd5, 4);
447
        foreach ($strSplit as $strPart) {
448
            $strInt[] = str_pad(hexdec($strPart), 5, '0', STR_PAD_LEFT);
449
        }
450
451
        $codeVersion = round(implode('', $strInt), 10);
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $strInt seems to be defined by a foreach iteration on line 447. Are you sure the iterator is never empty, otherwise this variable is not defined?
Loading history...
Bug introduced by
implode('', $strInt) of type string is incompatible with the type double expected by parameter $val of round(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

451
        $codeVersion = round(/** @scrutinizer ignore-type */ implode('', $strInt), 10);
Loading history...
452
453
        return substr_replace($codeVersion, '.', 3, strlen($codeVersion) - 5);
454
    }
455
456
    // ------------------------------------------------------------------------
457
458
    /**
459
     * AbstractPosition::__toString
460
     *
461
     * @return string
462
     */
463
    abstract public function __toString();
464
}