WhitespaceMinifier   A
last analyzed

Complexity

Total Complexity 10

Size/Duplication

Total Lines 122
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 1

Test Coverage

Coverage 100%

Importance

Changes 0
Metric Value
wmc 10
lcom 1
cbo 1
dl 0
loc 122
ccs 27
cts 27
cp 1
rs 10
c 0
b 0
f 0

6 Methods

Rating   Name   Duplication   Size   Complexity  
A process() 0 8 1
A trailingWhitespaces() 0 4 1
A runMinificationRules() 0 9 2
A removeSpacesAroundPlaceholders() 0 4 1
A provides() 0 4 1
A maxHtmlLineLength() 0 19 4
1
<?php
2
3
namespace ArjanSchouten\HtmlMinifier\Minifiers\Html;
4
5
use ArjanSchouten\HtmlMinifier\Constants;
6
use ArjanSchouten\HtmlMinifier\Minifiers\MinifierInterface;
7
use ArjanSchouten\HtmlMinifier\MinifyContext;
8
use ArjanSchouten\HtmlMinifier\Options;
9
10
class WhitespaceMinifier implements MinifierInterface
11
{
12
    /**
13
     * Max allowed html line length for old e.g. browsers, firewalls and routers.
14
     *
15
     * @var int
16
     */
17
    protected $maxHtmlLineLength = 32000;
18
19
    /**
20
     * Minification regexp's for replacing redundant whitespaces.
21
     *
22
     * @var array
23
     */
24
    protected $minifyRules = [
25
        '/\s?=\s?/' => '=',
26
        '/\s?\/>/'  => '>',
27
        '/>\s</'    => '><',
28
        '/\s\s/'    => ' ',
29
        '/<\s/'     => '<',
30
        '/\s>/'     => '>',
31
        '/\t/'      => ' ',
32
        '/\r/'      => '',
33
        '/\n/'      => '',
34
    ];
35
36
    /**
37
     * Minify redundant whitespaces.
38
     *
39
     * @param \ArjanSchouten\HtmlMinifier\MinifyContext $context
40
     *
41
     * @return \ArjanSchouten\HtmlMinifier\MinifyContext
42
     */
43 3
    public function process(MinifyContext $context)
44
    {
45 3
        $context->setContents($this->trailingWhitespaces($context->getContents()));
46 3
        $context->setContents($this->runMinificationRules($context->getContents()));
47 3
        $context->setContents($this->removeSpacesAroundPlaceholders($context->getContents()));
48
49 3
        return $context->setContents($this->maxHtmlLineLength($context->getContents(), $this->maxHtmlLineLength));
50
    }
51
52
    /**
53
     * Remove trailing whitespaces around the contents.
54
     *
55
     * @param string $contents
56
     *
57
     * @return string
58
     */
59 4
    public function trailingWhitespaces($contents)
60
    {
61 4
        return trim($contents);
62
    }
63
64
    /**
65
     * Loop over the minification rules as long as changes in output occur.
66
     *
67
     * @param string $contents
68
     *
69
     * @return string
70
     */
71 7
    public function runMinificationRules($contents)
72
    {
73
        do {
74 7
            $originalContents = $contents;
75 7
            $contents = preg_replace(array_keys($this->minifyRules), array_values($this->minifyRules), $contents);
76 7
        } while ($originalContents != $contents);
77
78 7
        return $contents;
79
    }
80
81
    /**
82
     * Remove all spaces around placeholders.
83
     *
84
     * @param string $contents
85
     *
86
     * @return string
87
     */
88 4
    public function removeSpacesAroundPlaceholders($contents)
89
    {
90 4
        return preg_replace('/\s*('.Constants::PLACEHOLDER_PATTERN.')\s*/', '$1', $contents);
91
    }
92
93
    /**
94
     * Old browsers, firewalls and more can't handle to long lines.
95
     * Therefore add a linebreak after specified character length.
96
     *
97
     * @param int    $maxHtmlLineLength
98
     * @param string $contents
99
     *
100
     * @return string
101
     */
102 4
    public function maxHtmlLineLength($contents, $maxHtmlLineLength)
103
    {
104 4
        if (strlen($contents) <= $maxHtmlLineLength) {
105 3
            return $contents;
106
        }
107
108 1
        $result = '';
109 1
        $splits = str_split($contents, $maxHtmlLineLength);
110 1
        foreach ($splits as $split) {
111 1
            $pos = strrpos($split, '><');
112 1
            if ($pos === false) {
113 1
                $result .= $split;
114
            } else {
115 1
                $result .= substr_replace($split, PHP_EOL, $pos + 1, 0);
116
            }
117
        }
118
119 1
        return $result;
120
    }
121
122
    /**
123
     * Indicates if minification rules depends on command options.
124
     *
125
     * @return string
126
     */
127 3
    public function provides()
128
    {
129 3
        return Options::WHITESPACES;
130
    }
131
}
132