Ejemplo n.º 1
0
 /**
  * OB callback
  *
  * @param string $buffer
  * @return string
  */
 function ob_callback(&$buffer)
 {
     if ($buffer != '' && w3_is_xml($buffer)) {
         if ($this->can_minify2($buffer)) {
             /**
              * Replace script and style tags
              */
             if (function_exists('is_feed') && !is_feed()) {
                 w3_require_once(W3TC_INC_DIR . '/functions/extract.php');
                 $head_prepend = '';
                 $body_prepend = '';
                 $body_append = '';
                 $embed_extsrcjs = false;
                 if ($this->_config->get_boolean('minify.auto')) {
                     if ($this->_config->get_boolean('minify.js.enable')) {
                         $ignore_js_files = $this->_config->get_array('minify.reject.files.js');
                         $embed_type = $this->_config->get_string('minify.js.header.embed_type');
                         $embed_type = $embed_type == 'extsrc' || $embed_type == 'asyncsrc' ? 'blocking' : $embed_type;
                         $embed_pos = strpos($buffer, '<!-- W3TC-include-js-head -->');
                         $buffer = str_replace('<!-- W3TC-include-js-head -->', '', $buffer);
                         if ($embed_pos === false) {
                             preg_match('~<head(\\s+[^<>]+)*>~Ui', $buffer, $match, PREG_OFFSET_CAPTURE);
                             $embed_pos = strlen($match[0][0]) + $match[0][1];
                         }
                         $ignore_js_files = array_map('w3_normalize_file', $ignore_js_files);
                         $files_to_minify = array();
                         $handled_scripts = array();
                         $script_tags = w3_extract_js2($buffer);
                         $previous_file_was_ignored = false;
                         foreach ($script_tags as $script_tag) {
                             $tag_pos = strpos($buffer, $script_tag);
                             $match = array();
                             preg_match('~<script\\s+[^<>]*src=["\']?([^"\']+)["\']?[^<>]*>\\s*</script>~is', $script_tag, $match);
                             $file = $match[1];
                             $file = w3_normalize_file_minify2($file);
                             $script_len = strlen($script_tag);
                             if (!$this->_filter_files($file) || in_array($file, $handled_scripts)) {
                                 continue;
                             }
                             $handled_scripts[] = $file;
                             $this->replaced_scripts[] = $file;
                             if (in_array($file, $ignore_js_files)) {
                                 if ($tag_pos > $embed_pos) {
                                     if ($files_to_minify) {
                                         $script = $this->get_script_custom($files_to_minify, $embed_type);
                                         $buffer = substr_replace($buffer, $script, $embed_pos, 0);
                                         $files_to_minify = array();
                                         $script_len = $script_len + strlen($script);
                                     }
                                     $embed_pos = $embed_pos + $script_len;
                                     $previous_file_was_ignored = true;
                                 }
                             } else {
                                 $buffer = substr_replace($buffer, '', $tag_pos, $script_len);
                                 if ($embed_pos > $tag_pos) {
                                     $embed_pos -= $script_len;
                                 } elseif ($previous_file_was_ignored) {
                                     $embed_pos = $tag_pos;
                                 }
                                 $files_to_minify[] = $file;
                             }
                         }
                         $script = $this->get_script_custom($files_to_minify, $embed_type);
                         $buffer = substr_replace($buffer, $script, $embed_pos, 0);
                     }
                     if ($this->_config->get_boolean('minify.css.enable')) {
                         $ignore_css_files = $this->_config->get_array('minify.reject.files.css');
                         $files_to_minify = array();
                         $embed_pos = strpos($buffer, '<!-- W3TC-include-css -->');
                         $buffer = str_replace('<!-- W3TC-include-css -->', '', $buffer);
                         if ($embed_pos === false) {
                             preg_match('~<head(\\s+[^<>]+)*>~Ui', $buffer, $match, PREG_OFFSET_CAPTURE);
                             $embed_pos = strlen($match[0][0]) + $match[0][1];
                         }
                         $ignore_css_files = array_map('w3_normalize_file', $ignore_css_files);
                         $handled_styles = array();
                         $style_tags = w3_extract_css2($buffer);
                         $previous_file_was_ignored = false;
                         foreach ($style_tags as $style_tag_tuple) {
                             $style_tag = $style_tag_tuple[0];
                             $tag_pos = strpos($buffer, $style_tag);
                             $match = array();
                             $file = $style_tag_tuple[1];
                             $file = w3_normalize_file_minify2($file);
                             $style_len = strlen($style_tag);
                             if (!$this->_filter_files($file) || in_array($file, $handled_styles)) {
                                 continue;
                             }
                             $handled_styles[] = $file;
                             $this->replaced_styles[] = $file;
                             if (in_array($file, $ignore_css_files)) {
                                 if ($tag_pos > $embed_pos) {
                                     if ($files_to_minify) {
                                         $style = $this->get_style_custom($files_to_minify);
                                         $buffer = substr_replace($buffer, $style, $embed_pos, 0);
                                         $files_to_minify = array();
                                         $style_len = $style_len + strlen($style);
                                     }
                                     $embed_pos = $embed_pos + $style_len;
                                     $previous_file_was_ignored = true;
                                 }
                             } else {
                                 $buffer = substr_replace($buffer, '', $tag_pos, $style_len);
                                 if ($embed_pos > $tag_pos) {
                                     $embed_pos -= $style_len;
                                 } elseif ($previous_file_was_ignored) {
                                     $embed_pos = $tag_pos;
                                 }
                                 $files_to_minify[] = $file;
                             }
                         }
                         $style = $this->get_style_custom($files_to_minify);
                         $buffer = substr_replace($buffer, $style, $embed_pos, 0);
                     }
                 } else {
                     if ($this->_config->get_boolean('minify.css.enable') && !in_array('include', $this->printed_styles)) {
                         $style = $this->get_style_group('include');
                         if ($style) {
                             if ($this->_custom_location_does_not_exist('/<!-- W3TC-include-css -->/', $buffer, $style)) {
                                 $head_prepend .= $style;
                             }
                             $this->remove_styles_group($buffer, 'include');
                         }
                     }
                     if ($this->_config->get_boolean('minify.js.enable')) {
                         if (!in_array('include', $this->printed_scripts)) {
                             $embed_type = $this->_config->get_string('minify.js.header.embed_type');
                             $script = $this->get_script_group('include', $embed_type);
                             if ($script) {
                                 $embed_extsrcjs = $embed_type == 'extsrc' || $embed_type == 'asyncsrc' ? true : $embed_extsrcjs;
                                 if ($this->_custom_location_does_not_exist('/<!-- W3TC-include-js-head -->/', $buffer, $script)) {
                                     $head_prepend .= $script;
                                 }
                                 $this->remove_scripts_group($buffer, 'include', $embed_type);
                             }
                         }
                         if (!in_array('include-body', $this->printed_scripts)) {
                             $embed_type = $this->_config->get_string('minify.js.body.embed_type');
                             $script = $this->get_script_group('include-body', $embed_type);
                             if ($script) {
                                 $embed_extsrcjs = $embed_type == 'extsrc' || $embed_type == 'asyncsrc' ? true : $embed_extsrcjs;
                                 if ($this->_custom_location_does_not_exist('/<!-- W3TC-include-js-body-start -->/', $buffer, $script)) {
                                     $body_prepend .= $script;
                                 }
                                 $this->remove_scripts_group($buffer, 'include-body', $embed_type);
                             }
                         }
                         if (!in_array('include-footer', $this->printed_scripts)) {
                             $embed_type = $this->_config->get_string('minify.js.footer.embed_type');
                             $script = $this->get_script_group('include-footer', $embed_type);
                             if ($script) {
                                 $embed_extsrcjs = $embed_type == 'extsrc' || $embed_type == 'asyncsrc' ? true : $embed_extsrcjs;
                                 if ($this->_custom_location_does_not_exist('/<!-- W3TC-include-js-body-end -->/', $buffer, $script)) {
                                     $body_append .= $script;
                                 }
                                 $this->remove_scripts_group($buffer, 'include-footer', $embed_type);
                             }
                         }
                     }
                 }
                 if ($head_prepend != '') {
                     $buffer = preg_replace('~<head(\\s+[^<>]+)*>~Ui', '\\0' . $head_prepend, $buffer, 1);
                 }
                 if ($body_prepend != '') {
                     $buffer = preg_replace('~<body(\\s+[^<>]+)*>~Ui', '\\0' . $body_prepend, $buffer, 1);
                 }
                 if ($body_append != '') {
                     $buffer = preg_replace('~<\\/body>~', $body_append . '\\0', $buffer, 1);
                 }
                 if ($embed_extsrcjs) {
                     $script = "\n<script type=\"text/javascript\">\n" . "var extsrc=null;\n" . '(function(){function j(){if(b&&g){document.write=k;document.writeln=l;var f=document.createElement("span");f.innerHTML=b;g.appendChild(f);b=""}}function d(){j();for(var f=document.getElementsByTagName("script"),c=0;c<f.length;c++){var e=f[c],h=e.getAttribute("asyncsrc");if(h){e.setAttribute("asyncsrc","");var a=document.createElement("script");a.async=!0;a.src=h;document.getElementsByTagName("head")[0].appendChild(a)}if(h=e.getAttribute("extsrc")){e.setAttribute("extsrc","");g=document.createElement("span");e.parentNode.insertBefore(g,e);document.write=function(a){b+=a};document.writeln=function(a){b+=a;b+="\\n"};a=document.createElement("script");a.async=!0;a.src=h;/msie/i.test(navigator.userAgent)&&!/opera/i.test(navigator.userAgent)?a.onreadystatechange=function(){("loaded"==this.readyState||"complete"==this.readyState)&&d()}:-1!=navigator.userAgent.indexOf("Firefox")||"onerror"in a?(a.onload=d,a.onerror=d):(a.onload=d,a.onreadystatechange=d);document.getElementsByTagName("head")[0].appendChild(a);return}}j();document.write=k;document.writeln=l;for(c=0;c<extsrc.complete.funcs.length;c++)extsrc.complete.funcs[c]()}function i(){arguments.callee.done||(arguments.callee.done=!0,d())}extsrc={complete:function(b){this.complete.funcs.push(b)}};extsrc.complete.funcs=[];var k=document.write,l=document.writeln,b="",g="";document.addEventListener&&document.addEventListener("DOMContentLoaded",i,!1);if(/WebKit/i.test(navigator.userAgent))var m=setInterval(function(){/loaded|complete/.test(document.readyState)&&(clearInterval(m),i())},10);window.onload=i})();' . "\n</script>\n";
                     $buffer = preg_replace('~<head(\\s+[^<>]+)*>~Ui', '\\0' . $script, $buffer, 1);
                 }
             }
             /**
              * Minify HTML/Feed
              */
             if ($this->_config->get_boolean('minify.html.enable')) {
                 try {
                     $this->minify_html($buffer);
                 } catch (Exception $exception) {
                     $this->error = $exception->getMessage();
                 }
             }
         }
         if ($this->_config->get_boolean('minify.debug')) {
             $buffer .= "\r\n\r\n" . $this->get_debug_info();
         }
     }
     return $buffer;
 }
Ejemplo n.º 2
0
 /**
  * Returns minify groups
  *
  * @param string $theme
  * @param string $template
  * @param string $type
  * @return array
  */
 function get_groups($theme, $template, $type)
 {
     $result = array();
     switch ($type) {
         case 'css':
             $groups = $this->_config->get_array('minify.css.groups');
             break;
         case 'js':
             $groups = $this->_config->get_array('minify.js.groups');
             break;
         default:
             return $result;
     }
     if (isset($groups[$theme]['default'])) {
         $locations = (array) $groups[$theme]['default'];
     } else {
         $locations = array();
     }
     if ($template != 'default' && isset($groups[$theme][$template])) {
         $locations = array_merge_recursive($locations, (array) $groups[$theme][$template]);
     }
     foreach ($locations as $location => $config) {
         if (!empty($config['files'])) {
             foreach ((array) $config['files'] as $file) {
                 $file = w3_normalize_file_minify2($file);
                 if (w3_is_url($file)) {
                     $precached_file = $this->_precache_file($file, $type);
                     if ($precached_file) {
                         $result[$location][$file] = $precached_file;
                     } else {
                         $this->error(sprintf('Unable to cache remote file: "%s"', $file));
                     }
                 } else {
                     $path = w3_get_document_root() . '/' . $file;
                     if (file_exists($path)) {
                         $result[$location][$file] = '//' . $file;
                     } else {
                         $this->error(sprintf('File "%s" doesn\'t exist', $path));
                     }
                 }
             }
         }
     }
     return $result;
 }
Ejemplo n.º 3
0
 /**
  * Returns custom files
  *
  * @param string $hash
  * @param string $type
  * @return array
  */
 function get_custom_files($hash, $type)
 {
     $files = $this->uncompress_minify_files($hash, $type);
     $result = array();
     if ($files) {
         foreach ($files as $file) {
             $file = w3_normalize_file_minify2($file);
             if (w3_is_url($file)) {
                 $precached_file = $this->_precache_file($file, $type);
                 if ($precached_file) {
                     $result[] = $precached_file;
                 } else {
                     $this->error(sprintf('Unable to cache remote file: "%s"', $file));
                 }
             } else {
                 $path = w3_get_document_root() . '/' . $file;
                 if (file_exists($path)) {
                     $result[] = $file;
                 } else {
                     $this->error(sprintf('File "%s" doesn\'t exist', $path));
                 }
             }
         }
     } else {
         $this->error(sprintf('Unable to fetch custom files list: "%s.%s"', $hash, $type), false, 404);
     }
     return $result;
 }
Ejemplo n.º 4
0
 /**
  * Processes script tag
  * @param $script_tag
  * @return void
  */
 private function process_script_tag($script_tag)
 {
     $tag_pos = strpos($this->buffer, $script_tag);
     $match = null;
     if (!preg_match('~<script\\s+[^<>]*src=["\']?([^"\'> ]+)["\'> ]~is', $script_tag, $match)) {
         $match = null;
     }
     if (is_null($match)) {
         if (preg_match('~</head>~is', $script_tag, $match)) {
             $this->group_type = 'body';
         }
         // it's not external script, have to flush what we have before it
         $this->flush_collected();
         return;
     }
     if ($tag_pos === false) {
         // script is external but not found, skip processing it
         return;
     }
     $file = $match[1];
     $file = w3_normalize_file_minify2($file);
     if (!$this->minify_helpers->is_file_for_minification($file) || in_array($file, $this->ignore_js_files)) {
         $this->flush_collected();
         return;
     }
     $this->debug_minified_urls[] = $file;
     $this->buffer = substr_replace($this->buffer, '', $tag_pos, strlen($script_tag));
     // for head group - put minified file at the place of first script
     // for body - put at the place of last script, to make as more DOM
     // objects available as possible
     if (count($this->files_to_minify) <= 0 || $this->group_type == 'body') {
         $this->embed_pos = $tag_pos;
     }
     $this->files_to_minify[] = $file;
 }