diff --git a/wp-cache-phase1.php b/wp-cache-phase1.php
index d638f351..302f9a8a 100644
--- a/wp-cache-phase1.php
+++ b/wp-cache-phase1.php
@@ -96,13 +96,19 @@
$cache_filename = '';
$meta_file = '';
$wp_cache_gzip_encoding = '';
+$wp_cache_br_encoding = '';
$gzipped = 0;
$gzsize = 0;
+$brotlied = 0;
+$brsize = 0;
if ( $cache_compression ) {
$wp_cache_gzip_encoding = gzip_accepted();
}
+if ( $cache_compression_br ) {
+ $wp_cache_br_encoding = br_accepted();
+}
add_cacheaction( 'supercache_filename_str', 'wp_cache_check_mobile' );
if ( function_exists( 'add_filter' ) ) { // loaded since WordPress 4.6
diff --git a/wp-cache-phase2.php b/wp-cache-phase2.php
index ec4dc94f..17b2c711 100644
--- a/wp-cache-phase2.php
+++ b/wp-cache-phase2.php
@@ -8,6 +8,14 @@ function gzip_accepted(){
return 'gzip';
}
+function br_accepted(){
+ if ( 1 == ini_get( 'zlib.output_compression' ) || "on" == strtolower( ini_get( 'zlib.output_compression' ) ) ) // don't compress WP-Cache data files when PHP is already doing it
+ return false;
+
+ if ( !isset( $_SERVER[ 'HTTP_ACCEPT_ENCODING' ] ) || ( isset( $_SERVER[ 'HTTP_ACCEPT_ENCODING' ] ) && strpos( $_SERVER[ 'HTTP_ACCEPT_ENCODING' ], 'br' ) === false ) ) return false;
+ return 'br';
+}
+
function setup_blog_cache_dir() {
global $blog_cache_dir, $cache_path;
if( false == @is_dir( $blog_cache_dir ) ) {
@@ -20,7 +28,7 @@ function setup_blog_cache_dir() {
}
function get_wp_cache_key( $url = false ) {
- global $wp_cache_request_uri, $wp_cache_gzip_encoding, $WPSC_HTTP_HOST;
+ global $wp_cache_request_uri, $wp_cache_gzip_encoding, $wp_cache_br_encoding, $WPSC_HTTP_HOST;
if ( ! $url ) {
$url = $wp_cache_request_uri;
}
@@ -43,8 +51,8 @@ function wp_super_cache_init() {
}
function wp_cache_serve_cache_file() {
- global $key, $blogcacheid, $wp_cache_request_uri, $file_prefix, $blog_cache_dir, $meta_file, $cache_file, $cache_filename, $meta_pathname, $wp_cache_gzip_encoding, $meta;
- global $cache_compression, $wp_cache_slash_check, $wp_supercache_304, $wp_cache_home_path, $wp_cache_no_cache_for_get;
+ global $key, $blogcacheid, $wp_cache_request_uri, $file_prefix, $blog_cache_dir, $meta_file, $cache_file, $cache_filename, $meta_pathname, $wp_cache_gzip_encoding, $wp_cache_br_encoding, $meta;
+ global $cache_compression, $cache_compression_br, $wp_cache_slash_check, $wp_supercache_304, $wp_cache_home_path, $wp_cache_no_cache_for_get;
global $wp_cache_disable_utf8, $wp_cache_mfunc_enabled, $wpsc_served_header;
if ( wpsc_is_backend() ) {
@@ -132,6 +140,14 @@ function wp_cache_serve_cache_file() {
$cachefiledata = gzencode( file_get_contents( $file ), 6, FORCE_GZIP );
wp_cache_debug( "Fetched static page data from supercache file using PHP and gzipped it. File: $file" );
}
+ } elseif ( $wp_cache_br_encoding ) {
+ if ( file_exists( $file . '.br' ) ) {
+ $cachefiledata = file_get_contents( $file . '.br' );
+ wp_cache_debug( "Fetched br static page data from supercache file using PHP. File: $file.br" );
+ } else {
+ $cachefiledata = brotli_compress( file_get_contents( $file ), BROTLI_COMPRESS_LEVEL_DEFAULT, BROTLI_TEXT );
+ wp_cache_debug( "Fetched static page data from supercache file using PHP and brotli'd it. File: $file" );
+ }
} else {
$cachefiledata = file_get_contents( $file );
wp_cache_debug( "Fetched static page data from supercache file using PHP. File: $file" );
@@ -142,6 +158,9 @@ function wp_cache_serve_cache_file() {
if ( $wp_cache_gzip_encoding ) {
$cachefiledata = gzencode( $cachefiledata, 6, FORCE_GZIP );
wp_cache_debug( "Fetched dynamic page data from supercache file using PHP and gzipped it. File: $file" );
+ } elseif ( $wp_cache_br_encoding ) {
+ $cachefiledata = brotli_compress( file_get_contents( $file ), BROTLI_COMPRESS_LEVEL_DEFAULT, BROTLI_TEXT );
+ wp_cache_debug( "Fetched dynamic page data from supercache file using PHP and brotli'd it. File: $file" );
} else {
wp_cache_debug( "Fetched dynamic page data from supercache file using PHP. File: $file" );
}
@@ -171,6 +190,12 @@ function wp_cache_serve_cache_file() {
}
header( 'Content-Encoding: ' . $wp_cache_gzip_encoding );
header( 'Content-Length: ' . $size );
+ } elseif ( $wp_cache_br_encoding ) {
+ if ( isset( $wpsc_served_header ) && $wpsc_served_header ) {
+ header( "X-WP-Super-Cache: Served supercache br file from PHP" );
+ }
+ header( 'Content-Encoding: ' . $wp_cache_br_encoding );
+ header( 'Content-Length: ' . $size );
} elseif ( $wp_supercache_304 ) {
if ( isset( $wpsc_served_header ) && $wpsc_served_header ) {
header( "X-WP-Super-Cache: Served supercache 304 file from PHP" );
@@ -847,6 +872,7 @@ function get_all_supercache_filenames( $dir = '' ) {
foreach( $filenames as $file ) {
$out[] = $file;
$out[] = $file . '.gz';
+ $out[] = $file . '.br';
}
return $out;
@@ -1967,8 +1993,8 @@ function wp_cache_maybe_dynamic( &$buffer ) {
function wp_cache_get_ob(&$buffer) {
global $cache_enabled, $cache_path, $cache_filename, $wp_start_time, $supercachedir;
- global $new_cache, $wp_cache_meta, $cache_compression, $wp_super_cache_query;
- global $wp_cache_gzip_encoding, $super_cache_enabled;
+ global $new_cache, $wp_cache_meta, $cache_compression, $cache_compression_br, $wp_super_cache_query;
+ global $wp_cache_gzip_encoding, $wp_cache_br_encoding, $super_cache_enabled;
global $gzsize, $supercacheonly;
global $blog_cache_dir, $wp_supercache_cache_list;
global $wp_cache_not_logged_in, $cache_max_time;
@@ -2086,7 +2112,7 @@ function wp_cache_get_ob(&$buffer) {
return $buffer;
}
- $fr = $fr2 = $gz = false;
+ $fr = $fr2 = $gz = $br = false;
// Open wp-cache cache file
if ( ! $supercacheonly ) {
$fr = @fopen( $tmp_wpcache_filename, 'w' );
@@ -2134,6 +2160,24 @@ function wp_cache_get_ob(&$buffer) {
wp_cache_writers_exit();
return wp_cache_maybe_dynamic( $buffer );
}
+ } elseif (
+ $cache_compression_br &&
+ (
+ ! isset( $wp_cache_mfunc_enabled ) ||
+ $wp_cache_mfunc_enabled == 0
+ )
+ ) { // don't want to store compressed files if using dynamic content
+ $br = @fopen( $tmp_cache_filename . ".br", 'w');
+ if ( !$br ) {
+ wp_cache_debug( 'Error. Supercache could not write to ' . str_replace( ABSPATH, '', $tmp_cache_filename ) . ".br", 1 );
+ wp_cache_add_to_buffer( $buffer, "File not cached! Super Cache Couldn't write to: " . str_replace( ABSPATH, '', $tmp_cache_filename ) . ".br" );
+ @fclose( $fr );
+ @unlink( $tmp_wpcache_filename );
+ @fclose( $fr2 );
+ @unlink( $tmp_cache_filename );
+ wp_cache_writers_exit();
+ return wp_cache_maybe_dynamic( $buffer );
+ }
}
}
}
@@ -2177,6 +2221,12 @@ function wp_cache_get_ob(&$buffer) {
$gzdata = gzencode( $buffer, 6, FORCE_GZIP );
$gzsize = function_exists( 'mb_strlen' ) ? mb_strlen( $gzdata, '8bit' ) : strlen( $gzdata );
}
+ if ( $cache_compression_br && $wp_cache_br_encoding ) {
+ wp_cache_debug( 'Brotling dynamic buffer for display.', 5 );
+ wp_cache_add_to_buffer( $buffer, "Compression = br" );
+ $brdata = brotli_compress( $buffer, BROTLI_COMPRESS_LEVEL_DEFAULT, BROTLI_TEXT );
+ $brsize = function_exists( 'mb_strlen' ) ? mb_strlen( $brdata, '8bit' ) : strlen( $brdata );
+ }
} else {
if ( defined( 'WPSC_VARY_HEADER' ) ) {
if ( WPSC_VARY_HEADER != '' ) {
@@ -2202,6 +2252,18 @@ function wp_cache_get_ob(&$buffer) {
wp_cache_debug( 'Writing gzipped buffer to wp-cache cache file.', 5 );
fputs($fr, '' . $gzdata);
}
+ } elseif ( $br || $wp_cache_br_encoding ) {
+ wp_cache_debug( 'Brotling buffer.', 5 );
+ wp_cache_add_to_buffer( $buffer, "Compression = br" );
+ $brdata = brotli_compress( $buffer, BROTLI_COMPRESS_LEVEL_DEFAULT, BROTLI_TEXT );
+ $brsize = function_exists( 'mb_strlen' ) ? mb_strlen( $brdata, '8bit' ) : strlen( $brdata );
+
+ $wp_cache_meta[ 'headers' ][ 'Content-Encoding' ] = 'Content-Encoding: ' . $wp_cache_br_encoding;
+ // Return uncompressed data & store compressed for later use
+ if ( $fr ) {
+ wp_cache_debug( 'Writing brotli\d buffer to wp-cache cache file.', 5 );
+ fputs($fr, '' . $brdata);
+ }
} else { // no compression
if ( $fr ) {
wp_cache_debug( 'Writing non-gzipped buffer to wp-cache cache file.' );
@@ -2217,6 +2279,10 @@ function wp_cache_get_ob(&$buffer) {
wp_cache_debug( 'Writing gzipped buffer to supercache file.' );
fwrite($gz, $gzdata );
}
+ if ( isset( $brdata ) && $br ) {
+ wp_cache_debug( 'Writing brotli\'d buffer to supercache file.' );
+ fwrite($br, $brdata );
+ }
}
$new_cache = true;
@@ -2275,6 +2341,20 @@ function wp_cache_get_ob(&$buffer) {
$added_cache = 1;
}
}
+ if ( $br ) {
+ fclose( $br );
+ if ( filesize( $tmp_cache_filename . '.br' ) == 0 ) {
+ wp_cache_debug( "Warning! The file {$tmp_cache_filename}.br was empty. Did not rename to {$cache_fname}.br", 5 );
+ @unlink( $tmp_cache_filename . '.br' );
+ } else {
+ if ( ! @rename( $tmp_cache_filename . '.br', $cache_fname . '.br' ) ) {
+ @unlink( $cache_fname . '.br' );
+ @rename( $tmp_cache_filename . '.br', $cache_fname . '.br' );
+ }
+ wp_cache_debug( "Renamed temp supercache br file to {$cache_fname}.br", 5 );
+ $added_cache = 1;
+ }
+ }
if ( $added_cache && isset( $wp_supercache_cache_list ) && $wp_supercache_cache_list ) {
update_option( 'wpsupercache_count', ( get_option( 'wpsupercache_count' ) + 1 ) );
@@ -2302,6 +2382,23 @@ function wp_cache_get_ob(&$buffer) {
}
header( 'Content-Length: ' . $gzsize );
return $gzdata;
+ } elseif ( !headers_sent() && $wp_cache_br_encoding && $brdata) {
+ wp_cache_debug( 'Writing br content headers. Sending buffer to browser', 5 );
+ header( 'Content-Encoding: ' . $wp_cache_br_encoding );
+ if ( defined( 'WPSC_VARY_HEADER' ) ) {
+ if ( WPSC_VARY_HEADER != '' ) {
+ $vary_header = WPSC_VARY_HEADER;
+ } else {
+ $vary_header = '';
+ }
+ } else {
+ $vary_header = 'Accept-Encoding, Cookie';
+ }
+ if ( $vary_header ) {
+ header( 'Vary: ' . $vary_header );
+ }
+ header( 'Content-Length: ' . $brsize );
+ return $brdata;
} else {
wp_cache_debug( 'Sending buffer to browser', 5 );
return $buffer;
@@ -2540,7 +2637,7 @@ function wp_cache_phase2_clean_expired( $file_prefix, $force = false ) {
}
function wp_cache_shutdown_callback() {
- global $cache_max_time, $meta_file, $new_cache, $wp_cache_meta, $known_headers, $blog_id, $wp_cache_gzip_encoding, $supercacheonly, $blog_cache_dir;
+ global $cache_max_time, $meta_file, $new_cache, $wp_cache_meta, $known_headers, $blog_id, $wp_cache_gzip_encoding, $wp_cache_br_encoding, $supercacheonly, $blog_cache_dir;
global $wp_cache_request_uri, $wp_cache_key, $cache_enabled, $wp_cache_blog_charset, $wp_cache_not_logged_in;
global $WPSC_HTTP_HOST, $wp_super_cache_query;
diff --git a/wp-cache.php b/wp-cache.php
index a01cc96e..72d33bc3 100644
--- a/wp-cache.php
+++ b/wp-cache.php
@@ -1,10 +1,10 @@
' . __( "Warning! You attempted to enable compression but zlib.output_compression is enabled. See #21 in the Troubleshooting section of the readme file.", 'wp-super-cache' ) . '';
} else {
@@ -756,6 +765,14 @@ function wp_cache_manager_updates() {
prune_super_cache( $cache_path, true );
delete_option( 'super_cache_meta' );
}
+ // Brotli
+ if ( $new_cache_compression_br != $cache_compression_br ) {
+ $cache_compression_br = $new_cache_compression_br;
+ wp_cache_replace_line('^ *\$cache_compression_br', "\$cache_compression_br = " . $cache_compression_br . ";", $wp_cache_config_file);
+ if ( function_exists( 'prune_super_cache' ) )
+ prune_super_cache( $cache_path, true );
+ delete_option( 'super_cache_meta' );
+ }
}
}
}
@@ -764,7 +781,7 @@ function wp_cache_manager_updates() {
add_action( 'admin_init', 'wp_cache_manager_updates' );
function wp_cache_manager() {
- global $wp_cache_config_file, $valid_nonce, $supercachedir, $cache_path, $cache_enabled, $cache_compression, $super_cache_enabled;
+ global $wp_cache_config_file, $valid_nonce, $supercachedir, $cache_path, $cache_enabled, $cache_compression, $cache_compression_br, $super_cache_enabled;
global $wp_cache_clear_on_post_edit, $cache_rebuild_files, $wp_cache_mutex_disabled, $wp_cache_mobile_enabled, $wp_cache_mobile_browsers, $wp_cache_no_cache_for_get;
global $wp_cache_not_logged_in, $wp_cache_make_known_anon, $wp_supercache_cache_list, $cache_page_secret;
global $wp_super_cache_front_page_check, $wp_cache_refresh_single_only, $wp_cache_mobile_prefixes;
@@ -1097,6 +1114,12 @@ function toggleLayer( whichLayer ) {
+
+
+
+
+
+
@@ -2737,7 +2760,7 @@ function wp_cache_format_fsize( $fsize ) {
}
function wp_cache_regenerate_cache_file_stats() {
- global $cache_compression, $supercachedir, $file_prefix, $wp_cache_preload_on, $cache_max_time;
+ global $cache_compression, $cache_compression_br, $supercachedir, $file_prefix, $wp_cache_preload_on, $cache_max_time;
if ( $supercachedir == '' )
$supercachedir = get_supercache_dir();
@@ -2766,7 +2789,7 @@ function wp_cache_regenerate_cache_file_stats() {
$sizes[ $cache_type ][ $status ] = $cached_list;
}
}
- if ( $cache_compression ) {
+ if ( $cache_compression || $cache_compression_br ) {
$sizes[ 'supercache' ][ 'cached' ] = intval( $sizes[ 'supercache' ][ 'cached' ] / 2 );
$sizes[ 'supercache' ][ 'expired' ] = intval( $sizes[ 'supercache' ][ 'expired' ] / 2 );
}