PHP 페이지 HTML 출력을 축소하는 방법?


143

Google 페이지 속도처럼 PHP 페이지 HTML 출력을 최소화 할 수있는 PHP 스크립트 또는 클래스를 찾고 있습니다.

어떻게해야합니까?


14
@RakeshS의 답변을 기반으로 한 라이너 :ob_start(function($b){return preg_replace(['/\>[^\S ]+/s','/[^\S ]+\</s','/(\s)+/s'],['>','<','\\1'],$b);});
Francisco Presencia

5
@FranciscoPresencia 그것은 정말 나쁜 일입니다. 스크립트 태그, 프리 태그 등을 깨고 있습니다.
Brad

그의 답변 의견에서 언급했듯이 올바른 구조를 위해 공백이 필요하기 때문에 태그 <pre>또는 <code>태그가 작동하지 않습니다 . 그러나 <script>외부 외부 또는 인라인이지만 ;엄격한 방식 으로 사용해야 하므로 작동합니다. @Brad를 깨는 다른 태그는 무엇입니까? 나는 다른 사람들을 생각할 수 없었다. 그래도 이전 의견 앞에 빠르고 더러운 방법 을 추가해야했습니다 .
Francisco Presencia

답변:


213

CSS와 자바 스크립트

Javascript / CSS 파일을 축소하려면 다음 링크를 고려하십시오. https://github.com/mrclay/minify

HTML

GZip을 사용하여 HTML을 제공하도록 Apache에 지시하십시오. 이는 일반적으로 응답 크기를 약 70 % 줄입니다. (Apache를 사용하는 경우 gzip을 구성하는 모듈은 버전에 따라 다릅니다. Apache 1.3은 mod_gzip을 사용하고 Apache 2.x는 mod_deflate를 사용합니다.)

수락 인코딩 : gzip, 수축

콘텐츠 인코딩 : gzip

도움말 ob_start의 버퍼로 HTML에서 공백을 제거 하려면 다음 스 니펫 을 사용하십시오 .

<?php

function sanitize_output($buffer) {

    $search = array(
        '/\>[^\S ]+/s',     // strip whitespaces after tags, except space
        '/[^\S ]+\</s',     // strip whitespaces before tags, except space
        '/(\s)+/s',         // shorten multiple whitespace sequences
        '/<!--(.|\s)*?-->/' // Remove HTML comments
    );

    $replace = array(
        '>',
        '<',
        '\\1',
        ''
    );

    $buffer = preg_replace($search, $replace, $buffer);

    return $buffer;
}

ob_start("sanitize_output");

?>

54
이것은 좋은 기능이지만 PRE 태그 를 사용하는 경우 조심하십시오 . 때로는 개행 문자가 제거됩니다.
fedmich

2
이 코드는 스크립트 상단 또는 하단에 어디에 있어야합니까?
jdepypere

8
해당 Minify 라이브러리에서 Minify_HTML 클래스를 사용할 수도 있습니다 ( $content = \Minify_HTML::minify($content);인라인 코드를 위해 js / css 축소기에 콜백을 추가 할 수도 있음). github.com/mrclay/minify/blob/master/min/lib/Minify/HTML.php
Barryvdh

21
이것은 또한 모든 문장의 끝에 포함 <script>되지 않거나 ;사용하는 주석 이있는 인라인 JavaScript (예 : 태그)를 손상 시킵니다//
Konstantin Pereiaslov

8
이것은 textarea, pre, input에서 공백을 제거합니다. img 또한 인라인 자바 스크립트를 중단합니다. 누군가가 DOM 구문 분석과 함께 부피가 큰 클래스를 사용하는 것을 좋아하지 않는다면 정규 표현식을 기반으로 한이 솔루션 은 훌륭합니다.
Peter

28

제대로하려면 gzip을 켜십시오. 다음과 같이 할 수도 있습니다.

$this->output = preg_replace(
    array(
        '/ {2,}/',
        '/<!--.*?-->|\t|(?:\r?\n[ \t]*)+/s'
    ),
    array(
        ' ',
        ''
    ),
    $this->output
);

이렇게하면 HTML을 한 줄, 탭 없음, 줄 바꿈 없음, 주석 없음으로 바꾸어 페이지 크기의 약 30 %를 제거 할 수 있습니다. 마일리지는 다를 수 있습니다


1
두 가지를 모두 수행하면 더 많은 바이트가 필요합니다.
Wander Nauta

1
실제로 두 가지를 모두 수행하는 것은 gzip을 수행하는 것과 동일합니다 .700kb 페이지에서 gzip은 약 400kb로 가져 가고 preg_replace ()는 450kb (모든 내용에 따라 다름)는 g99가 공백을 동일하게 제거한 다음 399kb와 같습니다. 압축
dogmatic69

18
이것은 IE 조건을 제거하기 때문에 잠재적으로 위험 할 수 있습니다 ...-/<!
Katai

3
작동하지 않고 너무 많이 제거하면 코드가 엉망이됩니다. W3C가 유효하기 전에는 유효하지 않습니다.
Codebeat

3
불행히도 Google지도의보다 복잡한 구현을 생성하는 것과 같은 Javascript 코드도 손상시킵니다.이 기능은 꼭 필요합니다.
richey 2012

19

위의 모든 preg_replace()솔루션에는 한 줄 주석, 조건부 주석 및 기타 함정 문제가 있습니다. 정규식을 처음부터 새로 만드는 대신 잘 테스트 된 Minify 프로젝트 를 활용하는 것이 좋습니다 .

필자의 경우 다음 코드를 PHP 페이지 상단에 배치하여 축소합니다.

function sanitize_output($buffer) {
    require_once('min/lib/Minify/HTML.php');
    require_once('min/lib/Minify/CSS.php');
    require_once('min/lib/JSMin.php');
    $buffer = Minify_HTML::minify($buffer, array(
        'cssMinifier' => array('Minify_CSS', 'minify'),
        'jsMinifier' => array('JSMin', 'minify')
    ));
    return $buffer;
}
ob_start('sanitize_output');

1
코드 한 줄에 HTML을 넣어하지 않습니다
karadayi

Minify 프로젝트 FAQ 의 첫 번째 질문을 읽으십시오 . TL; DR : 무시하십시오.
앤드류

시도했지만 작동하지 않습니다. 내 PHP 파일에 <style> 태그 사이의 CSS와 <script> 태그 사이에 php가 포함 된 자바 스크립트가 있습니다.
João Pimentel Ferreira

이 코드를 어디에 배치합니까? 바닥 글이나 머리글에서 마지막으로?
프란체스코

@francesco 이것은 페이지의 첫 번째 코드 여야합니다.
앤드류

19

나는 여러 가지 축소기를 시도했지만 너무 작거나 많이 제거했습니다.

이 코드는 여분의 빈 공간과 선택적 HTML (끝) 태그를 제거합니다. 또한 안전하게 재생되며 HTML, JS 또는 CSS를 손상시킬 수있는 것을 제거하지 않습니다.

또한 코드는 Zend Framework에서이를 수행하는 방법을 보여줍니다.

class Application_Plugin_Minify extends Zend_Controller_Plugin_Abstract {

  public function dispatchLoopShutdown() {
    $response = $this->getResponse();
    $body = $response->getBody(); //actually returns both HEAD and BODY

    //remove redundant (white-space) characters
    $replace = array(
        //remove tabs before and after HTML tags
        '/\>[^\S ]+/s'   => '>',
        '/[^\S ]+\</s'   => '<',
        //shorten multiple whitespace sequences; keep new-line characters because they matter in JS!!!
        '/([\t ])+/s'  => ' ',
        //remove leading and trailing spaces
        '/^([\t ])+/m' => '',
        '/([\t ])+$/m' => '',
        // remove JS line comments (simple only); do NOT remove lines containing URL (e.g. 'src="http://server.com/"')!!!
        '~//[a-zA-Z0-9 ]+$~m' => '',
        //remove empty lines (sequence of line-end and white-space characters)
        '/[\r\n]+([\t ]?[\r\n]+)+/s'  => "\n",
        //remove empty lines (between HTML tags); cannot remove just any line-end characters because in inline JS they can matter!
        '/\>[\r\n\t ]+\</s'    => '><',
        //remove "empty" lines containing only JS's block end character; join with next line (e.g. "}\n}\n</script>" --> "}}</script>"
        '/}[\r\n\t ]+/s'  => '}',
        '/}[\r\n\t ]+,[\r\n\t ]+/s'  => '},',
        //remove new-line after JS's function or condition start; join with next line
        '/\)[\r\n\t ]?{[\r\n\t ]+/s'  => '){',
        '/,[\r\n\t ]?{[\r\n\t ]+/s'  => ',{',
        //remove new-line after JS's line end (only most obvious and safe cases)
        '/\),[\r\n\t ]+/s'  => '),',
        //remove quotes from HTML attributes that does not contain spaces; keep quotes around URLs!
        '~([\r\n\t ])?([a-zA-Z0-9]+)="([a-zA-Z0-9_/\\-]+)"([\r\n\t ])?~s' => '$1$2=$3$4', //$1 and $4 insert first white-space character found before/after attribute
    );
    $body = preg_replace(array_keys($replace), array_values($replace), $body);

    //remove optional ending tags (see http://www.w3.org/TR/html5/syntax.html#syntax-tag-omission )
    $remove = array(
        '</option>', '</li>', '</dt>', '</dd>', '</tr>', '</th>', '</td>'
    );
    $body = str_ireplace($remove, '', $body);

    $response->setBody($body);
  }
}

그러나 gZip 압축을 사용하면 코드가 압축되어 압축이 최소화되어 축소를 결합 할 수 있으므로 gZip은 의미가 없습니다. 다운로드로 절약 된 시간은 축소로 인해 손실되고 최소값도 절약하기 때문입니다.

내 결과는 다음과 같습니다 (3G 네트워크를 통해 다운로드).

 Original HTML:        150kB       180ms download
 gZipped HTML:          24kB        40ms
 minified HTML:        120kB       150ms download + 150ms minification
 min+gzip HTML:         22kB        30ms download + 150ms minification

4
그래, 나는 그것이 무의미 해 보이지만 동의하지만 Google의 페이지 속도에서 하나 또는 두 개의 귀중한 점수를 얻을 수 있으며 이는 Google 순위와 관련이 있습니다. 코드는 불필요한 공간을 제거하는 데 적합합니다. 감사합니다 :-)
Tschallacka

1
이것은 잘 작동하고 = "/"에 문제가 있었으므로 '~ ([\ r \ n \ t]) / /를 가져 갔습니까? ([a-zA-Z0-9] +) = "([a-zA -Z0-9 _ / \\-] +) "([\ r \ n \ t])? ~ s ​​'=>'$ 1 $ 2 = $ 3 $ 4 ', // $ 1 및 $ 4 앞에있는 첫 번째 공백 문자 삽입 after after 속성
ask_io

글쎄, 나는 일을 가속화하기 위해 공백을 제거하려고하지 않고 오히려 인라인 블록 요소와 같이 완전히 망치지 않기 위해 HTML을 사용해야 하는 방식이기 때문에 유능한 것을 찾고 있습니다. 이전 또는 이후에 하나의 공백이 있어야하는 것을 무시하는 것 (예 : 텍스트 블록의 대담한 요소).
Deji

다음 줄을 주석 처리하지 않으면 특정 Jquery / Foundation 관련 문제가 발견되었습니다. // JS의 블록 끝 문자 만 포함하는 "빈"줄을 제거하십시오. 다음 줄과 연결 (예 : "} \ n} \ n </ script>"-> "}} </ script>"// '/} [\ r \ n \ t] + / s'=> '} ', //'/} [\ r \ n \ t] +, [\ r \ n \ t] + / s '=>'} ',
Ian

1
서버 측 캐싱 (Smarty V3의 경우)을 사용하는 경우 min + gzip은 첫 번째 호출을 제외하고 좋은 솔루션입니다. 따라서 15 번째 호출 이후에는 서버 시간 동안 중단됩니다. rule = 40x15 = (30x15 + 150) 그러나 두 번째 전화의 경우 이미 방문자에게 더 빠릅니다.
Meloman

6

이것은 나를 위해 일합니다.

function Minify_Html($Html)
{
   $Search = array(
    '/(\n|^)(\x20+|\t)/',
    '/(\n|^)\/\/(.*?)(\n|$)/',
    '/\n/',
    '/\<\!--.*?-->/',
    '/(\x20+|\t)/', # Delete multispace (Without \n)
    '/\>\s+\</', # strip whitespaces between tags
    '/(\"|\')\s+\>/', # strip whitespaces between quotation ("') and end tags
    '/=\s+(\"|\')/'); # strip whitespaces between = "'

   $Replace = array(
    "\n",
    "\n",
    " ",
    "",
    " ",
    "><",
    "$1>",
    "=$1");

$Html = preg_replace($Search,$Replace,$Html);
return $Html;
}

5

문서 루트 외부에 PHP 파일을 작성하십시오. 문서 루트가

/var/www/html/

minify.php라는 파일을 한 수준 위의 파일로 만듭니다.

/var/www/minify.php

다음 PHP 코드를 복사하여 붙여 넣으십시오.

<?php
function minify_output($buffer){
    $search = array('/\>[^\S ]+/s','/[^\S ]+\</s','/(\s)+/s');
    $replace = array('>','<','\\1');
    if (preg_match("/\<html/i",$buffer) == 1 && preg_match("/\<\/html\>/i",$buffer) == 1) {
        $buffer = preg_replace($search, $replace, $buffer);
    }
    return $buffer;
}
ob_start("minify_output");?>

minify.php 파일을 저장하고 php.ini 파일을여십시오. 전용 서버 / VPS 인 경우 다음 옵션을 검색하고 사용자 정의 php.ini와의 공유 호스팅에서 추가하십시오.

auto_prepend_file = /var/www/minify.php

참조 : http://websistent.com/how-to-use-php-to-minify-html-output/



2

- 당신은 HTML TIDY로 볼 수 http://uk.php.net/tidy

PHP 모듈로 설치 될 수 있으며, 공백과 다른 모든 불쾌감을 제거하면서 (올 바르고 안전하게) 완전히 유효한 HTML / XHTML 마크 업을 출력합니다. 또한 코드를 깨끗하게 할 것입니다. 처음에 유효한 코드를 작성하는 데 얼마나 좋은지에 따라 훌륭하거나 끔찍한 일이 될 수 있습니다. ;-)

또한 파일 시작시 다음 코드를 사용하여 출력을 압축 할 수 있습니다.

ob_start('ob_gzhandler');

문제는 사이트가 공유에서 호스팅되며 그러한 모듈을 설치할 수있는 권한이 없다는 것입니다.
m3tsys

이미 설치되어있을 것입니다. 확인 phpinfo()... 최소한 zlib을 사용할 수 있도록 설치해야합니다 ob_gzhandler.
Rudi Visser 2016

나는 이미 if (substr_count($_SERVER['HTTP_ACCEPT_ENCODING'], 'gzip')) ob_start("ob_gzhandler"); else ob_start();같은 것이 아닌가?
m3tsys 2016

2
예, 실제로 else ob_start()부품이 필요하지 않으며 gzip 검사 ob_gzhandler는 브라우저가 내부에서 압축 방법을 지원하는지 여부를 감지합니다. 단순히 ob_start('ob_gzhandler');충분할 것입니다.
Rudi Visser 2016

여분의 구문 분석 오버 헤드로 인해 TIDY가 다른 답변보다 느릴 가능성이 있습니까? 개발에 도움이 될 수 있습니다. 그러면 실제 소스 코드에서 HTML 오류를 수정할 수 있습니다. 그러나 이것이 프로덕션에 가장 적합한 선택인지 의문입니다.
매트 브라운

2

우선 gzip은 HTML Minifier 이상의 기능을 제공합니다.

  1. nginx로 :

    gzip on;
    gzip_disable "msie6";
    
    gzip_vary on;
    gzip_proxied any;
    gzip_comp_level 6;
    gzip_buffers 16 8k;
    gzip_http_version 1.1;
    gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript;
  2. 아파치와 함께 mod_gzip을 사용할 수 있습니다

둘째 : gzip + Html Minification을 사용하면 파일 크기를 크게 줄일 수 있습니다!

HtmlMinifier for PHP를 만들었습니다 .

composer를 통해 검색 할 수 있습니다 : composer require arjanschouten/htmlminifier dev-master.

라 라벨 서비스 제공 업체가 있습니다. 라 라벨을 사용하지 않는다면 PHP에서 사용할 수 있습니다.

// create a minify context which will be used through the minification process
$context = new MinifyContext(new PlaceholderContainer());
// save the html contents in the context
$context->setContents('<html>My html...</html>');
$minify = new Minify();
// start the process and give the context with it as parameter
$context = $minify->run($context);

// $context now contains the minified version
$minifiedContents = $context->getContents();

보시다시피 여기에서 많은 것을 확장하고 다양한 옵션을 전달할 수 있습니다. 읽어보기 확인사용 가능한 모든 옵션을 보려면 를 확인하십시오.

HtmlMinifier 는 완전하고 안전합니다. 축소 프로세스에는 3 단계가 필요합니다.

  1. 중요한 콘텐츠를 임시로 자리 표시 자로 바꿉니다.
  2. 축소 전략을 실행하십시오.
  3. 원본 내용을 복원하십시오.

뷰의 출력을 캐시하는 것이 좋습니다. 축소 프로세스는 일회성 프로세스 여야합니다. 또는 예를 들어 간격 기반으로하십시오.

당시에는 명확한 벤치 마크가 생성되지 않았습니다. 그러나 축소 도구는 마크 업을 기준으로 페이지 크기를 5-25 % 줄일 수 있습니다!

자신 만의 전략을 추가하려면 addPlaceholderaddMinifier방법을 사용할 수 있습니다 .


도서관 주셔서 감사합니다. 지시 사항에는 포함해야 할 PHP 파일이 나와 있지 않습니다. 나는 결국 그것을 알아낼 것이지만, 그것은 당신이 아마 당신의 웹 사이트에 추가해야 할 것입니다.
rosewater

여전히 Illuminate \ Support \ Collection이 필요한 것 같습니다. 독립형 PHP 솔루션이 아닙니다.
rosewater

피드백 감사드립니다! 그것은이다 작곡가 패키지로 제공된다. 다음 규칙으로 readme업데이트했습니다 . 수행 require __DIR__ . '/vendor/autoload.php';해야 할 유일한 것은이 파일을 포함하는 것입니다. 이것은 작곡가에 의해 생성됩니다!
ArjanSchouten

2

HTML, CSS 및 JS 파일을 최소화하는 PHP 기능이 포함 된 GitHub 요지가 있습니다 → https://gist.github.com/taufik-nurrohman/d7b310dea3b33e4732c0

출력 버퍼를 사용하여 HTML 출력을 즉석에서 최소화하는 방법은 다음과 같습니다.

<?php

include 'path/to/php-html-css-js-minifier.php';

ob_start('minify_html');

?>

<!-- HTML code goes here ... -->

<?php echo ob_get_clean(); ?>

요점 링크는 404 페이지로 이어집니다
1111161171159459134

2
링크를 업데이트했습니다.
Taufik Nurrohman

1

페이지에서 모든 줄 바꿈을 제거하려면 다음 빠른 코드를 사용하십시오.

ob_start(function($b){
if(strpos($b, "<html")!==false) {
return str_replace(PHP_EOL,"",$b);
} else {return $b;}
});

0

Andrew 에게 감사합니다 . cakePHP에서 이것을 사용하는 방법은 다음과 같습니다.

  1. 축소 다운로드 -2.1.7
  2. 파일의 압축을 풀고 min 하위 폴더를 cake의 Vendor 폴더에 복사하십시오.
  3. 케이크의 View / Helper에서 MinifyCodeHelper.php를 다음과 같이 만듭니다.

    App::import('Vendor/min/lib/Minify/', 'HTML');
    App::import('Vendor/min/lib/Minify/', 'CommentPreserver');
    App::import('Vendor/min/lib/Minify/CSS/', 'Compressor');
    App::import('Vendor/min/lib/Minify/', 'CSS');
    App::import('Vendor/min/lib/', 'JSMin');
    class MinifyCodeHelper extends Helper {
        public function afterRenderFile($file, $data) {
            if( Configure::read('debug') < 1 ) //works only e production mode
                $data = Minify_HTML::minify($data, array(
                    'cssMinifier' => array('Minify_CSS', 'minify'),
                    'jsMinifier' => array('JSMin', 'minify')
                ));
            return $data;
        }
    }
  4. AppController에서 도우미를 활성화했습니다.

    공개 $ helpers = 배열 ​​( 'Html', '...', 'MinifyCode');

5 ... 짜잔!

내 결론 : 서버에서 apache의 deflate 및 headers 모듈이 비활성화되면 크기가 21 % 줄어들고 압축 요청에 0.35s가 더해집니다 (이 숫자는 제 경우였습니다).

그러나 아파치 모듈을 활성화했다면 압축 응답에는 큰 차이 (1.3 %)가 없으며 압축 시간은 samne (0.3s to me)입니다.

그래서 ... 내가 왜 그랬어? '내 프로젝트의 문서가 주석 (php, css 및 js)에 있으며 최종 사용자는 이것을 볼 필요가 없습니다.)


0

( )를 사용하여 HTMLCompressor 와 같이 잘 테스트 된 Java 축소기를 사용할 수 있습니다 . 콘솔을 사용하여 리디렉션해야 함passthruexec
2>&1

그러나 속도가 문제가되는 경우 유용하지 않을 수 있습니다. 정적 PHP 출력에 사용합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.