PluginProbe
Powered Cache – Caching and Optimization for WordPress – Easily Improve PageSpeed & Web Vitals Score / 3.7
Powered Cache – Caching and Optimization for WordPress – Easily Improve PageSpeed & Web Vitals Score v3.7
trunk 1.0 1.0.1 1.1 1.1.1 1.1.2 1.2 1.2.1 1.2.2 1.2.3 1.2.4 1.2.5 1.2.6 1.2.7 1.2.8 2.0 2.0.1 2.0.2 2.0.3 2.0.4 2.1 2.1.1 2.1.2 2.2 2.2.1 All 69 releases
powered-cache / includes / classes / Optimizer / CSS.php

CSS.php in Powered Cache – Caching and Optimization for WordPress – Easily Improve PageSpeed & Web Vitals Score 3.7, at includes/classes/Optimizer/CSS.php

295 lines 7.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * CSS contact
4 *
5 * @package PoweredCache\Optimizer
6 */
7
8 //phpcs:disable Squiz.Commenting.VariableComment.Missing
9 //phpcs:disable Generic.Commenting.DocComment.MissingShort
10 //phpcs:disable Squiz.Commenting.FunctionComment.MissingParamName
11 //phpcs:disable Squiz.Commenting.FunctionComment.MissingParamTag
12
13 namespace PoweredCache\Optimizer;
14
15 use PoweredCache\CDN;
16 use \WP_Styles as WP_Styles;
17
18 /**
19 * Class CSS
20 */
21 class CSS extends WP_Styles {
22 private $old_styles;
23 public $allow_gzip_compression;
24 public $do_minify;
25 public $enable_cdn;
26
27 /**
28 * CSS constructor.
29 *
30 * @param object $styles WP_Styles
31 */
32 public function __construct( $styles ) {
33 if ( empty( $styles ) || ! ( $styles instanceof WP_Styles ) ) {
34 $this->old_styles = new WP_Styles();
35 } else {
36 $this->old_styles = $styles;
37 }
38
39 // Unset all the object properties except our private copy of the styles object.
40 // We have to unset everything so that the overload methods talk to $this->old_styles->whatever
41 // instead of $this->whatever.
42 foreach ( array_keys( get_object_vars( $this ) ) as $key ) {
43 if ( 'old_styles' === $key ) {
44 continue;
45 }
46 unset( $this->$key );
47 }
48 }
49
50 /**
51 * Prep items for concat
52 *
53 * @param bool $handles CSS handler
54 * @param bool $group CSS group
55 *
56 * @return string[]
57 */
58 public function do_items( $handles = false, $group = false ) {
59 $abspath = wp_normalize_path( ABSPATH );
60 $handles = false === $handles ? $this->queue : (array) $handles;
61 $stylesheets = array();
62 /**
63 * Filters site url
64 *
65 * @hook powered_cache_fo_site_url
66 *
67 * @param {string} $base_url Site URL.
68 *
69 * @return {string} New value.
70 * @since 2.0
71 */
72 $siteurl = apply_filters( 'powered_cache_fo_site_url', $this->base_url );
73 $this->all_deps( $handles );
74
75 $stylesheet_group_index = 0;
76 foreach ( $this->to_do as $key => $handle ) {
77 $obj = $this->registered[ $handle ];
78
79 $obj->src = apply_filters( 'style_loader_src', $obj->src, $obj->handle );
80
81 // Core is kind of broken and returns "true" for src of "colors" handle
82 // http://core.trac.wordpress.org/attachment/ticket/16827/colors-hacked-fixed.diff
83 // http://core.trac.wordpress.org/ticket/20729
84 $css_url = $obj->src;
85 if ( 'colors' === $obj->handle && true === $css_url ) {
86 $css_url = wp_style_loader_src( $css_url, $obj->handle );
87 }
88
89 $css_url_parsed = wp_parse_url( $obj->src );
90 $extra = $obj->extra;
91
92 // Don't concat by default
93 $do_concat = false;
94
95 // Only try to concat static css files
96 if ( false !== strpos( $css_url_parsed['path'], '.css' ) ) {
97 $do_concat = true;
98 }
99
100 // Don't try to concat styles which are loaded conditionally (like IE stuff)
101 if ( isset( $extra['conditional'] ) ) {
102 $do_concat = false;
103 }
104
105 // Don't concat rtl stuff for now until concat supports it correctly
106 if ( 'rtl' === $this->text_direction && ! empty( $extra['rtl'] ) ) {
107 $do_concat = false;
108 }
109
110 // Don't try to concat externally hosted scripts
111 $is_internal_url = Helper::is_internal_url( $css_url, $siteurl );
112 if ( ! $is_internal_url ) {
113 $do_concat = false;
114 }
115
116 // Concat and canonicalize the paths only for
117 // existing scripts that aren't outside $abspath
118 $css_realpath = Helper::realpath( $css_url, $siteurl );
119 if ( ! $css_realpath || 0 !== strpos( $css_realpath, $abspath ) ) {
120 $do_concat = false;
121 } else {
122 $css_url_parsed['path'] = substr( $css_realpath, strlen( $abspath ) - 1 );
123 }
124
125 if ( Helper::is_excluded_css( $css_url ) ) {
126 $do_concat = false;
127 }
128
129 /**
130 * Allow plugins to disable concatenation of certain stylesheets.
131 *
132 * @hook powered_cache_fo_css_do_concat
133 *
134 * @param {boolean} $do_concat Contact status.
135 * @param {string} $handle Handle of registered CSS item.
136 * @param {string} $css_url CSS Url. @since 3.2.1
137 *
138 * @return {boolean} New value.
139 * @since 2.0
140 */
141 $do_concat = apply_filters( 'powered_cache_fo_css_do_concat', $do_concat, $handle, $css_url );
142
143 if ( true === $do_concat ) {
144 $media = $obj->args;
145 if ( empty( $media ) ) {
146 $media = 'all';
147 }
148 if ( ! isset( $stylesheets[ $stylesheet_group_index ] ) || ( isset( $stylesheets[ $stylesheet_group_index ] ) && ! is_array( $stylesheets[ $stylesheet_group_index ] ) ) ) {
149 $stylesheets[ $stylesheet_group_index ] = array();
150 }
151
152 $stylesheets[ $stylesheet_group_index ][ $media ][ $handle ] = $css_url_parsed['path'];
153 $this->done[] = $handle;
154 } else {
155 $stylesheet_group_index ++;
156 $stylesheets[ $stylesheet_group_index ]['noconcat'][] = $handle;
157 $stylesheet_group_index ++;
158 }
159 unset( $this->to_do[ $key ] );
160 }
161
162 foreach ( $stylesheets as $idx => $stylesheets_group ) {
163 foreach ( $stylesheets_group as $media => $css ) {
164 if ( 'noconcat' === $media ) {
165
166 foreach ( $css as $handle ) {
167 if ( $this->do_item( $handle, $group ) ) {
168 $this->done[] = $handle;
169 }
170 }
171 continue;
172 } elseif ( count( $css ) > 1 ) {
173 $paths = array_map(
174 function ( $url ) use ( $abspath ) {
175 return $abspath . $url;
176 },
177 $css
178 );
179 $mtime = max( array_map( 'filemtime', $paths ) );
180 $path_str = implode( ',', $css ) . "?m={$mtime}";
181
182 if ( $this->allow_gzip_compression ) {
183 $path_64 = base64_encode( gzcompress( $path_str ) ); // phpcs:ignore WordPress.PHP.DiscouragedPHPFunctions.obfuscation_base64_encode
184 if ( strlen( $path_str ) > ( strlen( $path_64 ) + 1 ) ) {
185 $path_str = '-' . $path_64;
186 }
187 }
188
189 $href = Helper::get_optimized_url( $path_str, $this->do_minify );
190 } else {
191 if ( $this->do_minify ) {
192 $href = Helper::get_optimized_url( current( $css ), $this->do_minify );
193 } else {
194 $href = $this->cache_bust_mtime( $siteurl . current( $css ), $siteurl );
195 }
196 }
197
198 $handles = array_keys( $css );
199 $css_tag = "<link rel='stylesheet' id='$media-css-$idx' href='$href' type='text/css' media='$media' />\n"; // phpcs:ignore WordPress.WP.EnqueuedResources.NonEnqueuedStylesheet
200 /**
201 * Filters combined CSS tag.
202 *
203 * @hook powered_cache_fo_style_loader_tag
204 *
205 * @param {string} $css_tag CSS tag.
206 * @param {array} $handles The list of CSS handles.
207 * @param {string} $href CSS URL.
208 * @param {string} $media Media type.
209 *
210 * @return {string} New value.
211 * @since 2.0
212 */
213 echo apply_filters( 'powered_cache_fo_style_loader_tag', $css_tag, $handles, $href, $media ); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
214 array_map( array( $this, 'print_inline_style' ), array_keys( $css ) );
215 }
216 }
217
218 return $this->done;
219 }
220
221 /**
222 * Bust cache
223 *
224 * @param string $url CSS URL
225 * @param string $siteurl Site URL
226 *
227 * @return string
228 */
229 public function cache_bust_mtime( $url, $siteurl ) {
230 if ( strpos( $url, '?m=' ) ) {
231 return $url;
232 }
233
234 $parts = wp_parse_url( $url );
235 if ( ! isset( $parts['path'] ) || empty( $parts['path'] ) ) {
236 return $url;
237 }
238
239 $file = Helper::realpath( $url, $siteurl );
240
241 $mtime = false;
242 if ( file_exists( $file ) ) {
243 $mtime = filemtime( $file );
244 }
245
246 if ( ! $mtime ) {
247 return $url;
248 }
249
250 if ( false === strpos( $url, '?' ) ) {
251 $q = '';
252 } else {
253 list( $url, $q ) = explode( '?', $url, 2 );
254 if ( strlen( $q ) ) {
255 $q = '&amp;' . $q;
256 }
257 }
258
259 return "$url?m={$mtime}g{$q}";
260 }
261
262 /**
263 * @param $key
264 *
265 * @return bool
266 */
267 public function __isset( $key ) {
268 return isset( $this->old_styles->$key );
269 }
270
271 /**
272 * @param $key
273 */
274 public function __unset( $key ) {
275 unset( $this->old_styles->$key );
276 }
277
278 /**
279 * @param $key
280 *
281 * @return mixed
282 */
283 public function &__get( $key ) {
284 return $this->old_styles->$key;
285 }
286
287 /**
288 * @param $key
289 * @param $value
290 */
291 public function __set( $key, $value ) {
292 $this->old_styles->$key = $value;
293 }
294 }
295