PluginProbe ʕ •ᴥ•ʔ
WP Super Cache / 0.6.2
WP Super Cache v0.6.2
3.1.1 trunk 0.1 0.2 0.3 0.3.1 0.4 0.5 0.5.1 0.5.2 0.5.3 0.6.2 0.6.3 0.6.4 0.6.5 0.6.6 0.6.7 0.6.8 0.7 0.7.1 0.8 0.8.1 0.8.2 0.8.3 0.8.4 0.8.5 0.8.6 0.8.7 0.8.8 0.8.9 0.9 0.9.1 0.9.2 0.9.3 0.9.3.1 0.9.4 0.9.4.1 0.9.4.2 0.9.4.3 0.9.5 0.9.6 0.9.6.1 0.9.7 0.9.8 0.9.9 0.9.9.1 0.9.9.2 0.9.9.3 0.9.9.4 0.9.9.5 0.9.9.6 0.9.9.7 0.9.9.8 0.9.9.9 1.0 1.0.1 1.1 1.1.1 1.10.0 1.11.0 1.12.0 1.12.1 1.12.2 1.12.3 1.12.4 1.2 1.2.1 1.3 1.3.1 1.3.2 1.3.3 1.4 1.4.1 1.4.2 1.4.3 1.4.4 1.4.5 1.4.6 1.4.7 1.4.8 1.4.9 1.5.0 1.5.1 1.5.2 1.5.3 1.5.4 1.5.5 1.5.6 1.5.7 1.5.7.1 1.5.8 1.5.9 1.6.0 1.6.1 1.6.2 1.6.3 1.6.4 1.6.5 1.6.6 1.6.7 1.6.8 1.6.9 1.7.0 1.7.1 1.7.2 1.7.3 1.7.4 1.7.5 1.7.6 1.7.7 1.7.8 1.7.9 1.8 1.9 1.9.1 1.9.2 1.9.3 1.9.4 2.0.0 2.0.1 3.0.0 3.0.1 3.0.2 3.0.3 3.1.0
wp-super-cache / wp-cache-phase2.php
wp-super-cache Last commit date
plugins 18 years ago Changelog.txt 18 years ago readme.txt 18 years ago wp-cache-base.php 18 years ago wp-cache-config-sample.php 18 years ago wp-cache-phase1.php 18 years ago wp-cache-phase2.php 18 years ago wp-cache.php 18 years ago
wp-cache-phase2.php
481 lines
1 <?php
2
3 /** Diable here because PHP4.3 does not make the global
4 Serious bug?
5
6 $mutex_filename = 'wp_cache_mutex.lock';
7 $new_cache = false;
8 */
9
10 function wp_cache_phase2() {
11 global $cache_filename, $cache_acceptable_files, $wp_cache_meta_object;
12 global $wp_cache_gzip_encoding;
13
14 wp_cache_mutex_init();
15 if(function_exists('add_action') && ( !defined( 'WPLOCKDOWN' ) || ( defined( 'WPLOCKDOWN' ) && constant( 'WPLOCKDOWN' ) == '0' ) ) ) {
16 // Post ID is received
17 add_action('publish_post', 'wp_cache_post_change', 0);
18 add_action('edit_post', 'wp_cache_post_change', 0);
19 add_action('delete_post', 'wp_cache_post_change', 0);
20 add_action('publish_phone', 'wp_cache_post_change', 0);
21 // Coment ID is received
22 add_action('trackback_post', 'wp_cache_get_postid_from_comment', 0);
23 add_action('pingback_post', 'wp_cache_get_postid_from_comment', 0);
24 add_action('comment_post', 'wp_cache_get_postid_from_comment', 0);
25 add_action('edit_comment', 'wp_cache_get_postid_from_comment', 0);
26 add_action('wp_set_comment_status', 'wp_cache_get_postid_from_comment', 0);
27 // No post_id is available
28 add_action('delete_comment', 'wp_cache_no_postid', 0);
29 add_action('switch_theme', 'wp_cache_no_postid', 0);
30
31 do_cacheaction( 'add_cacheaction' );
32 }
33 if( $_SERVER["REQUEST_METHOD"] == 'POST' || get_option('gzipcompression'))
34 return;
35 $script = basename($_SERVER['PHP_SELF']);
36 if (!in_array($script, $cache_acceptable_files) &&
37 wp_cache_is_rejected($_SERVER["REQUEST_URI"]))
38 return;
39 if (wp_cache_user_agent_is_rejected()) return;
40 $wp_cache_meta_object = new CacheMeta;
41 ob_start('wp_cache_ob_callback');
42 register_shutdown_function('wp_cache_shutdown_callback');
43 }
44
45 function wp_cache_get_response_headers() {
46 if(function_exists('apache_response_headers')) {
47 flush();
48 $headers = apache_response_headers();
49 } else if(function_exists('headers_list')) {
50 $headers = array();
51 foreach(headers_list() as $hdr) {
52 list($header_name, $header_value) = explode(': ', $hdr, 2);
53 $headers[$header_name] = $header_value;
54 }
55 } else
56 $headers = null;
57
58 return $headers;
59 }
60
61 function wp_cache_is_rejected($uri) {
62 global $cache_rejected_uri;
63
64 if (strstr($uri, '/wp-admin/'))
65 return true; // we don't allow caching of wp-admin for security reasons
66 foreach ($cache_rejected_uri as $expr) {
67 if( preg_match( "~$expr~", $uri ) )
68 return true;
69 }
70 return false;
71 }
72
73 function wp_cache_user_agent_is_rejected() {
74 global $cache_rejected_user_agent;
75
76 if (!function_exists('apache_request_headers')) return false;
77 $headers = apache_request_headers();
78 if (!isset($headers["User-Agent"])) return false;
79 foreach ($cache_rejected_user_agent as $expr) {
80 if (strlen($expr) > 0 && stristr($headers["User-Agent"], $expr))
81 return true;
82 }
83 return false;
84 }
85
86
87 function wp_cache_mutex_init() {
88 global $use_flock, $mutex, $cache_path, $mutex_filename, $sem_id;
89
90 if(!is_bool($use_flock)) {
91 if(function_exists('sem_get'))
92 $use_flock = false;
93 else
94 $use_flock = true;
95 }
96
97 $mutex = false;
98 if ($use_flock)
99 $mutex = @fopen($cache_path . $mutex_filename, 'w');
100 else
101 $mutex = @sem_get($sem_id, 1, 0644 | IPC_CREAT, 1);
102 }
103
104 function wp_cache_writers_entry() {
105 global $use_flock, $mutex, $cache_path, $mutex_filename;
106
107 if( !$mutex )
108 return false;
109
110 if ($use_flock)
111 flock($mutex, LOCK_EX);
112 else
113 sem_acquire($mutex);
114
115 return true;
116 }
117
118 function wp_cache_writers_exit() {
119 global $use_flock, $mutex, $cache_path, $mutex_filename;
120
121 if( !$mutex )
122 return false;
123
124 if ($use_flock)
125 flock($mutex, LOCK_UN);
126 else
127 sem_release($mutex);
128 }
129
130 function wp_cache_ob_callback($buffer) {
131 global $cache_path, $cache_filename, $meta_file, $wp_start_time, $supercachedir;
132 global $new_cache, $wp_cache_meta_object, $file_expired, $blog_id, $cache_compression;
133 global $wp_cache_gzip_encoding, $super_cache_enabled, $cached_direct_pages;
134
135 /* Mode paranoic, check for closing tags
136 * we avoid caching incomplete files */
137 if (is_404() || !preg_match('/(<\/html>|<\/rss>|<\/feed>)/i',$buffer) ) {
138 $new_cache = false;
139 return $buffer;
140 }
141
142 $duration = wp_cache_microtime_diff($wp_start_time, microtime());
143 $duration = sprintf("%0.3f", $duration);
144 $buffer .= "\n<!-- Dynamic Page Served (once) in $duration seconds -->\n";
145
146 if( !wp_cache_writers_entry() )
147 return false;
148 $mtime = @filemtime($cache_path . $cache_filename);
149 /* Return if:
150 the file didn't exist before but it does exist now (another connection created)
151 OR
152 the file was expired and its mtime is less than 5 seconds
153 */
154 if( !((!$file_expired && $mtime) || ($mtime && $file_expired && (time() - $mtime) < 5)) ) {
155 $uri = preg_replace('/[ <>\'\"\r\n\t\(\)]/', '', str_replace( '/index.php', '/', str_replace( '..', '', $_SERVER['REQUEST_URI']) ) );
156 $dir = strtolower(preg_replace('/:.*$/', '', $_SERVER["HTTP_HOST"])) . $uri; // To avoid XSS attacs
157 $dir = trailingslashit( $cache_path . 'supercache/' . $dir );
158 if( is_array( $cached_direct_pages ) && in_array( $_SERVER[ 'REQUEST_URI' ], $cached_direct_pages ) ) {
159 $dir = trailingslashit( ABSPATH . $uri );
160 }
161 $supercachedir = $cache_path . 'supercache/' . preg_replace('/:.*$/', '', $_SERVER["HTTP_HOST"]);
162 if( !empty( $_GET ) || is_feed() || ( $super_cache_enabled == true && is_dir( substr( $supercachedir, 0, -1 ) . '.disabled' ) ) )
163 $super_cache_enabled = false;
164
165 $fr = @fopen($cache_path . $cache_filename, 'w');
166 if (!$fr)
167 $buffer = "Couldn't write to: " . $cache_path . $cache_filename . "\n";
168 if( $super_cache_enabled ) {
169 $dir = str_replace( '//', '/', $dir );
170 if( @is_dir( $dir ) == false )
171 @wp_mkdir_p( $dir );
172
173 $user_info = wp_cache_get_cookies_values();
174 $do_cache = apply_filters( 'do_createsupercache', $user_info );
175 if( $user_info == '' || $do_cache === true ) {
176 $fr2 = @fopen("{$dir}index.html", 'w');
177 if( $cache_compression )
178 $gz = @gzopen("{$dir}index.html.gz", 'w3');
179 }
180 }
181
182 if (preg_match('/<!--mclude|<!--mfunc/', $buffer)) { //Dynamic content
183 $store = preg_replace('|<!--mclude (.*?)-->(.*?)<!--/mclude-->|is',
184 "<!--mclude-->\n<?php include_once('" . ABSPATH . "$1'); ?>\n<!--/mclude-->", $buffer);
185 $store = preg_replace('|<!--mfunc (.*?)-->(.*?)<!--/mfunc-->|is',
186 "<!--mfunc-->\n<?php $1 ;?>\n<!--/mfunc-->", $store);
187 $wp_cache_meta_object->dynamic = true;
188 /* Clean function calls in tag */
189 $buffer = preg_replace('|<!--mclude (.*?)-->|is', '<!--mclude-->', $buffer);
190 $buffer = preg_replace('|<!--mfunc (.*?)-->|is', '<!--mfunc-->', $buffer);
191 fputs($fr, $store);
192 if( $fr2 )
193 fputs($fr2, $store . '<!-- super cache -->' );
194 if( $gz )
195 gzwrite($gz, $store . '<!-- super cache gz -->' );
196 } else {
197 $log = "<!-- Cached page served by WP-Cache -->\n";
198
199 if ($wp_cache_gzip_encoding) {
200 $log .= "<!-- Compression = " . $wp_cache_gzip_encoding ." -->";
201 $gzdata = gzencode($buffer . $log, 3, FORCE_GZIP);
202 $gzsize = strlen($gzdata);
203
204 array_push($wp_cache_meta_object->headers, 'Content-Encoding: ' . $wp_cache_gzip_encoding);
205 array_push($wp_cache_meta_object->headers, 'Vary: Accept-Encoding');
206 array_push($wp_cache_meta_object->headers, 'Content-Length: ' . strlen($gzdata));
207 // Return uncompressed data & store compressed for later use
208 fputs($fr, $gzdata);
209 }else{ // no compression
210 fputs($fr, $buffer.$log);
211 }
212 if( $fr2 )
213 fputs($fr2, $buffer . '<!-- super cache -->' );
214 if( $gz )
215 gzwrite($gz, $buffer . '<!-- super cache gz -->' );
216 }
217 $new_cache = true;
218 fclose($fr);
219 if( $fr2 )
220 fclose($fr2);
221 if( $gz )
222 fclose($gz);
223 }
224 wp_cache_writers_exit();
225 return $buffer;
226 }
227
228 function wp_cache_phase2_clean_cache($file_prefix) {
229 global $cache_path;
230
231 if( !wp_cache_writers_entry() )
232 return false;
233 if ( ($handle = opendir( $cache_path )) ) {
234 while ( false !== ($file = readdir($handle))) {
235 if ( preg_match("/^$file_prefix/", $file) ) {
236 @unlink($cache_path . $file);
237 }
238 }
239 closedir($handle);
240 }
241 wp_cache_writers_exit();
242 }
243
244 function prune_super_cache($directory, $force = false) {
245 global $super_cache_max_time, $cache_path;
246
247 if( !isset( $super_cache_max_time ) )
248 $super_cache_max_time = 21600;
249
250 $now = time();
251
252 $protected_directories = array( $cache_path . '.htaccess', $cache_path . 'meta', $cache_path . 'supercache' );
253
254 $oktodelete = false;
255 if (is_dir($directory)) {
256 $directory = trailingslashit( $directory );
257 $entries = glob($directory. '*');
258 if( is_array( $entries ) && !empty( $entries ) ) foreach ($entries as $entry) {
259 if ($entry != '.' && $entry != '..') {
260 prune_super_cache($entry, $force);
261 if( is_dir( $entry ) && ( $force || @filemtime( $entry ) + $super_cache_max_time <= $now ) ) {
262 $oktodelete = true;
263 if( in_array( $entry, $protected_directories ) )
264 $oktodelete = false;
265 if( $oktodelete )
266 @rmdir( addslashes( $entry ) );
267 }
268 }
269 }
270 } else {
271 if( is_file($directory) && ($force || filemtime( $directory ) + $super_cache_max_time <= $now ) ) {
272 $oktodelete = true;
273 if( in_array( $directory, $protected_directories ) )
274 $oktodelete = false;
275 if( $oktodelete )
276 @unlink( addslashes( $directory ) );
277 }
278 }
279 }
280
281 function wp_cache_phase2_clean_expired($file_prefix) {
282 global $cache_path, $cache_max_time;
283
284 clearstatcache();
285 if( !wp_cache_writers_entry() )
286 return false;
287 $now = time();
288 if ( ($handle = opendir( $cache_path )) ) {
289 while ( false !== ($file = readdir($handle))) {
290 if ( preg_match("/^$file_prefix/", $file) &&
291 (filemtime($cache_path . $file) + $cache_max_time) <= $now ) {
292 @unlink($cache_path . $file);
293 @unlink($cache_path . 'meta/' . str_replace( '.html', '.meta', $file ) );
294 continue;
295 }
296 if($file != '.' && $file != '..') {
297 if( is_dir( $cache_path . $file ) == false && (filemtime($cache_path . $file) + $cache_max_time) <= $now ) {
298 if( substr( $file, -9 ) != '.htaccess' )
299 @unlink($cache_path . $file);
300 } elseif( is_dir( $cache_path . $file ) ) {
301 prune_super_cache( $cache_path . $file );
302 }
303 }
304 }
305 closedir($handle);
306 }
307
308 wp_cache_writers_exit();
309 }
310
311 function wp_cache_shutdown_callback() {
312 global $cache_path, $cache_max_time, $file_expired, $file_prefix, $meta_file, $new_cache;
313 global $wp_cache_meta_object, $known_headers, $blog_id;
314
315 $wp_cache_meta_object->uri = $_SERVER["SERVER_NAME"].preg_replace('/[ <>\'\"\r\n\t\(\)]/', '', $_SERVER['REQUEST_URI']); // To avoid XSS attacs
316 $wp_cache_meta_object->blog_id=$blog_id;
317 $wp_cache_meta_object->post = wp_cache_post_id();
318
319 $response = wp_cache_get_response_headers();
320 foreach ($known_headers as $key) {
321 if(isset($response{$key})) {
322 array_push($wp_cache_meta_object->headers, "$key: " . $response{$key});
323 }
324 }
325 /* Not used because it gives problems with some
326 * PHP installations
327 if (!$response{'Content-Length'}) {
328 // WP does not set content size
329 $content_size = ob_get_length();
330 @header("Content-Length: $content_size");
331 array_push($wp_cache_meta_object->headers, "Content-Length: $content_size");
332 }
333 */
334 if (!$response{'Last-Modified'}) {
335 $value = gmdate('D, d M Y H:i:s') . ' GMT';
336 /* Dont send this the first time */
337 /* @header('Last-Modified: ' . $value); */
338 array_push($wp_cache_meta_object->headers, "Last-Modified: $value");
339 }
340 if (!$response{'Content-Type'} && !$response{'Content-type'}) {
341 // On some systems, headers set by PHP can't be fetched from
342 // the output buffer. This is a last ditch effort to set the
343 // correct Content-Type header for feeds, if we didn't see
344 // it in the response headers already. -- dougal
345 if (is_feed()) {
346 $type = get_query_var('feed');
347 $type = str_replace('/','',$type);
348 switch ($type) {
349 case 'atom':
350 $value = "application/atom+xml";
351 break;
352 case 'rdf':
353 $value = "application/rdf+xml";
354 break;
355 case 'rss':
356 case 'rss2':
357 default:
358 $value = "application/rss+xml";
359 }
360 } else { // not a feed
361 $value = 'text/html';
362 }
363 $value .= "; charset=\"" . get_option('blog_charset') . "\"";
364
365 @header("Content-Type: $value");
366 array_push($wp_cache_meta_object->headers, "Content-Type: $value");
367 }
368
369 ob_end_flush();
370 if ($new_cache) {
371 $serial = serialize($wp_cache_meta_object);
372 if( !wp_cache_writers_entry() )
373 return false;
374 $fr = @fopen($cache_path . 'meta/' . $meta_file, 'w');
375 if( !$fr )
376 @mkdir( $cache_path . 'meta' );
377 $fr = fopen($cache_path . 'meta/' . $meta_file, 'w');
378 fputs($fr, $serial);
379 fclose($fr);
380 wp_cache_writers_exit();
381 }
382
383 if ($file_expired == false) {
384 return;
385 }
386
387 // we delete expired files
388 flush(); //Ensure we send data to the client
389 wp_cache_phase2_clean_expired($file_prefix);
390 }
391
392 function wp_cache_no_postid($id) {
393 return wp_cache_post_change(wp_cache_post_id());
394 }
395
396 function wp_cache_get_postid_from_comment($comment_id) {
397 global $super_cache_enabled;
398 $comment = get_commentdata($comment_id, 1, true);
399 $postid = $comment['comment_post_ID'];
400 // Do nothing if comment is not moderated
401 // http://ocaoimh.ie/2006/12/05/caching-wordpress-with-wp-cache-in-a-spam-filled-world
402 if( !preg_match('/wp-admin\//', $_SERVER['REQUEST_URI']) )
403 if( $comment['comment_approved'] == 'spam' ) { // changed from 1 to "spam"
404 return $post_id;
405 } elseif( $comment['comment_approved'] == '0' ) {
406 $super_cache_enabled = 0; // don't remove the super cache static file until comment is approved
407 }
408 // We must check it up again due to WP bugs calling two different actions
409 // for delete, for example both wp_set_comment_status and delete_comment
410 // are called when deleting a comment
411 if ($postid > 0)
412 return wp_cache_post_change($postid);
413 else
414 return wp_cache_post_change(wp_cache_post_id());
415 }
416
417 function wp_cache_post_change($post_id) {
418 global $file_prefix, $cache_path, $blog_id, $blogcacheid, $super_cache_enabled;
419 static $last_processed = -1;
420
421 // Avoid cleaning twice the same pages
422 if ($post_id == $last_processed) return $post_id;
423 $last_processed = $post_id;
424 $permalink = trailingslashit( str_replace( get_option( 'siteurl' ), '', post_permalink( $post_id ) ) );
425 if( $super_cache_enabled ) {
426 $permalink = trailingslashit( str_replace( get_option( 'siteurl' ), '', post_permalink( $post_id ) ) );
427 $siteurl = str_replace( 'http://', '', get_option( 'siteurl' ) );
428 $dir = $cache_path . 'supercache/' . strtolower(preg_replace('/:.*$/', '', $siteurl ) );
429 $files_to_delete = array( $dir . '/index.html', $dir . '/feed/index.html', $dir . $permalink . 'index.html', $dir . $permalink . 'feed/index.html' );
430 foreach( $files_to_delete as $cache_file ) {
431 @unlink( $cache_file );
432 @unlink( $cache_file . '.gz' );
433 }
434 }
435
436 $meta = new CacheMeta;
437 $matches = array();
438 if( !wp_cache_writers_entry() )
439 return $post_id;
440 if ( ($handle = opendir( $cache_path . 'meta/' )) ) {
441 while ( false !== ($file = readdir($handle))) {
442 if ( preg_match("/^({$file_prefix}{$blogcacheid}.*)\.meta/", $file, $matches) ) {
443 $meta_pathname = $cache_path . 'meta/' . $file;
444 $content_pathname = $cache_path . $matches[1] . ".html";
445 $meta = unserialize(@file_get_contents($meta_pathname));
446 if ($post_id > 0 && $meta) {
447 if ($meta->blog_id == $blog_id && (!$meta->post || $meta->post == $post_id) ) {
448 @unlink($meta_pathname);
449 @unlink($content_pathname);
450 }
451 } elseif ($meta->blog_id == $blog_id) {
452 @unlink($meta_pathname);
453 @unlink($content_pathname);
454 }
455
456 }
457 }
458 closedir($handle);
459 }
460 wp_cache_writers_exit();
461 return $post_id;
462 }
463
464 function wp_cache_microtime_diff($a, $b) {
465 list($a_dec, $a_sec) = explode(' ', $a);
466 list($b_dec, $b_sec) = explode(' ', $b);
467 return $b_sec - $a_sec + $b_dec - $a_dec;
468 }
469
470 function wp_cache_post_id() {
471 global $posts, $comment_post_ID, $post_ID;
472 // We try hard all options. More frequent first.
473 if ($post_ID > 0 ) return $post_ID;
474 if ($comment_post_ID > 0 ) return $comment_post_ID;
475 if (is_single() || is_page()) return $posts[0]->ID;
476 if ($_GET['p'] > 0) return $_GET['p'];
477 if ($_POST['p'] > 0) return $_POST['p'];
478 return 0;
479 }
480 ?>
481