Completed
Push — master ( 7173cb...23e6ba )
by Vitaly
02:37
created

CSS::prepare()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 7
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 3
CRAP Score 1

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 7
ccs 3
cts 3
cp 1
rs 9.4285
cc 1
eloc 3
nc 1
nop 1
crap 1
1
<?php
2
/**
3
 * Created by Vitaly Iegorov <[email protected]>.
4
 * on 07.07.16 at 18:19
5
 */
6
namespace samsonphp\css;
7
8
use samson\core\ExternalModule;
9
use samsonphp\event\Event;
10
use samsonphp\resource\exception\ResourceNotFound;
11
use samsonphp\resource\ResourceValidator;
12
use samsonphp\resource\Router;
13
14
/**
15
 * CSS assets handling class
16
 *
17
 * @author Vitaly Iegorov <[email protected]>
18
 * @package samsonphp\resource
19
 * TODO: Remove ResourceValidator as it is unnecessary
20
 */
21
class CSS extends ExternalModule
22
{
23
    /** @var string Module identifer */
24
    protected $id = 'resource_css';
25
26
    /** Pattern for matching CSS url */
27
    const P_URL = '/url\s*\(\s*(\'|\")?([^\)\s\'\"]+)(\'|\")?\s*\)/i';
28
29
    /** Event for firing before handling CSS resource */
30
    const E_BEFORE_HANDLER = 'samsonphp.css.before_handle';
31
32
    /** Event for firing after handling CSS resource */
33
    const E_AFTER_HANDLER = 'samsonphp.css.after_handle';
34
35
    /** @var string Path to current resource file */
36
    protected $currentResource;
37
38
    /** Module preparation stage handler */
39 5
    public function prepare(array $params = [])
40
    {
41
        // Subscribe for CSS handling
42 5
        Event::subscribe(Router::E_RESOURCE_COMPILE, [$this, 'compile']);
43
44 5
        return parent::prepare($params);
0 ignored issues
show
Unused Code introduced by
The call to ExternalModule::prepare() has too many arguments starting with $params.

This check compares calls to functions or methods with their respective definitions. If the call has more 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.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
45
    }
46
47
    /**
48
     * LESS resource compiler.
49
     *
50
     * @param string $resource  Resource full path
51
     * @param string $extension Resource extension
52
     * @param string $content   Compiled output resource content
53
     */
54 5
    public function compile($resource, $extension, &$content)
55
    {
56 5
        if ($extension === 'css') {
57 5
            $this->currentResource = $resource;
58
59
            // Fire event
60 5
            Event::fire(self::E_BEFORE_HANDLER, [&$content, $resource]);
61
62
            // Rewrite Urls
63 5
            $content = preg_replace_callback(self::P_URL, [$this, 'rewriteUrls'], $content);
64
65
            // Fire event
66 4
            Event::fire(self::E_AFTER_HANDLER, [&$content, $resource]);
67 4
        }
68 4
    }
69
70
    /**
71
     * Callback for CSS url(...) rewriting.
72
     *
73
     * @param array $matches Regular expression matches collection
74
     *
75
     * @return string Rewritten url(..) with static resource handler url
76
     * @throws ResourceNotFound
77
     */
78 5
    public function rewriteUrls($matches)
79
    {
80
        // Store static resource path
81 5
        $url = $matches[2];
82
83
        // Ignore inline resources
84 5
        if (strpos($url, 'data/') === false && strpos($url, 'data:') === false) {
85
            // Remove possible GET, HASH parameters from resource path
86 4
            $url = $this->getOnlyUrl($this->getOnlyUrl($url, '#'), '?');
87
88
            // Try to find resource and output full error
89
            try {
90 4
                $path = ResourceValidator::getProjectRelativePath($url, dirname($this->currentResource));
91 4
            } catch (ResourceNotFound $e) {
92 1
                throw new ResourceNotFound('Cannot find resource "' . $url . '" in "' . $this->currentResource . '"');
93
            }
94
95
            // Build path to static resource handler
96 3
            return 'url("/' . STATIC_RESOURCE_HANDLER . '/?p=' . $path . '")';
97
        }
98
99 1
        return $matches[0];
100
    }
101
102
    /**
103
     * Get only path or URL before marker.
104
     *
105
     * @param string $path   Full URL with possible unneeded data
106
     * @param string $marker Marker for separation
107
     *
108
     * @return string Filtered asset URL
109
     */
110 4
    protected function getOnlyUrl($path, $marker)
111
    {
112
        // Remove possible GET parameters from resource path
113 4
        if (($getStart = strpos($path, $marker)) !== false) {
114 3
            return substr($path, 0, $getStart);
115
        }
116
117 4
        return $path;
118
    }
119
}
120