php多文件上传,大型网址优化技巧

图片 7
永利402com官方网站

静态能源文件自动裁减并替换来压缩版本(大型网址优化能力)

2015/11/26 · HTML5 ·
静态能源

初藳出处: Kelly   

那三遍,笔者总括和分享一项大型网址优化本事,那正是在项目中机动裁减静态财富文件(css、js),并让网址自行加载压缩后的能源文件。当然,那项技能在雅虎35条前端优化提出里也许有记载,但它那只是给出贰个答辩的方案而已,况兼利用的是外界压缩工具去收缩,而在自己的类型中,是向来通过和谐的前后相继自动化去减少全数css、js文件,然后让页面一直加载所减弱后的财富,接下去直接进入正题。

本次试验应用的是PHP脚本语言,版本是PHP5.6,是在LINUX下搭建的条件(互连网搭建无论是搭建LAMP照旧LNMP的学科都丰富多彩倒三颠四,后一次笔者会计算和享受怎样在LINUX下搭建服务器境遇的博文,并且搭建的情形必得贰次性搭建形成功的)。所接收的框架是CI框架,所接收的模板是斯马特y模板引擎。当然了,这几个只是自家所使用的条件而已,倘使你是PHP开辟者,要是你要测量检验下此番实验,那么,笔者建议您的PHP版本选取5.4之上,至于框架用什么都以足以的。而只要您不是PHP开荒者(你是JSP或许是ASP开拓者大概是其余开辟者),那么您领悟好那意气风发思路后,完全能够在融洽熟谙的言语里实行试验测量试验。

一、原理图

先是小编画一张思路图,便于我们先领会。

第一是能源减少原理图:

图片 1

继之是能源文件替换的准绳图:

图片 2

黄金时代旦我们认真掌握并且看懂这两张原理图的话,基本上也就精通了自己所享用的思绪。假诺照旧不能理解的话,接下去笔者会结合代码,对上述原理图的每一步举办详细讲明。

二、思路详细深入分析

1.第一是调用该滑坡的不二秘诀,你能够把该方法放在网址所要加载的公共类的地方,比如每趟访谈网址都会调用该滑坡方法举办压缩。当然,这些只是在支付条件才会每一趟都调用,如若是线上的条件,在你的网址发一回新本子的时候,调用二次用来生成压缩版的静态财富就能够了。

class MY_Controller extends CI_Controller { public function
__construct() { parent::__construct(); //压缩jscss财富文件
$this->compressResHandle(); } /** * 压缩js、css能源文件(优化) *
@return [type] [description] */ private function
compressResHandle() { $this->load->library(‘ResMinifier’);
//压缩内定文件夹下的能源文件 $this->resminifier->compressRes(); }
}

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
class MY_Controller extends CI_Controller {
    public function __construct() {
        parent::__construct();
 
        //压缩jscss资源文件
        $this->compressResHandle();
    }
    /**
     * 压缩js、css资源文件(优化)
     * @return [type] [description]
     */
    private function compressResHandle() {
        $this->load->library(‘ResMinifier’);
        //压缩指定文件夹下的资源文件
        $this->resminifier->compressRes();
    }
}

2.跟着就调用了 ResMinifier类里的 compressRes方法。在这里地本身先附上
ResMinifier那几个类的代码,然后方便一步步拓宽分析传授

PHP

<?php defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
/** * 能源压缩类 */ class ResMinifier { /** 要求减小的财富目录*/
public $compressResDir = [‘css’, ‘js’]; /**
忽视压缩的门路,举个例子此处是js/icon最早的门路忽视压缩*/ public
$compressResIngorePrefix = [‘js/icon’]; /** 能源根目录*/ public
$resRootDir; /** 财富版本文件路线*/ private $resStatePath; public
function __construct() { $this->resRootDir = WEBROOT . ‘www/’;
$this->resStatePath = WEBROOT . ‘www/resState.php’; } public function
compressRes() { //获取寄存版本的能源文件 $resState =
$this->getResState(); $count = 0; //开端遍历须求减小的财富目录
foreach ($this->compressResDir as $resDir) { foreach (new
RecursiveIteratorIterator(new
RecursiveDirectoryIterator($this->resRootDir . $resDir ,
FilesystemIterator::SKIP_DOTS)) as $file) { //获取该财富文件的相对路线$filePath = str_replace(‘\\’, ‘/’, $file->getRealPath());
//获取文件相对路线 $object = substr($filePath,
strlen($this->resRootDir)); //总计文件的本子号 $state =
$this->_getResStateVersion($filePath); //获取文件的几个参数值 if
(true !== $this->getObjectInfo($object, $minObject, $needCompress,
$state, $extension)) { continue; } //压缩文件的相对路线 $minFilePath =
str_replace(‘\\’, ‘/’, $this->resRootDir. $minObject);
//************此处p剖断是最重视部分之生龙活虎*****************//
//剖断文件是还是不是留存且早就改成过 if (isset($resState[$object]) &&
$resState[$object] == $state && isset($resState[$minObject]) &&
file_exists($minFilePath)) { continue; } //确定保障/www/min/目录可写
$this->_ensureWritableDir(dirname($minFilePath)); if ($needCompress)
{ $this->compressResFileAndSave($filePath, $minFilePath); } else {
copy($filePath, $minFilePath); } $resState[$object] = $state;
$resState[$minObject] = ”; $count++; if ($count == 50) {
$this->_saveResState($resState); $count = 0; } } } if($count)
$this->_saveResState($resState); } public function
getObjectInfo($object, &$minObject, &$needCompress, &$state,
&$extension) { //获取财富绝对路线 $file帕特h = $this->resRootDir .
$object; //推断能源是或不是留存 if (!file_exists($filePath)) return
“资源文件不设有{$file帕特h}”; //版本号 $state = $this->
_getResStateVersion($filePath); //文件名后缀 $extension =
pathinfo($filePath, PATHINFO_EXTENSION); //是还是不是要压缩 $needCompress =
true; //判定财富文件是或不是是以 .min.css大概.min.js结尾的
//此类结尾日常都以已调整和减弱过,比方jquery.min.js,就不需求再压缩了 if
(str_end_with($object, ‘.min.’.$extension, true)) {
//压缩后的能源存放路线,放在 /www/min/ 目录下 $minObject =
‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) .
$state .’.’. $extension; $needCompress = false; } else if
(in_array($extension, $this->compressResDir)) {
//此处是急需减小的文件目录 $minObject = ‘min/’.substr($object, 0,
strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
//看看是还是不是是忽略的不二等秘书籍前缀 foreach ($this->compressResIngorePrefix as
$v) { if (str_start_with($object, $v, true)) { $needCompress = false;
} } } else { $minObject = ‘min/’.$object; $needCompress = false; }
return true; } /** * 获取寄放能源版本的文件 * 它是献身三个数组里 *
$resState = array( * ‘文件路线’ => ‘对应的本子号’, * ‘文件路线’
=> ‘对应的版本号’, * ‘文件路线’ => ‘对应的本子号’, * ); *
@return [type] [description] */ public function getResState() { if
(file_exists($this->resStatePath)) { require $this->resStatePath;
return $resState; } return []; } /** *
总结文件的本子号,那些是基于总结文件MD5散列值得到版本号 *
只要文件内容改动了,所总结获得的散列值就能够不均等 *
用于判定财富文件是或不是有改变过 * @param [type] $filePath
[description] * @return [type] [description] */ public function
_getResStateVersion($filePath) { return
base_convert(crc32(md5_file($filePath)), 10, 36); } /** *
确定保障目录可写 * @param [type] $dir [description] * @return [type]
[description] */ private function _ensureWritableDir($dir) { if
(!file_exists($dir)) { @mkdir($dir, 0777, true); @chmod($dir, 0777); }
else if (!is_writable($dir)) { @chmod($dir, 0777); if
(!is_writable($dir)) { show_error(‘目录’.$dir.’不可写’); } } } /**
* 将精减后的能源文件写入到/www/min/下去 * @param [type] $filePath
[description] * @param [type] $minFilePath [description] *
@return [type] [description] */ private function
compressResFileAndSave($filePath, $minFilePath) { if
(!file_put_contents($minFilePath,
$this->compressResFile($filePath))) {
//$CI->exceptions->show_exception(“写入文件{$minFile帕特h}退步”);
show_error(“写入文件{$minFilePath}战败”, -1); } } /** * 压缩能源文件
* @param [type] $filePath [description] * @return [type]
[description] */ private function compressResFile($filePath) {
$extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION)); if
($extension === ‘js’) { require_once ‘JShrink/Minifier.php’; return
\JShrink\Minifier::minify(file_get_contents($filePath)); } else if
($extension ===’css’) { $content = file_get_contents($filePath);
$content =
preg_replace(‘!/\*[^*]*\*+([^/][^*]*\*+)*/!’, ”,
$content); $content = str_replace([“\r\n”, “\r”, “\n”], ”,
$content); $content = preg_replace(‘/([{}),;:>])\s+/’, ‘$1’,
$content); $content = preg_replace(‘/\s+([{}),;:>])/’, ‘$1’,
$content); $content = str_replace(‘;}’, ‘}’, $content); return
$content; } else {
//$CI->exceptions->show_exception(“不扶植压缩{extension}文件[$filePath]”);
show_error(“不扶助压缩{extension}文件[$filePath]”, -1); } } private
function _saveResState($resState) { ksort($resState); $content =
“<?php\n\n\$resState = array(\n”; foreach ($resState as $k =>
$v) { $content .= “\t ‘$k’ => ‘$v’,\n”; } $content .= “);\n\n”;
file_put_contents($this->resStatePath, $content); } } 点击展开财富压缩类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
<?php
defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
/**
* 资源压缩类
*/
class ResMinifier {
    /** 需要压缩的资源目录*/
    public $compressResDir = [‘css’, ‘js’];
    /** 忽略压缩的路径,例如此处是js/icon开头的路径忽略压缩*/
    public $compressResIngorePrefix = [‘js/icon’];
    /** 资源根目录*/
    public $resRootDir;
    /** 资源版本文件路径*/
    private $resStatePath;
 
    public function __construct() {
        $this->resRootDir = WEBROOT . ‘www/’;
        $this->resStatePath = WEBROOT . ‘www/resState.php’;
    }
 
    public function compressRes() {
        //获取存放版本的资源文件
        $resState = $this->getResState();
        $count = 0;
 
        //开始遍历需要压缩的资源目录
        foreach ($this->compressResDir as $resDir) {
            foreach (new RecursiveIteratorIterator(new RecursiveDirectoryIterator($this->resRootDir . $resDir , FilesystemIterator::SKIP_DOTS)) as $file) {
                //获取该资源文件的绝对路径
                $filePath = str_replace(‘\\’, ‘/’, $file->getRealPath());
                //获取文件相对路径
                $object = substr($filePath, strlen($this->resRootDir));
                //计算文件的版本号
                $state = $this->_getResStateVersion($filePath);
 
                //获取文件的几个参数值
                if (true !== $this->getObjectInfo($object, $minObject, $needCompress, $state, $extension)) {
                    continue;
                }
 
                //压缩文件的绝对路径
                $minFilePath = str_replace(‘\\’, ‘/’, $this->resRootDir. $minObject);
 
                //************此处p判断是最重要部分之一*****************//
                //判断文件是否存在且已经改动过
                if (isset($resState[$object]) && $resState[$object] == $state && isset($resState[$minObject]) && file_exists($minFilePath)) {
                    continue;
                }
 
                //确保/www/min/目录可写
                $this->_ensureWritableDir(dirname($minFilePath));
 
                if ($needCompress) {
                    $this->compressResFileAndSave($filePath, $minFilePath);
                } else {
                    copy($filePath, $minFilePath);
                }
 
                $resState[$object] = $state;
                $resState[$minObject] = ”;
                $count++;
 
                if ($count == 50) {
                    $this->_saveResState($resState);
                    $count = 0;
                }
 
            }
        }
        if($count) $this->_saveResState($resState);
    }
 
    public function getObjectInfo($object, &$minObject, &$needCompress, &$state, &$extension) {
        //获取资源绝对路径
        $filePath = $this->resRootDir . $object;
        //判断资源是否存在
        if (!file_exists($filePath)) return "资源文件不存在{$filePath}";
        //版本号
        $state = $this-> _getResStateVersion($filePath);
        //文件名后缀
        $extension = pathinfo($filePath, PATHINFO_EXTENSION);
        //是否要压缩
        $needCompress = true;
 
        //判断资源文件是否是以 .min.css或者.min.js结尾的
        //此类结尾一般都是已压缩过,例如jquery.min.js,就不必再压缩了
        if (str_end_with($object, ‘.min.’.$extension, true)) {
            //压缩后的资源存放路径,放在 /www/min/ 目录下
            $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) . $state .’.’. $extension;
            $needCompress = false;
        } else if (in_array($extension, $this->compressResDir)) {
            //此处是需要压缩的文件目录
            $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
            //看看是否是忽略的路径前缀
            foreach ($this->compressResIngorePrefix as $v) {
                if (str_start_with($object, $v, true)) {
                    $needCompress = false;
                }
            }
        } else {
            $minObject = ‘min/’.$object;
            $needCompress = false;
        }
        return true;
    }
 
    /**
     * 获取存放资源版本的文件
     * 它是放在一个数组里
     * $resState = array(
     *         ‘文件路径’ => ‘对应的版本号’,
     *         ‘文件路径’ => ‘对应的版本号’,
     *         ‘文件路径’ => ‘对应的版本号’,
     *     );
     * @return [type] [description]
     */
    public function getResState() {
        if (file_exists($this->resStatePath)) {
            require $this->resStatePath;
            return $resState;
        }
        return [];
    }
 
    /**
     * 计算文件的版本号,这个是根据计算文件MD5散列值得到版本号
     * 只要文件内容改变了,所计算得到的散列值就会不一样
     * 用于判断资源文件是否有改动过
     * @param  [type] $filePath [description]
     * @return [type]           [description]
     */
    public function _getResStateVersion($filePath) {
        return base_convert(crc32(md5_file($filePath)), 10, 36);
    }
 
    /**
     * 确保目录可写
     * @param  [type] $dir [description]
     * @return [type]      [description]
     */
    private function _ensureWritableDir($dir) {
        if (!file_exists($dir)) {
            @mkdir($dir, 0777, true);
            @chmod($dir, 0777);
        } else if (!is_writable($dir)) {
            @chmod($dir, 0777);
            if (!is_writable($dir)) {
                show_error(‘目录’.$dir.’不可写’);
            }
        }
    }
 
    /**
     * 将压缩后的资源文件写入到/www/min/下去
     * @param  [type] $filePath    [description]
     * @param  [type] $minFilePath [description]
     * @return [type]              [description]
     */
    private function compressResFileAndSave($filePath, $minFilePath) {
        if (!file_put_contents($minFilePath, $this->compressResFile($filePath))) {
 
            //$CI->exceptions->show_exception("写入文件{$minFilePath}失败");
            show_error("写入文件{$minFilePath}失败", -1);
        }
    }
 
    /**
     * 压缩资源文件
     * @param  [type] $filePath [description]
     * @return [type]           [description]
     */
    private function compressResFile($filePath) {
        $extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
        if ($extension === ‘js’) {
            require_once ‘JShrink/Minifier.php’;
            return \JShrink\Minifier::minify(file_get_contents($filePath));
        } else if ($extension ===’css’) {
            $content = file_get_contents($filePath);
            $content = preg_replace(‘!/\*[^*]*\*+([^/][^*]*\*+)*/!’, ”, $content);
            $content = str_replace(["\r\n", "\r", "\n"], ”, $content);
            $content = preg_replace(‘/([{}),;:>])\s+/’, ‘$1’, $content);
            $content = preg_replace(‘/\s+([{}),;:>])/’, ‘$1’, $content);
            $content = str_replace(‘;}’, ‘}’, $content);
            return $content;
        } else {
            //$CI->exceptions->show_exception("不支持压缩{extension}文件[$filePath]");
            show_error("不支持压缩{extension}文件[$filePath]", -1);
 
        }
    }
 
    private function _saveResState($resState) {
        ksort($resState);
        $content = "<?php\n\n\$resState = array(\n";
        foreach ($resState as $k => $v) {
            $content .= "\t ‘$k’ => ‘$v’,\n";
        }
        $content .= ");\n\n";
        file_put_contents($this->resStatePath, $content);
    }
 
}
 
点击打开 资源压缩类

全套类大多数代码小编都加了讲解,方便大家急迅领会。这里自身也会对每风流倜傥行代码举行降解。

(1)

PHP

/** 须要收缩的财富目录*/ public $compressResDir = [‘css’, ‘js’];
/** 忽视压缩的门径,比方此处是js/icon最早的门路忽视压缩*/ public
$compressResIngorePrefix = [‘js/icon’]; /** 财富根目录*/ public
$resRootDir; /** 财富版本文件路线*/ private $resStatePath; public
function __construct() { $this->resRootDir = WEBROOT . ‘www/’;
$this->resStatePath = WEBROOT . ‘www/resState.php’; }

1
2
3
4
5
6
7
8
9
10
11
12
13
/** 需要压缩的资源目录*/
    public $compressResDir = [‘css’, ‘js’];
    /** 忽略压缩的路径,例如此处是js/icon开头的路径忽略压缩*/
    public $compressResIngorePrefix = [‘js/icon’];
    /** 资源根目录*/
    public $resRootDir;
    /** 资源版本文件路径*/
    private $resStatePath;
 
    public function __construct() {
        $this->resRootDir = WEBROOT . ‘www/’;
        $this->resStatePath = WEBROOT . ‘www/resState.php’;
    }

$compressResDir变量是亟需收缩的财富目录,倘使你有新的管理目录,能够在这里变量里假使新的目录名就可以管理。附上本身测量试验项指标目录图

图片 3

$compressResIngorePrefix 忽视被裁减的路线的路线前有的是该数组变量的字符串,举个例子有三个财富路线为
js/icon/bg.js只怕是js/icon_index.js恐怕是js/icon.header.js,假使在该数组中参与了
js/icon那几个字符串,那么财富路径为js/icon早前的都会被忽视掉,也正是直接跳过,不用压缩。(因为财富文件里总有一点点是不要求减小的呗)

$resRootDir贮存能源根目录的

$resStatePath 那几个是财富版本文件路线

(2)步入compressRes() 方法,大家先剖判后边那黄金年代段代码

PHP

public function compressRes() { //获取寄放版本的能源文件 $resState =
$this->getResState(); $count = 0;

1
2
3
4
public function compressRes() {
        //获取存放版本的资源文件
        $resState = $this->getResState();
        $count = 0;

——————————-调用getResState() 讲解start————————————————————-

此间首先是调用 $this->getResState() 方法来博取存放版本的财富文件,此处先跳到该方法看看是怎样写的,其实正是带有该公文,然后再次来到里面贮存版本号的数组,大家看注释可见该公文里寄存版本号的格式(顺便附上图让我们看看)

PHP

/** * 获取寄放财富版本的文书 * 它是坐落三个数组里 * $resState =
array( * ‘文件路线’ => ‘对应的版本号’, * ‘文件路线’ =>
‘对应的本子号’, * ‘文件路线’ => ‘对应的版本号’, * ); * @return
[type] [description] */ public function getResState() { if
(file_exists($this->resStatePath)) { require $this->resStatePath;
return $resState; } return []; }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
/**
     * 获取存放资源版本的文件
     * 它是放在一个数组里
     * $resState = array(
     *         ‘文件路径’ => ‘对应的版本号’,
     *         ‘文件路径’ => ‘对应的版本号’,
     *         ‘文件路径’ => ‘对应的版本号’,
     *     );
     * @return [type] [description]
     */
    public function getResState() {
        if (file_exists($this->resStatePath)) {
            require $this->resStatePath;
            return $resState;
        }
        return [];
    }

(能源版本文件截图:)

图片 4

——————————-调用getResState() 讲解end————————————————————-

继之看compressRes()里的那大器晚成段代码

PHP

//开首遍历要求减小的财富目录 foreach ($this->compressResDir as
$resDir) { foreach (new RecursiveIteratorIterator(new
RecursiveDirectoryIterator($this->resRootDir . $resDir ,
FilesystemIterator::SKIP_DOTS)) as $file) { //获取该能源文件的相对路线$filePath = str_replace(‘\\’, ‘/’, $file->getRealPath());
//获取文件绝对路线 $object = substr($filePath,
strlen($this->resRootDir)); //总结文件的本子号 $state =
$this->_getResStateVersion($filePath);

1
2
3
4
5
6
7
8
9
//开始遍历需要压缩的资源目录
        foreach ($this->compressResDir as $resDir) {
            foreach (new RecursiveIteratorIterator(new RecursiveDirectoryIterator($this->resRootDir . $resDir , FilesystemIterator::SKIP_DOTS)) as $file) {
                //获取该资源文件的绝对路径
                $filePath = str_replace(‘\\’, ‘/’, $file->getRealPath());
                //获取文件相对路径
                $object = substr($filePath, strlen($this->resRootDir));
                //计算文件的版本号
                $state = $this->_getResStateVersion($filePath);

首先个遍历的是js和css目录
第三个遍历是将js目录大概css目录里的文书都形成路线方式,

例如说获取文件的相对路线 $filePath 的值是那样子的:

/usr/local/apache2/htdocs/project/www/css/home/index.css

而文件的相对路线$object是那样子的 :

css/home/index.css

此间就起来调用$this->_getResStateVersion($filePath)来计算文件的本子号

——————————-调用_getResStateVersion($filePath)
讲解start————————————————————

PHP

/** * 总计文件的本子号,这么些是依附总计文件MD5散列值获得版本号 *
只要文件内容退换了,所计算获得的散列值就能够不肖似 *
用于决断财富文件是或不是有转移过 * @param [type] $filePath
[description] * @return [type] [description] */ public function
_getResStateVersion($filePath) { return
base_convert(crc32(md5_file($filePath)), 10, 36); }

1
2
3
4
5
6
7
8
9
10
/**
     * 计算文件的版本号,这个是根据计算文件MD5散列值得到版本号
     * 只要文件内容改变了,所计算得到的散列值就会不一样
     * 用于判断资源文件是否有改动过
     * @param  [type] $filePath [description]
     * @return [type]           [description]
     */
    public function _getResStateVersion($filePath) {
        return base_convert(crc32(md5_file($filePath)), 10, 36);
    }

——————————-调用_getResStateVersion($filePath)
讲解end————————————————————-

要么到版本号后,再看下风流倜傥段代码,这里最初调用$this->getObjectInfo()方法,这里收获到压缩文件的绝对路线$minObject,是不是必要压缩$needCompress,版本号$state,文件后缀$extension。

PHP

//获取文件的多少个参数值 if (true !== $this->getObjectInfo($object,
$minObject, $needCompress, $state, $extension)) { continue; }

1
2
3
4
//获取文件的几个参数值
                if (true !== $this->getObjectInfo($object, $minObject, $needCompress, $state, $extension)) {
                    continue;
                }

——————————调用$this->getObjectInfo() 讲解start————————————————————

PHP

/** * 获取财富文件有关消息 * @param [type] $object 能源文件路线(www/css/home/index.css) * @param [type] $minObject 压缩财富文件路线(www/min/css/home/index.ae123a.css) * @param [type] $needCompress
是或不是须要压缩 * @param [type] $state 文件版本号 * @param [type]
$extension 文件名后缀 * @return [type] [description] */ public
function getObjectInfo($object, &$minObject, &$needCompress, &$state,
&$extension) { //获取财富相对路线 $filePath = $this->resRootDir .
$object; //剖断能源是还是不是留存 if (!file_exists($filePath)) return
“财富文件不设有{$filePath}”; //版本号 $state = $this->
_getResStateVersion($filePath); //文件名后缀 $extension =
pathinfo($filePath, PATHINFO_EXTENSION); //是还是不是要减小 $needCompress =
true; //剖断财富文件是还是不是是以 .min.css或然.min.js结尾的
//此类结尾经常都以已减少过,比如jquery.min.js,就不必再压缩了 if
(str_end_with($object, ‘.min.’.$extension, true)) {
//压缩后的能源寄放路线,放在 /www/min/ 目录下 $minObject =
‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) .
$state .’.’. $extension; $needCompress = false; } else if
(in_array($extension, $this->compressResDir)) {
//此处是内需减小的文件目录 $minObject = ‘min/’.substr($object, 0,
strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
//看看是或不是是忽略的不二秘籍前缀 foreach ($this->compressResIngorePrefix as
$v) { if (str_start_with($object, $v, true)) { $needCompress = false;
} } } else { $minObject = ‘min/’.$object; $needCompress = false; }
return true; }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
/**
     * 获取资源文件相关信息
     * @param  [type] $object       资源文件路径 (www/css/home/index.css)
     * @param  [type] $minObject    压缩资源文件路径 (www/min/css/home/index.ae123a.css)
     * @param  [type] $needCompress 是否需要压缩
     * @param  [type] $state        文件版本号
     * @param  [type] $extension    文件名后缀
     * @return [type]               [description]
     */
    public function getObjectInfo($object, &$minObject, &$needCompress, &$state, &$extension) {
        //获取资源绝对路径
        $filePath = $this->resRootDir . $object;
        //判断资源是否存在
        if (!file_exists($filePath)) return "资源文件不存在{$filePath}";
        //版本号
        $state = $this-> _getResStateVersion($filePath);
        //文件名后缀
        $extension = pathinfo($filePath, PATHINFO_EXTENSION);
        //是否要压缩
        $needCompress = true;
 
        //判断资源文件是否是以 .min.css或者.min.js结尾的
        //此类结尾一般都是已压缩过,例如jquery.min.js,就不必再压缩了
        if (str_end_with($object, ‘.min.’.$extension, true)) {
            //压缩后的资源存放路径,放在 /www/min/ 目录下
            $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) . $state .’.’. $extension;
            $needCompress = false;
        } else if (in_array($extension, $this->compressResDir)) {
            //此处是需要压缩的文件目录
            $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
            //看看是否是忽略的路径前缀
            foreach ($this->compressResIngorePrefix as $v) {
                if (str_start_with($object, $v, true)) {
                    $needCompress = false;
                }
            }
        } else {
            $minObject = ‘min/’.$object;
            $needCompress = false;
        }
        return true;
    }

本条主意里的每风华正茂行代码基本上都有注释了,所以就不一句句举行教学了,这里关键看下边包车型地铁推断部分:

if (str_end_with($object, ‘.min.’.$extension, true))
那么些论断是比较能源文件路线字串后面部分是还是不是以 .min.$extension
结尾,比方是 jquery.min.js,这种文件本来就是
压缩过的文书,所以就不用再开展裁减管理了, $minObject
这么些变量贮存的是减少后的能源文件路线。
此处附上str_end_with()函数的代码:

PHP

/** * 剖断 subject 是不是以 search结尾, 参数内定是还是不是忽视大小写 *
@param [type] $subject [description] * @param [type] $search
[description] * @param boolean $ignore_case [description] *
@return [type] [description] */ function str_end_with($subject,
$search, $ignore_case = false) { $len2 = strlen($search); if (0 ===
$len2) return true; $len1 = strlen($subject); if ($len2 > $len1)
return false; if ($ignore_case) { return 0 === strcmp(substr($subject,
$len1 – $len2), $search); } else { return 0 ===
strcasecmp(substr($subject, $len1 – $len2), $search); } }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
/**
     * 判断 subject 是否以 search结尾, 参数指定是否忽略大小写
     * @param  [type]  $subject     [description]
     * @param  [type]  $search      [description]
     * @param  boolean $ignore_case [description]
     * @return [type]               [description]
     */
    function str_end_with($subject, $search, $ignore_case = false) {
        $len2 = strlen($search);
        if (0 === $len2) return true;
        $len1 = strlen($subject);
        if ($len2 > $len1) return false;
        if ($ignore_case) {
            return 0 === strcmp(substr($subject, $len1 – $len2), $search);
        } else {
            return 0 === strcasecmp(substr($subject, $len1 – $len2), $search);
        }
    }

if
(in_array($extension, $this->compressResDir),这几个剖断正是是还是不是是须要管理的七个目录里的。

下一场中间的foreach ($this->compressResIngorePrefix as $v) { if
(str_start_with($object, $v, true)) { $needCompress = false; } }

其一是判定是或不是是以$this->compressResIngorePrefix属性定义的前方部分字串发轫的不二秘技,是的话就忽视压缩该能源文件。

看清到终极else
正是表明该能源文件无需收缩了,最后是回来$minObject,$needCompress,$state,$extension这两个变量。

——————————-调用$this->getObjectInfo() 讲解end————————————————————-

到此地继续回到看 compressRes()方法里面包车型客车代码

PHP

//压缩文件的相对路线 $minFilePath = str_replace(‘\\’, ‘/’,
$this->resRootDir. $minObject);
//************此处p决断是最主要部分之风度翩翩*****************//
//决断文件是或不是留存且早就改成过 if (isset($resState[$object]) &&
$resState[$object] == $state && isset($resState[$minObject]) &&
file_exists($minFilePath)) { continue; }

1
2
3
4
5
6
7
8
//压缩文件的绝对路径
                $minFilePath = str_replace(‘\\’, ‘/’, $this->resRootDir. $minObject);
 
                //************此处p判断是最重要部分之一*****************//
                //判断文件是否存在且已经改动过
                if (isset($resState[$object]) && $resState[$object] == $state && isset($resState[$minObject]) && file_exists($minFilePath)) {
                    continue;
                }

这段代码首先是东挪西凑出压缩文件的相对路线,

继而上面那几个论断是最首要的局地,通过那个判别就能够知晓该能源文件是或不是被转移过,假设更改过的话,就重新对该财富文件实行压缩,借使没改换过,就持续管理下一个财富文件。看这里的判别:isset($resState[$object])
&& $resState[$object] == $state,那么些论断就是剖断该公文路线是否留存 
何况文件中对应的版本号和计算出的版本号是还是不是还同样;isset($resState[$minObject])
&&file_exists($minFilePath),那个是决断压缩文件路线是还是不是留存,而且该压缩文件是不是真正存在目录中。

看下大器晚成段代码,假诺能走到那风度翩翩某个,表达当前的这几个财富文件是被转移过的(代码更改进),那么当时就对文本举办减削操作了

PHP

//确认保障/www/min/目录可写
$this->_ensureWritableDir(dirname($minFilePath)); if ($needCompress)
{ $this->compressResFileAndSave($filePath, $minFilePath); } else {
copy($filePath, $minFilePath); }

1
2
3
4
5
6
7
8
//确保/www/min/目录可写
                $this->_ensureWritableDir(dirname($minFilePath));
 
                if ($needCompress) {
                    $this->compressResFileAndSave($filePath, $minFilePath);
                } else {
                    copy($filePath, $minFilePath);
                }

$this->_ensureWritableDir(),此办法是要确定保证新成立的www/min目录是可写的,这里附上代码:

——————————-调用$this->_ensureWritableDir() 讲解start————————————————————-

PHP

/** * 确认保障目录可写 * @param [type] $dir [description] * @return
[type] [description] */ private function _ensureWritableDir($dir)
{ if (!file_exists($dir)) { @mkdir($dir, 0777, true); @chmod($dir,
0777); } else if (!is_writable($dir)) { @chmod($dir, 0777); if
(!is_writable($dir)) { show_error(‘目录’.$dir.’不可写’); } } }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
/**
     * 确保目录可写
     * @param  [type] $dir [description]
     * @return [type]      [description]
     */
    private function _ensureWritableDir($dir) {
        if (!file_exists($dir)) {
            @mkdir($dir, 0777, true);
            @chmod($dir, 0777);
        } else if (!is_writable($dir)) {
            @chmod($dir, 0777);
            if (!is_writable($dir)) {
                show_error(‘目录’.$dir.’不可写’);
            }
        }
    }

——————————-调用$this->_ensureWritableDir() 讲解end————————————————————-

if
($needCompress),那些判别能源文件是或不是须要减小,需求的话调用$this->compressResFileAndSave($file帕特h,
$minFilePath);无需的话,直接复制文件到压缩文件路线 copy($filePath,
$minFilePath);

先看$this->compressResFileAndSave()

——————————-调用$this->compressResFileAndSave()
讲解start————————————————————-

PHP

/** * 将滑坡后的能源文件写入到/www/min/下去 * @param [type]
$filePath [description] * @param [type] $minFilePath
[description] * @return [type] [description] */ private function
compressResFileAndSave($filePath, $minFilePath) { if
(!file_put_contents($minFilePath,
$this->compressResFile($filePath))) {
//$CI->exceptions->show_exception(“写入文件{$minFilePath}退步”);
show_error(“写入文件{$minFilePath}失利”, -1); } } /** * 压缩财富文件
* @param [type] $filePath [description] * @return [type]
[description] */ private function compressResFile($filePath) {
$extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION)); if
($extension === ‘js’) { require_once ‘JShrink/Minifier.php’; return
\JShrink\Minifier::minify(file_get_contents($filePath)); } else if
($extension ===’css’) { $content = file_get_contents($filePath);
$content =
preg_replace(‘!/\*[^*]*\*+([^/][^*]*\*+)*/!’, ”,
$content); $content = str_replace([“\r\n”, “\r”, “\n”], ”,
$content); $content = preg_replace(‘/([{}),;:>])\s+/’, ‘$1’,
$content); $content = preg_replace(‘/\s+([{}),;:>])/’, ‘$1’,
$content); $content = str_replace(‘;}’, ‘}’, $content); return
$content; } else {
//$CI->exceptions->show_exception(“不帮助压缩{extension}文件[$filePath]”);
show_error(“不帮助压缩{extension}文件[$filePath]”, -1); } }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
/**
     * 将压缩后的资源文件写入到/www/min/下去
     * @param  [type] $filePath    [description]
     * @param  [type] $minFilePath [description]
     * @return [type]              [description]
     */
    private function compressResFileAndSave($filePath, $minFilePath) {
        if (!file_put_contents($minFilePath, $this->compressResFile($filePath))) {
 
            //$CI->exceptions->show_exception("写入文件{$minFilePath}失败");
            show_error("写入文件{$minFilePath}失败", -1);
        }
    }
 
    /**
     * 压缩资源文件
     * @param  [type] $filePath [description]
     * @return [type]           [description]
     */
    private function compressResFile($filePath) {
        $extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
        if ($extension === ‘js’) {
            require_once ‘JShrink/Minifier.php’;
            return \JShrink\Minifier::minify(file_get_contents($filePath));
        } else if ($extension ===’css’) {
            $content = file_get_contents($filePath);
            $content = preg_replace(‘!/\*[^*]*\*+([^/][^*]*\*+)*/!’, ”, $content);
            $content = str_replace(["\r\n", "\r", "\n"], ”, $content);
            $content = preg_replace(‘/([{}),;:>])\s+/’, ‘$1’, $content);
            $content = preg_replace(‘/\s+([{}),;:>])/’, ‘$1’, $content);
            $content = str_replace(‘;}’, ‘}’, $content);
            return $content;
        } else {
            //$CI->exceptions->show_exception("不支持压缩{extension}文件[$filePath]");
            show_error("不支持压缩{extension}文件[$filePath]", -1);
 
        }
    }

先减少,再将滑坡后的内容写入到 压缩文件路线里去。

咱俩先看下那一个压缩方法:

$this->compressResFile($filePath);
此方法中分两类压缩,第意气风发类时对js文件举办减削,第二类的对css文件实行压缩。先说js压缩,这里是调用叁个JShrink的类,它

叁个用来压缩js文件的PHP类,百度能够找到,调用那一个类的minify()那一个点子就足以缩小了;而css的滑坡利用正则替换到减弱,把那多少个空格换行什么的都去掉。到此就降低成功

了,然后再将减少后的能源写入到相应的压缩文件路径里去。

——————————-调用$this->compressResFileAndSave()
讲解end————————————————————-

随着继续看compressRes()那么些法子里的代码,这里开头便是保存新的版本号到$resState数组里
$object=>$state,还会有便是新的减削路线$minObject,而那边$count++的效益是,当那么些轮回四拾伍次就将
$resState这几个数组写入贰次到
resState.php文件里,这里是由于严谨思念而已,要是你不加那一个$count的管理这大器晚成部分也足以,最后写入三遍就行了。

PHP

$resState[$object] = $state; $resState[$minObject] = ”; $count++;
if ($count == 50) { $this->_saveResState($resState); $count = 0; } }
} if($count) $this->_saveResState($resState);

1
2
3
4
5
6
7
8
9
10
11
12
$resState[$object] = $state;
                $resState[$minObject] = ”;
                $count++;
 
                if ($count == 50) {
                    $this->_saveResState($resState);
                    $count = 0;
                }
 
            }
        }
        if($count) $this->_saveResState($resState);

这里看$this->_saveResState($resState),那几个措施便是将$resState数组写入到resState.php文件里去的方法。

——————————-调用$this->_saveResState($resState)
讲解start————————————————————-

PHP

private function _saveResState($resState) { ksort($resState); $content
= “<?php\n\n\$resState = array(\n”; foreach ($resState as $k
=> $v) { $content .= “\t ‘$k’ => ‘$v’,\n”; } $content .=
“);\n\n”; file_put_contents($this->resStatePath, $content); }

1
2
3
4
5
6
7
8
9
private function _saveResState($resState) {
        ksort($resState);
        $content = "<?php\n\n\$resState = array(\n";
        foreach ($resState as $k => $v) {
            $content .= "\t ‘$k’ => ‘$v’,\n";
        }
        $content .= ");\n\n";
        file_put_contents($this->resStatePath, $content);
    }

——————————-调用$this->_saveResState($resState)
讲解end————————————————————-

拍卖完后,看看所生成的公文,这里四个文书会有三个版本,旧版本从不删除掉,在支付条件下删不删除都没难题,这里怎么不删除旧版本的压缩文件,这就提到到在更新七个应用服务器代码时所要注意的难题里。在这笔者就多疏解一点吗,轻松地举个例证吗,平日大型项目中的静态能源和模板文件是布署在不一样的机器集群上的,上线的历程中,静态能源和页面文件的配置时间距离恐怕会非常长,对于叁个巨型互连网选择来说便是在四个十分的小的时日间距内,皆有异常的大或许现身新客商访谈,假若旧版本的静态财富删除了,但新本子的静态能源还未有安插到位,那么顾客就加载不到该静态财富,结果同理可得,所以,经常境况下大家会保留旧版本的静态财富,然后等具有片段布置造成了,再通过自然的剧本删除掉也没提到,其实,那几个不必删除也是足以的,你想想,二个品种发贰回版本,才会调用三回财富文件缩短方法,它只会对改良过的文件进行生成新版本号的静态文件而已。那个就看个人的做法了。

图片 5

咱俩得以展开看看,下边那几个就是压缩后的文书的代码了,文件原大小为16K,压缩后差不离少了5K,以后是11K,压缩比大约是2/3,借使在大型项目中,三个复杂点的页面会有非常大的静态财富文件要加载,通过此办法,大大地升高了加载的快慢。(或许有一点朋友感觉压缩个几K或然十几K算什么,完全能够忽视,其实本身想说的是,当您在大型项目中优化品种的时候,能够减弱几K的代码,也给网站的特性进步了一大截)

图片 6

到此,能源减少管理就深入分析实现了。其实,有一定基础的对象,可以直接看本身享受的非常代码就足以了,要是通晓不了,再看本人上边这一步步的解析解说,作者是处在能看过来此博客的心上人,无论本事是好只怕是稍弱,都能看懂,所以才对代码一步步地扩充深入解析教学。(希望各位多多照管四哥)

————————————————————————————————————————-

  1. 接下去便是助教怎么着替换压缩后的财富文件了。

这个到Home.php

PHP

<?php defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
class Home extends MY_Controller { public function index() {
$this->smartyData[‘test’] = 111; //那些私下认可是加载
www/css/home/index.css文件 $this->addResLink(‘index.css’);
//那几个暗中认可是加载www/js/jquery.all.min.js文件
$this->addResLink(‘/jquery.all.min.js’);
//那个默许是加载www/js/index.js文件 $this->addResLink(‘index.js’);
$this->displayView(‘home/index.tpl’); } }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<?php
defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
 
class Home extends MY_Controller {
    public function index() {
        $this->smartyData[‘test’] = 111;
        //这个默认是加载 www/css/home/index.css文件
        $this->addResLink(‘index.css’);
        //这个默认是加载www/js/jquery.all.min.js文件
        $this->addResLink(‘/jquery.all.min.js’);
        //这个默认是加载www/js/index.js文件
        $this->addResLink(‘index.js’);
        $this->displayView(‘home/index.tpl’);
    }
}

下边有加载多个财富文件,我们先看看$this->addResLink();那么些方式,这几个方法放在My_Controller.php里:

PHP

/** * 能源路线 * @param [type] $filePath [description] */
protected function addResLink($filePath) { list($filePath, $query) =
explode(‘?’, $filePath . ‘?’); $extension =
strtolower(pathinfo($filePath, PATHINFO_EXTENSION)); foreach
($this->_resLink as $v) { if (false === array_search($filePath,
$this->_resLink[$extension])) {
$this->_resLink[$extension][] = $query == null ? $filePath :
$filePath .’?’. $query; } } return $this; }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
/**
     * 资源路径
     * @param [type] $filePath [description]
     */
    protected function addResLink($filePath) {
        list($filePath, $query) = explode(‘?’, $filePath . ‘?’);
        $extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
        foreach ($this->_resLink as $v) {
            if (false === array_search($filePath, $this->_resLink[$extension])) {
                $this->_resLink[$extension][] = $query == null ? $filePath : $filePath .’?’. $query;
            }
        }
 
        return $this;
    }

这里根本是决断了能源文件是css依旧js,然后将其存放在
$this->_resLink那特性子里。

那么这里我就先附上My_Controller.php那几个父类的有着代码吧

PHP

<?php defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
class MY_Controller extends CI_Controller { public function
__construct() { parent::__construct(); //压缩jscss能源文件
$this->compressResHandle(); }
//==========================使用SMARTY模板引擎================================//
/* Smarty母版页文件路线 */ protected $masterPage = ‘default.tpl’; /*
视图像和文字件路线*/ protected $smartyView; /* 要赋值给smarty视图的多寡*/
protected $smartyData = []; /* 财富文件*/ protected $_resLink =
[‘js’=>[], ‘css’=>[]]; /** * 使用母版页输出七个视图 *
@return [type] [description] */ protected function
displayView($viewName = null, $masterPage = null) { //为空则选拔默许母版
if ($masterPage == null) $masterPage = $this->masterPage;
//获取视图的出口内容 $viewContent =
$this->_fetchView($this->smartyData, $viewName, $masterPage);
$output = ”; //添加css Link foreach ($this->_resLink[‘css’] as
$v) { $output .= res_link($v); } //内容部分 $output .= $viewContent;
//尾巴部分增添js 链接 foreach ($this->_resLink[‘js’] as $v) { $output
.= res_link($v); } //发送最后输出结果以致服务器的 HTTP 头到浏览器
$this->output->_display($output); return $output; } private
function _fetchView($smartyData, &$viewName, &$masterPage) { if
($viewName == null) $viewName = $this->smartyView; if
(empty($this->smarty)) { require_once
SMARTY_DIEvoque.’斯马特y.class.php’; $this->smarty = new 斯马特y();
$this->smarty->setCompileDir(应用软件PATH . ‘cache/’);
$this->smarty->setCacheDir(APPPATH . ‘cache/’); }
//设置视图真实路径 $this->_getViewDir(true, $viewName, $masterPage,
$templateDir); foreach ($smartyData as $k => $v) {
$this->smarty->assign($k, $v); } if (empty($masterPage)) { return
$this->smarty->fetch($viewName); } else {
$this->smarty->assign(‘VIEW_MAIN’, $viewName); return
$this->smarty->fetch($masterPage); } } /** * 财富路线 * @param
[type] $filePath [description] */ protected function
addResLink($filePath) { list($filePath, $query) = explode(‘?’, $filePath
. ‘?’); $extension = strtolower(pathinfo($filePath,
PATHINFO_EXTENSION)); foreach ($this->_resLink as $v) { if (false
=== array_search($filePath, $this->_resLink[$extension])) {
$this->_resLink[$extension][] = $query == null ? $filePath :
$filePath .’?’. $query; } } return $this; } private function
_getViewDir($setTemplateDir, &$viewName, &$masterPage = null,
&$templateDir) { if (‘/’ === $viewName[0]) $viewName =
substr($viewName, 1); //是不是使用模板,有,则路由到
/views/master_page/*****.tpl下去 if ($masterPage) { $masterPage =
‘/’ === $masterPage[0] ? substr($masterPage, 1) : (‘master_page’
.’/’. $masterPage); } //是还是不是设置模板目录 if ($setTemplateDir) {
$templateDir = VIEWPATH;
$this->smarty->setTemplateDir($templateDir); } } /** *
压缩js、css能源文件(优化) * @return [type] [description] */
private function compressResHandle() {
$this->load->library(‘Res迷你fier’); //压缩指定文件夹下的能源文件
$this->resminifier->compressRes(); } } 点击张开 My_Controller.php

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
<?php
defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
 
class MY_Controller extends CI_Controller {
    public function __construct() {
        parent::__construct();
 
        //压缩jscss资源文件
        $this->compressResHandle();
    }
 
    //==========================使用SMARTY模板引擎================================//
    /* Smarty母版页文件路径 */
    protected $masterPage = ‘default.tpl’;
    /* 视图文件路径*/
    protected $smartyView;
    /* 要赋值给smarty视图的数据*/
    protected $smartyData = [];
    /* 资源文件*/
    protected $_resLink = [‘js’=>[], ‘css’=>[]];
 
    /**
     * 使用母版页输出一个视图
     * @return [type] [description]
     */
    protected function displayView($viewName = null, $masterPage = null) {
        //为空则选用默认母版
        if ($masterPage == null) $masterPage = $this->masterPage;
        //获取视图的输出内容
        $viewContent = $this->_fetchView($this->smartyData, $viewName, $masterPage);
 
        $output = ”;
 
        //添加css Link
        foreach ($this->_resLink[‘css’] as $v) {
            $output .= res_link($v);
        }
 
        //内容部分
        $output .= $viewContent;
        //尾部添加js 链接
        foreach ($this->_resLink[‘js’] as $v) {
            $output .= res_link($v);
        }
        //发送最终输出结果以及服务器的 HTTP 头到浏览器
 
        $this->output->_display($output);
        return $output;
    }
 
    private function _fetchView($smartyData, &$viewName, &$masterPage) {
        if ($viewName == null) $viewName = $this->smartyView;
 
        if (empty($this->smarty)) {
            require_once SMARTY_DIR.’Smarty.class.php’;
            $this->smarty = new Smarty();
            $this->smarty->setCompileDir(APPPATH . ‘cache/’);
            $this->smarty->setCacheDir(APPPATH . ‘cache/’);
        }
 
        //设置视图真实路径
        $this->_getViewDir(true, $viewName, $masterPage, $templateDir);
 
        foreach ($smartyData as $k => $v) {
            $this->smarty->assign($k, $v);
        }
 
        if (empty($masterPage)) {
            return $this->smarty->fetch($viewName);
        } else {
            $this->smarty->assign(‘VIEW_MAIN’, $viewName);
            return $this->smarty->fetch($masterPage);
        }
    }
 
    /**
     * 资源路径
     * @param [type] $filePath [description]
     */
    protected function addResLink($filePath) {
        list($filePath, $query) = explode(‘?’, $filePath . ‘?’);
        $extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
        foreach ($this->_resLink as $v) {
            if (false === array_search($filePath, $this->_resLink[$extension])) {
                $this->_resLink[$extension][] = $query == null ? $filePath : $filePath .’?’. $query;
            }
        }
 
        return $this;
    }
 
    private function _getViewDir($setTemplateDir, &$viewName, &$masterPage = null, &$templateDir) {
        if (‘/’ === $viewName[0]) $viewName = substr($viewName, 1);
 
        //是否使用模板,有,则路由到 /views/master_page/*****.tpl下去
        if ($masterPage) {
            $masterPage = ‘/’ === $masterPage[0] ? substr($masterPage, 1) : (‘master_page’ .’/’. $masterPage);
        }
 
        //是否设置模板目录
        if ($setTemplateDir) {
            $templateDir = VIEWPATH;
            $this->smarty->setTemplateDir($templateDir);
        }
    }
 
    /**
     * 压缩js、css资源文件(优化)
     * @return [type] [description]
     */
    private function compressResHandle() {
        $this->load->library(‘ResMinifier’);
        //压缩指定文件夹下的资源文件
        $this->resminifier->compressRes();
    }
}
 
点击打开 My_Controller.php

打字与印刷出来 $this->_resLink这本性格的布局是那样子的:

PHP

Array ( [js] => Array ( [0] => /jquery.all.min.js [1] =>
index.js ) [css] => Array ( [0] => index.css ) )

1
2
3
4
5
6
7
8
9
10
11
12
13
14
Array
(
    [js] => Array
        (
            [0] => /jquery.all.min.js
            [1] => index.js
        )
 
    [css] => Array
        (
            [0] => index.css
        )
 
)

再回去Home.php里面调用 $this->displayView(‘home/index.tpl’);

大家看那么些法子:

PHP

/** * 使用母版页输出二个视图 * @return [type] [description] */
protected function displayView($viewName = null, $masterPage = null) {
//为空则接收暗中认可母版 if ($masterPage == null) $masterPage =
$this->masterPage; //获取视图的出口内容 $viewContent =
$this->_fetchView($this->smartyData, $viewName, $masterPage);
$output = ”; //添加css Link foreach ($this->_resLink[‘css’] as
$v) { $output .= res_link($v); } //内容部分 $output .= $viewContent;
//尾巴部分增添js 链接 foreach ($this->_resLink[‘js’] as $v) { $output
.= res_link($v); } //发送最后输出结果甚至服务器的 HTTP 头到浏览器
$this->output->_display($output); return $output; } private
function _fetchView($smartyData, &$viewName, &$masterPage) { if
($viewName == null) $viewName = $this->smartyView; if
(empty($this->smarty)) { require_once
SMARTY_DI大切诺基.’Smarty.class.php’; $this->smarty = new 斯玛特y();
$this->smarty->setCompileDir(APPPATH . ‘cache/’);
$this->smarty->setCacheDir(APPPATH . ‘cache/’); }
//设置视图真实路径 $this->_getViewDir(true, $viewName, $masterPage,
$templateDir); foreach ($smartyData as $k => $v) {
$this->smarty->assign($k, $v); } if (empty($masterPage)) { return
$this->smarty->fetch($viewName); } else {
$this->smarty->assign(‘VIEW_MAIN’, $viewName); return
$this->smarty->fetch($masterPage); } }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
/**
     * 使用母版页输出一个视图
     * @return [type] [description]
     */
    protected function displayView($viewName = null, $masterPage = null) {
        //为空则选用默认母版
        if ($masterPage == null) $masterPage = $this->masterPage;
        //获取视图的输出内容
        $viewContent = $this->_fetchView($this->smartyData, $viewName, $masterPage);
 
        $output = ”;
 
        //添加css Link
        foreach ($this->_resLink[‘css’] as $v) {
            $output .= res_link($v);
        }
 
        //内容部分
        $output .= $viewContent;
        //尾部添加js 链接
        foreach ($this->_resLink[‘js’] as $v) {
            $output .= res_link($v);
        }
        //发送最终输出结果以及服务器的 HTTP 头到浏览器
 
        $this->output->_display($output);
        return $output;
    }
 
    private function _fetchView($smartyData, &$viewName, &$masterPage) {
        if ($viewName == null) $viewName = $this->smartyView;
 
        if (empty($this->smarty)) {
            require_once SMARTY_DIR.’Smarty.class.php’;
            $this->smarty = new Smarty();
            $this->smarty->setCompileDir(APPPATH . ‘cache/’);
            $this->smarty->setCacheDir(APPPATH . ‘cache/’);
        }
 
        //设置视图真实路径
        $this->_getViewDir(true, $viewName, $masterPage, $templateDir);
 
        foreach ($smartyData as $k => $v) {
            $this->smarty->assign($k, $v);
        }
 
        if (empty($masterPage)) {
            return $this->smarty->fetch($viewName);
        } else {
            $this->smarty->assign(‘VIEW_MAIN’, $viewName);
            return $this->smarty->fetch($masterPage);
        }
    }

那大器晚成段代码没有少年老成部分正是调用了Smarty模板引擎的从头到尾的经过,那一个关于斯马特y的学问作者就不讲了,大家能够团结百度,这里关键讲
res_link()
那些函数,便是通过那个函数来进行财富文件替换的。先看那个函数的代码:

PHP

/** * 输出 HttpHead 中的财富总是。 css/js 自动判别真实路线 * @param
string 文件路径 * @return string */ function res_link($file) { $file
= res_path($file, $extension); if ($extension === ‘css’) { return
‘<link rel=”stylesheet” type=”text/css” href=”‘%20.%20$file%20.%20′”/>’; }
else if ($extension === ‘js’) { return ‘<script
type=”text/javascript” src=”‘.$file.'”></script>’; } else {
return false; } }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
/**
     * 输出 HttpHead 中的资源连接。 css/js 自动判断真实路径
     * @param  string  文件路径
     * @return string      
     */
    function res_link($file) {
        $file = res_path($file, $extension);
 
        if ($extension === ‘css’) {
           return ‘<link rel="stylesheet" type="text/css" href="’%20.%20$file%20.%20’"/>’;
        } else if ($extension === ‘js’) {
            return ‘<script type="text/javascript" src="’.$file.’"></script>’;
        } else {
            return false;
        }
    }

此处最入眼就是 res_path() 函数了,那些函数能自行路由财富的真人真事路线。举例:index.css = > css/home/index.css

该函数最重大的八个效果与利益是替换财富的压缩版本。

平昔看代码:

PHP

/** * 智能路由财富实际路线 * @param string 路径 * @param string
扩展名 * @return string 真实路线 */ function res_path($file,
&$extension) { //检查是否留存询问字符串 list($file, $query) =
explode(‘?’, $file . ‘?’); //获得增添名 $extension =
strtolower(pathinfo($file, PATHINFO_EXTENSION)); // $file =
str_replace(‘\\’, ‘/’, $file); //取安妥前调整器名 global $class; if
($class == null) exit(‘can not get class name’); $className =
strtolower($class); //此处的平整是那样: //比方,如若不加 /
,Home调节器对应的格式是: index.css,那么
此处的路线会产生css/home/index.css //假诺有 / ,调控器的格式能够是
/main.css,那么这里的路线会变成 css/main.css(公用的css类) if (‘/’ !==
$file[0]) { //index.css => css/home/index.css $object = $extension
.’/’. $className .’/’ . $file; } else { // /css/main.css 可能 /main.css
=> css/main.css $object = substr($file, 1); //若object是 main.css
,则自动抬高 扩充名目录 => css/main.css if (0 !==
strncasecmp($extension, $object, strlen($extension))) { $object =
$extension . ‘/’ . $object; } } //财富真实路线 $filepath =
WEBROOT.’www/’.$object; //替换压缩版本,这一部分逻辑与公事收缩逻辑对应 if
(in_array($extension, array(‘css’, ‘js’))) {
if(!str_start_with($object, ‘min/’) &&
file_exists(APPPATH.’libraries/ResMinifier.php’)) { require_once
应用软件PATH.’libraries/ResMinifier.php’; $resminifier = new ResMinifier();
//获取存放财富版本的文书的数组变量 $resState =
$resminifier->getResState(); //计算取安妥前文件版本号 $state =
$resminifier->_getResStateVersion($filepath); //判定该版本号是还是不是留存
if (isset($resState[$object])) { //剖断是不是是.min.css或.min.js结尾 if
(str_end_with($object, ‘.min.’.$extension)) {
//将版本号拼接上去,然后拿走min的文件路线 $minObject =
‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) .
$state . ‘.’ . $extension; } else {
//将版本号拼接上去,然后拿走min的公文路线 $minObject =
‘min/’.substr($object, 0, strlen($object) – strlen($extension)) . $state
. ‘.’ . $extension; } //判定min的路径是不是留存在$resState里面 if
(isset($resState[$minObject])) { $object = $minObject; $query = ”; }
} } $file = RES_BASE_URL . $object; } return ($query == null) ? $file
: ($file .’?’. $query); }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
/**
     * 智能路由资源真实路径
     * @param  string      路径
     * @param  string      扩展名
     * @return string       真实路径
     */
    function res_path($file, &$extension) {
        //检查是否存在查询字符串
        list($file, $query) = explode(‘?’, $file . ‘?’);
        //取得扩展名
        $extension = strtolower(pathinfo($file, PATHINFO_EXTENSION));
        //
        $file = str_replace(‘\\’, ‘/’, $file);
        //取得当前控制器名
        global $class;
        if ($class == null) exit(‘can not get class name’);
        $className = strtolower($class);
 
        //此处的规则是这样:
        //例如,如果不加 / ,Home控制器对应的格式是: index.css,那么 此处的路径会变成css/home/index.css
        //假如有 / ,控制器的格式可以是 /main.css,那么此处的路径会变成 css/main.css(公用的css类)
        if (‘/’ !== $file[0]) {
            //index.css => css/home/index.css
            $object = $extension .’/’. $className .’/’ . $file;
        } else {
            // /css/main.css 或者 /main.css => css/main.css
            $object = substr($file, 1);
 
            //若object是 main.css ,则自动加上 扩展名目录 => css/main.css
            if (0 !== strncasecmp($extension, $object, strlen($extension))) {
                $object = $extension . ‘/’ . $object;
            }
        }
        //资源真实路径
        $filepath = WEBROOT.’www/’.$object;
 
        //替换压缩版本,这部分逻辑与文件压缩逻辑对应
        if (in_array($extension, array(‘css’, ‘js’))) {
            if(!str_start_with($object, ‘min/’) && file_exists(APPPATH.’libraries/ResMinifier.php’)) {
                require_once APPPATH.’libraries/ResMinifier.php’;
                $resminifier = new ResMinifier();
                //获取存放资源版本的文件的数组变量
                $resState = $resminifier->getResState();
                //计算得到当前文件版本号
                $state = $resminifier->_getResStateVersion($filepath);
                //判断该版本号是否存在
                if (isset($resState[$object])) {
                    //判断是否是.min.css或.min.js结尾
                    if (str_end_with($object, ‘.min.’.$extension)) {
                        //将版本号拼接上去,然后得到min的文件路径
                        $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) . $state . ‘.’ . $extension;
                    } else {
                        //将版本号拼接上去,然后得到min的文件路径
                        $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
                    }
                    //判断min的路径是否存在在$resState里面
                     if (isset($resState[$minObject])) {
                        $object = $minObject;
                        $query = ”;
                     }
                }
 
            }
 
            $file = RES_BASE_URL . $object;
        }
 
        return ($query == null) ? $file : ($file .’?’. $query);
 
    }

代码基本上都给了疏解,方便我们轻便去精晓,前边生龙活虎部分是智能路线css、js能源的路子,后边后生可畏都部队分是替换压缩版本,这一片段的逻辑其实和能源裁减这里的逻辑基本风度翩翩致,便是经过能源文件路线,举办判断和拍卖,最终获得财富的滑坡版本的路线,最终就将财富的回退版本的门路再次回到去,放在'<link
rel=”stylesheet” type=”text/css” href=”‘ . $file . ‘”/>’里面。那样 
,就瓜熟蒂名落孙山将财富文件路线替换来了压缩版本的财富文件路线,并且在模板输出时,输出的是减削后的资源文件。

到此,财富替换的源委就到此解说结束。而整大器晚成项本领也剖判到此。

三、总结

在此本人聚集地附着本博文解说中的多少个公文代码:

Home.php

PHP

<?php defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
class Home extends MY_Controller { public function index() {
$this->smartyData[‘test’] = 111; //这几个默许是加载
www/css/home/index.css文件 $this->addResLink(‘index.css’);
//这一个暗许是加载www/js/jquery.all.min.js文件
$this->addResLink(‘/jquery.all.min.js’);
//那么些默许是加载www/js/index.js文件 $this->addResLink(‘index.js’);
$this->displayView(‘home/index.tpl’); } } 点击张开

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<?php
defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
 
class Home extends MY_Controller {
    public function index() {
        $this->smartyData[‘test’] = 111;
        //这个默认是加载 www/css/home/index.css文件
        $this->addResLink(‘index.css’);
        //这个默认是加载www/js/jquery.all.min.js文件
        $this->addResLink(‘/jquery.all.min.js’);
        //这个默认是加载www/js/index.js文件
        $this->addResLink(‘index.js’);
        $this->displayView(‘home/index.tpl’);
    }
}
 
点击打开

My_Controller.php

PHP

<?php defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
class MY_Controller extends CI_Controller { public function
__construct() { parent::__construct(); //压缩jscss能源文件
$this->compressResHandle(); }
//==========================使用SMARTY模板引擎================================//
/* 斯马特y母版页文件路线 */ protected $masterPage = ‘default.tpl’; /*
视图像和文字件路线*/ protected $smartyView; /* 要赋值给smarty视图的数额*/
protected $smartyData = []; /* 财富文件*/ protected $_resLink =
[‘js’=>[], ‘css’=>[]]; /** * 使用母版页输出一个视图 *
@return [type] [description] */ protected function
displayView($viewName = null, $masterPage = null) { //为空则选用私下认可母版
if ($masterPage == null) $masterPage = $this->masterPage;
//获取视图的输出内容 $viewContent =
$this->_fetchView($this->smartyData, $viewName, $masterPage);
$output = ”; //添加css Link foreach ($this->_resLink[‘css’] as
$v) { $output .= res_link($v); } //内容部分 $output .= $viewContent;
//尾部增加js 链接 foreach ($this->_resLink[‘js’] as $v) { $output
.= res_link($v); } //发送最后输出结果以至服务器的 HTTP 头到浏览器
$this->output->_display($output); return $output; } private
function _fetchView($smartyData, &$viewName, &$masterPage) { if
($viewName == null) $viewName = $this->smartyView; if
(empty($this->smarty)) { require_once
SMARTY_DI奥迪Q5.’斯马特y.class.php’; $this->smarty = new 斯马特y();
$this->smarty->setCompileDir(应用程式PATH . ‘cache/’);
$this->smarty->setCacheDir(应用软件PATH . ‘cache/’); }
//设置视图真实路线 $this->_getViewDir(true, $viewName, $masterPage,
$templateDir); foreach ($smartyData as $k => $v) {
$this->smarty->assign($k, $v); } if (empty($masterPage)) { return
$this->smarty->fetch($viewName); } else {
$this->smarty->assign(‘VIEW_MAIN’, $viewName); return
$this->smarty->fetch($masterPage); } } /** * 能源路线 * @param
[type] $filePath [description] */ protected function
addResLink($filePath) { list($filePath, $query) = explode(‘?’, $filePath
. ‘?’); $extension = strtolower(pathinfo($filePath,
PATHINFO_EXTENSION)); foreach ($this->_resLink as $v) { if (false
=== array_search($filePath, $this->_resLink[$extension])) {
$this->_resLink[$extension][] = $query == null ? $filePath :
$filePath .’?’. $query; } } return $this; } private function
_getViewDir($setTemplateDir, &$viewName, &$masterPage = null,
&$templateDir) { if (‘/’ === $viewName[0]) $viewName =
substr($viewName, 1); //是或不是使用模板,有,则路由到
/views/master_page/*****.tpl下去 if ($masterPage) { $masterPage =
‘/’ === $masterPage[0] ? substr($masterPage, 1) : (‘master_page’
.’/’. $masterPage); } //是不是设置模板目录 if ($setTemplateDir) {
$templateDir = VIEWPATH;
$this->smarty->setTemplateDir($templateDir); } } /** *
压缩js、css财富文件(优化) * @return [type] [description] */
private function compressResHandle() {
$this->load->library(‘ResMinifier’); //压缩钦命文件夹下的财富文件
$this->resminifier->compressRes(); } } 点击张开

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
<?php
defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
 
class MY_Controller extends CI_Controller {
    public function __construct() {
        parent::__construct();
 
        //压缩jscss资源文件
        $this->compressResHandle();
    }
 
    //==========================使用SMARTY模板引擎================================//
    /* Smarty母版页文件路径 */
    protected $masterPage = ‘default.tpl’;
    /* 视图文件路径*/
    protected $smartyView;
    /* 要赋值给smarty视图的数据*/
    protected $smartyData = [];
    /* 资源文件*/
    protected $_resLink = [‘js’=>[], ‘css’=>[]];
 
    /**
     * 使用母版页输出一个视图
     * @return [type] [description]
     */
    protected function displayView($viewName = null, $masterPage = null) {
        //为空则选用默认母版
        if ($masterPage == null) $masterPage = $this->masterPage;
        //获取视图的输出内容
        $viewContent = $this->_fetchView($this->smartyData, $viewName, $masterPage);
 
        $output = ”;
 
        //添加css Link
        foreach ($this->_resLink[‘css’] as $v) {
            $output .= res_link($v);
        }
 
        //内容部分
        $output .= $viewContent;
        //尾部添加js 链接
        foreach ($this->_resLink[‘js’] as $v) {
            $output .= res_link($v);
        }
        //发送最终输出结果以及服务器的 HTTP 头到浏览器
 
        $this->output->_display($output);
        return $output;
    }
 
    private function _fetchView($smartyData, &$viewName, &$masterPage) {
        if ($viewName == null) $viewName = $this->smartyView;
 
        if (empty($this->smarty)) {
            require_once SMARTY_DIR.’Smarty.class.php’;
            $this->smarty = new Smarty();
            $this->smarty->setCompileDir(APPPATH . ‘cache/’);
            $this->smarty->setCacheDir(APPPATH . ‘cache/’);
        }
 
        //设置视图真实路径
        $this->_getViewDir(true, $viewName, $masterPage, $templateDir);
 
        foreach ($smartyData as $k => $v) {
            $this->smarty->assign($k, $v);
        }
 
        if (empty($masterPage)) {
            return $this->smarty->fetch($viewName);
        } else {
            $this->smarty->assign(‘VIEW_MAIN’, $viewName);
            return $this->smarty->fetch($masterPage);
        }
    }
 
    /**
     * 资源路径
     * @param [type] $filePath [description]
     */
    protected function addResLink($filePath) {
        list($filePath, $query) = explode(‘?’, $filePath . ‘?’);
        $extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
        foreach ($this->_resLink as $v) {
            if (false === array_search($filePath, $this->_resLink[$extension])) {
                $this->_resLink[$extension][] = $query == null ? $filePath : $filePath .’?’. $query;
            }
        }
 
        return $this;
    }
 
    private function _getViewDir($setTemplateDir, &$viewName, &$masterPage = null, &$templateDir) {
        if (‘/’ === $viewName[0]) $viewName = substr($viewName, 1);
 
        //是否使用模板,有,则路由到 /views/master_page/*****.tpl下去
        if ($masterPage) {
            $masterPage = ‘/’ === $masterPage[0] ? substr($masterPage, 1) : (‘master_page’ .’/’. $masterPage);
        }
 
        //是否设置模板目录
        if ($setTemplateDir) {
            $templateDir = VIEWPATH;
            $this->smarty->setTemplateDir($templateDir);
        }
    }
 
    /**
     * 压缩js、css资源文件(优化)
     * @return [type] [description]
     */
    private function compressResHandle() {
        $this->load->library(‘ResMinifier’);
        //压缩指定文件夹下的资源文件
        $this->resminifier->compressRes();
    }
}
 
点击打开

ResMinifier.php

PHP

<?php defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
/** * 能源压缩类 */ class ResMinifier { /** 需求减小的能源目录*/
public $compressResDir = [‘css’, ‘js’]; /**
忽视压缩的门径,举例此处是js/icon发轫的门路忽视压缩*/ public
$compressResIngorePrefix = [‘js/icon’]; /** 财富根目录*/ public
$resRootDir; /** 财富版本文件路线*/ private $resStatePath; public
function __construct() { $this->resRootDir = WEBROOT . ‘www/’;
$this->resStatePath = WEBROOT . ‘www/resState.php’; } public function
compressRes() { //获取寄存版本的能源文件 $resState =
$this->getResState(); $count = 0; //初始遍历供给减小的能源目录
foreach ($this->compressResDir as $resDir) { foreach (new
RecursiveIteratorIterator(new
RecursiveDirectoryIterator($this->resRootDir . $resDir ,
FilesystemIterator::SKIP_DOTS)) as $file) { //获取该能源文件的相对路线$filePath = str_replace(‘\\’, ‘/’, $file->getRealPath());
//获取文件相对路线 $object = substr($filePath,
strlen($this->resRootDir)); //总结文件的本子号 $state =
$this->_getResStateVersion($filePath); //获取文件的多少个参数值 if
(true !== $this->getObjectInfo($object, $minObject, $needCompress,
$state, $extension)) { continue; } //压缩文件的相对路线 $minFilePath =
str_replace(‘\\’, ‘/’, $this->resRootDir. $minObject);
//************此处p推断是最器重片段之风流罗曼蒂克*****************//
//判别文件是不是存在且已经转移过 if (isset($resState[$object]) &&
$resState[$object] == $state && isset($resState[$minObject]) &&
file_exists($minFilePath)) { continue; } //确认保证/www/min/目录可写
$this->_ensureWritableDir(dirname($minFilePath)); if ($needCompress)
{ $this->compressResFileAndSave($filePath, $minFilePath); } else {
copy($filePath, $minFilePath); } $resState[$object] = $state;
$resState[$minObject] = ”; $count++; if ($count == 50) {
$this->_saveResState($resState); $count = 0; } } } if($count)
$this->_saveResState($resState); } /** * 获取财富文件有关新闻 *
@param [type] $object 能源文件路线 (www/css/home/index.css) * @param
[type] $minObject 压缩能源文件路线 (www/min/css/home/index.ae123a.css)
* @param [type] $needCompress 是还是不是须求压缩 * @param [type] $state
文件版本号 * @param [type] $extension 文件名后缀 * @return [type]
[description] */ public function getObjectInfo($object, &$minObject,
&$needCompress, &$state, &$extension) { //获取财富绝对路线 $filePath =
$this->resRootDir . $object; //决断能源是不是留存 if
(!file_exists($filePath)) return “财富文件不设有{$filePath}”; //版本号
$state = $this-> _getResStateVersion($filePath); //文件名后缀
$extension = pathinfo($filePath, PATHINFO_EXTENSION); //是不是要削减$needCompress = true; //决断财富文件是不是是以 .min.css只怕.min.js结尾的
//此类结尾常常都以已回降过,举个例子jquery.min.js,就不要再压缩了 if
(str_end_with($object, ‘.min.’.$extension, true)) {
//压缩后的财富存放路线,放在 /www/min/ 目录下 $minObject =
‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) .
$state .’.’. $extension; $needCompress = false; } else if
(in_array($extension, $this->compressResDir)) {
//此处是索要减小的文件目录 $minObject = ‘min/’.substr($object, 0,
strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
//看看是或不是是忽略的不二秘籍前缀 foreach ($this->compressResIngorePrefix as
$v) { if (str_start_with($object, $v, true)) { $needCompress = false;
} } } else { $minObject = ‘min/’.$object; $needCompress = false; }
return true; } /** * 获取寄放能源版本的公文 * 它是位于五个数组里 *
$resState = array( * ‘文件路线’ => ‘对应的版本号’, * ‘文件路线’
=> ‘对应的本子号’, * ‘文件路线’ => ‘对应的版本号’, * ); *
@return [type] [description] */ public function getResState() { if
(file_exists($this->resStatePath)) { require $this->resStatePath;
return $resState; } return []; } /** *
总括文件的本子号,那几个是基于测算文件MD5散列值得到版本号 *
只要文件内容改换了,所计算获得的散列值就能够不平等 *
用于判别能源文件是或不是有改动过 * @param [type] $filePath
[description] * @return [type] [description] */ public function
_getResStateVersion($filePath) { return
base_convert(crc32(md5_file($filePath)), 10, 36); } /** *
确定保证目录可写 * @param [type] $dir [description] * @return [type]
[description] */ private function _ensureWritableDir($dir) { if
(!file_exists($dir)) { @mkdir($dir, 0777, true); @chmod($dir, 0777); }
else if (!is_writable($dir)) { @chmod($dir, 0777); if
(!is_writable($dir)) { show_error(‘目录’.$dir.’不可写’); } } } /**
* 将压缩后的财富文件写入到/www/min/下去 * @param [type] $filePath
[description] * @param [type] $minFilePath [description] *
@return [type] [description] */ private function
compressResFileAndSave($filePath, $minFilePath) { if
(!file_put_contents($minFilePath,
$this->compressResFile($filePath))) {
//$CI->exceptions->show_exception(“写入文件{$minFilePath}退步”);
show_error(“写入文件{$minFilePath}战败”, -1); } } /** * 压缩财富文件
* @param [type] $filePath [description] * @return [type]
[description] */ private function compressResFile($filePath) {
$extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION)); if
($extension === ‘js’) { require_once ‘JShrink/Minifier.php’; return
\JShrink\Minifier::minify(file_get_contents($filePath)); } else if
($extension ===’css’) { $content = file_get_contents($filePath);
$content =
preg_replace(‘!/\*[^*]*\*+([^/][^*]*\*+)*/!’, ”,
$content); $content = str_replace([“\r\n”, “\r”, “\n”], ”,
$content); $content = preg_replace(‘/([{}),;:>])\s+/’, ‘$1’,
$content); $content = preg_replace(‘/\s+([{}),;:>])/’, ‘$1’,
$content); $content = str_replace(‘;}’, ‘}’, $content); return
$content; } else {
//$CI->exceptions->show_exception(“不援救压缩{extension}文件[$filePath]”);
show_error(“不扶植压缩{extension}文件[$filePath]”, -1); } } private
function _saveResState($resState) { ksort($resState); $content =
“<?php\n\n\$resState = array(\n”; foreach ($resState as $k =>
$v) { $content .= “\t ‘$k’ => ‘$v’,\n”; } $content .= “);\n\n”;
file_put_contents($this->resStatePath, $content); } } 点击张开

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
<?php
defined(‘BASEPATH’) OR exit(‘No direct script access allowed’);
/**
* 资源压缩类
*/
class ResMinifier {
    /** 需要压缩的资源目录*/
    public $compressResDir = [‘css’, ‘js’];
    /** 忽略压缩的路径,例如此处是js/icon开头的路径忽略压缩*/
    public $compressResIngorePrefix = [‘js/icon’];
    /** 资源根目录*/
    public $resRootDir;
    /** 资源版本文件路径*/
    private $resStatePath;
 
    public function __construct() {
        $this->resRootDir = WEBROOT . ‘www/’;
        $this->resStatePath = WEBROOT . ‘www/resState.php’;
    }
 
    public function compressRes() {
        //获取存放版本的资源文件
        $resState = $this->getResState();
        $count = 0;
 
        //开始遍历需要压缩的资源目录
        foreach ($this->compressResDir as $resDir) {
            foreach (new RecursiveIteratorIterator(new RecursiveDirectoryIterator($this->resRootDir . $resDir , FilesystemIterator::SKIP_DOTS)) as $file) {
                //获取该资源文件的绝对路径
                $filePath = str_replace(‘\\’, ‘/’, $file->getRealPath());
 
                //获取文件相对路径
                $object = substr($filePath, strlen($this->resRootDir));
 
                //计算文件的版本号
                $state = $this->_getResStateVersion($filePath);
 
                //获取文件的几个参数值
                if (true !== $this->getObjectInfo($object, $minObject, $needCompress, $state, $extension)) {
                    continue;
                }
 
                //压缩文件的绝对路径
                $minFilePath = str_replace(‘\\’, ‘/’, $this->resRootDir. $minObject);
 
                //************此处p判断是最重要部分之一*****************//
                //判断文件是否存在且已经改动过
                if (isset($resState[$object]) && $resState[$object] == $state && isset($resState[$minObject]) && file_exists($minFilePath)) {
                    continue;
                }
 
                //确保/www/min/目录可写
                $this->_ensureWritableDir(dirname($minFilePath));
 
                if ($needCompress) {
                    $this->compressResFileAndSave($filePath, $minFilePath);
                } else {
                    copy($filePath, $minFilePath);
                }
 
                $resState[$object] = $state;
                $resState[$minObject] = ”;
                $count++;
 
                if ($count == 50) {
                    $this->_saveResState($resState);
                    $count = 0;
                }
 
            }
        }
        if($count) $this->_saveResState($resState);
    }
 
    /**
     * 获取资源文件相关信息
     * @param  [type] $object       资源文件路径 (www/css/home/index.css)
     * @param  [type] $minObject    压缩资源文件路径 (www/min/css/home/index.ae123a.css)
     * @param  [type] $needCompress 是否需要压缩
     * @param  [type] $state        文件版本号
     * @param  [type] $extension    文件名后缀
     * @return [type]               [description]
     */
    public function getObjectInfo($object, &$minObject, &$needCompress, &$state, &$extension) {
        //获取资源绝对路径
        $filePath = $this->resRootDir . $object;
        //判断资源是否存在
        if (!file_exists($filePath)) return "资源文件不存在{$filePath}";
        //版本号
        $state = $this-> _getResStateVersion($filePath);
        //文件名后缀
        $extension = pathinfo($filePath, PATHINFO_EXTENSION);
        //是否要压缩
        $needCompress = true;
 
        //判断资源文件是否是以 .min.css或者.min.js结尾的
        //此类结尾一般都是已压缩过,例如jquery.min.js,就不必再压缩了
        if (str_end_with($object, ‘.min.’.$extension, true)) {
            //压缩后的资源存放路径,放在 /www/min/ 目录下
            $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) . $state .’.’. $extension;
            $needCompress = false;
        } else if (in_array($extension, $this->compressResDir)) {
            //此处是需要压缩的文件目录
            $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
            //看看是否是忽略的路径前缀
            foreach ($this->compressResIngorePrefix as $v) {
                if (str_start_with($object, $v, true)) {
                    $needCompress = false;
                }
            }
        } else {
            $minObject = ‘min/’.$object;
            $needCompress = false;
        }
        return true;
    }
 
    /**
     * 获取存放资源版本的文件
     * 它是放在一个数组里
     * $resState = array(
     *         ‘文件路径’ => ‘对应的版本号’,
     *         ‘文件路径’ => ‘对应的版本号’,
     *         ‘文件路径’ => ‘对应的版本号’,
     *     );
     * @return [type] [description]
     */
    public function getResState() {
        if (file_exists($this->resStatePath)) {
            require $this->resStatePath;
            return $resState;
        }
        return [];
    }
 
    /**
     * 计算文件的版本号,这个是根据计算文件MD5散列值得到版本号
     * 只要文件内容改变了,所计算得到的散列值就会不一样
     * 用于判断资源文件是否有改动过
     * @param  [type] $filePath [description]
     * @return [type]           [description]
     */
    public function _getResStateVersion($filePath) {
        return base_convert(crc32(md5_file($filePath)), 10, 36);
    }
 
    /**
     * 确保目录可写
     * @param  [type] $dir [description]
     * @return [type]      [description]
     */
    private function _ensureWritableDir($dir) {
        if (!file_exists($dir)) {
            @mkdir($dir, 0777, true);
            @chmod($dir, 0777);
        } else if (!is_writable($dir)) {
            @chmod($dir, 0777);
            if (!is_writable($dir)) {
                show_error(‘目录’.$dir.’不可写’);
            }
        }
    }
 
    /**
     * 将压缩后的资源文件写入到/www/min/下去
     * @param  [type] $filePath    [description]
     * @param  [type] $minFilePath [description]
     * @return [type]              [description]
     */
    private function compressResFileAndSave($filePath, $minFilePath) {
        if (!file_put_contents($minFilePath, $this->compressResFile($filePath))) {
 
            //$CI->exceptions->show_exception("写入文件{$minFilePath}失败");
            show_error("写入文件{$minFilePath}失败", -1);
        }
    }
 
    /**
     * 压缩资源文件
     * @param  [type] $filePath [description]
     * @return [type]           [description]
     */
    private function compressResFile($filePath) {
        $extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
        if ($extension === ‘js’) {
            require_once ‘JShrink/Minifier.php’;
            return \JShrink\Minifier::minify(file_get_contents($filePath));
        } else if ($extension ===’css’) {
            $content = file_get_contents($filePath);
            $content = preg_replace(‘!/\*[^*]*\*+([^/][^*]*\*+)*/!’, ”, $content);
            $content = str_replace(["\r\n", "\r", "\n"], ”, $content);
            $content = preg_replace(‘/([{}),;:>])\s+/’, ‘$1’, $content);
            $content = preg_replace(‘/\s+([{}),;:>])/’, ‘$1’, $content);
            $content = str_replace(‘;}’, ‘}’, $content);
            return $content;
        } else {
            //$CI->exceptions->show_exception("不支持压缩{extension}文件[$filePath]");
            show_error("不支持压缩{extension}文件[$filePath]", -1);
 
        }
    }
 
    private function _saveResState($resState) {
        ksort($resState);
        $content = "<?php\n\n\$resState = array(\n";
        foreach ($resState as $k => $v) {
            $content .= "\t ‘$k’ => ‘$v’,\n";
        }
        $content .= ");\n\n";
        file_put_contents($this->resStatePath, $content);
    }
 
}
 
点击打开

Common.php

PHP

<?php /** * 输出 HttpHead 中的财富总是。 css/js 自动判别真实路线
* @param string 文件路线 * @return string */ function
res_link($file) { $file = res_path($file, $extension); if ($extension
=== ‘css’) { return ‘<link rel=”stylesheet” type=”text/css” href=”‘ .
$file . ‘”/>’; } else if ($extension === ‘js’) { return ‘<script
type=”text/javascript” src=”‘.$file.'”></script>’; } else {
return false; } } /** * 智能路由能源实际路线 * @param string 路径 *
@param string 扩展名 * @return string 真实路线 */ function
res_path($file, &$extension) { //检查是或不是留存询问字符串 list($file,
$query) = explode(‘?’, $file . ‘?’); //取得扩张名 $extension =
strtolower(pathinfo($file, PATHINFO_EXTENSION)); // $file =
str_replace(‘\\’, ‘/’, $file); //取稳当前调控器名 global $class; if
($class == null) exit(‘can not get class name’); $className =
strtolower($class); //此处的国有国法是那般: //举例,如若不加 /
,Home调控器对应的格式是: index.css,那么
此处的路线会变成css/home/index.css //假若有 / ,调控器的格式能够是
/main.css,那么这里的路线会变成 css/main.css(公用的css类) if (‘/’ !==
$file[0]) { //index.css => css/home/index.css $object = $extension
.’/’. $className .’/’ . $file; } else { // /css/main.css 可能 /main.css
=> css/main.css $object = substr($file, 1); //若object是 main.css
,则自动抬高 扩大名目录 => css/main.css if (0 !==
strncasecmp($extension, $object, strlen($extension))) { $object =
$extension . ‘/’ . $object; } } //能源真实路线 $filepath =
WEBROOT.’www/’.$object; //替换压缩版本,那有个别逻辑与公事减弱逻辑对应 if
(in_array($extension, array(‘css’, ‘js’))) {
if(!str_start_with($object, ‘min/’) &&
file_exists(APPPATH.’libraries/ResMinifier.php’)) { require_once
APPPATH.’libraries/ResMinifier.php’; $resminifier = new ResMinifier();
//获取寄存财富版本的公文的数组变量 $resState =
$resminifier->getResState(); //计算取妥帖前文件版本号 $state =
$resminifier->_getResStateVersion($filepath); //推断该版本号是还是不是存在
if (isset($resState[$object])) { //推断是不是是.min.css或.min.js结尾 if
(str_end_with($object, ‘.min.’.$extension)) {
//将版本号拼接上去,然后拿走min的文书路线 $minObject =
‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) .
$state . ‘.’ . $extension; } else {
//将版本号拼接上去,然后拿走min的文件路线 $minObject =
‘min/’.substr($object, 0, strlen($object) – strlen($extension)) . $state
. ‘.’ . $extension; } //判定min的门径是还是不是存在在$resState里面 if
(isset($resState[$minObject])) { $object = $minObject; $query = ”; }
} } $file = RES_BASE_URL . $object; } return ($query == null) ? $file
: ($file .’?’. $query); } /** * 判别 subject 是或不是以 search领头,
参数钦定是还是不是忽视大小写 * @param [type] $subject [description] *
@param [type] $search [description] * @param boolean $ignore_case
[description] * @return [type] [description] */ function
str_start_with($subject, $search, $ignore_case = false) { $len2 =
strlen($search); if (0 === $len2) return true; $len1 = strlen($subject);
if ($len1 < $len2) return false; if ($ignore_case) { return 0 ===
strncmp($subject, $search, $len2); } else { return 0 ===
strncasecmp($subject, $search, $len2); } } /** * 判别 subject 是还是不是以
search结尾, 参数钦赐是不是忽视大小写 * @param [type] $subject
[description] * @param [type] $search [description] * @param
boolean $ignore_case [description] * @return [type]
[description] */ function str_end_with($subject, $search,
$ignore_case = false) { $len2 = strlen($search); if (0 === $len2)
return true; $len1 = strlen($subject); if ($len2 > $len1) return
false; if ($ignore_case) { return 0 === strcmp(substr($subject, $len1 –
$len2), $search); } else { return 0 === strcasecmp(substr($subject,
$len1 – $len2), $search); } } 点击张开

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
<?php
    /**
     * 输出 HttpHead 中的资源连接。 css/js 自动判断真实路径
     * @param  string  文件路径
     * @return string      
     */
    function res_link($file) {
        $file = res_path($file, $extension);
 
        if ($extension === ‘css’) {
           return ‘<link rel="stylesheet" type="text/css" href="’%20.%20$file%20.%20’"/>’;
        } else if ($extension === ‘js’) {
            return ‘<script type="text/javascript" src="’.$file.’"></script>’;
        } else {
            return false;
        }
    }
 
    /**
     * 智能路由资源真实路径
     * @param  string      路径
     * @param  string      扩展名
     * @return string       真实路径
     */
    function res_path($file, &$extension) {
        //检查是否存在查询字符串
        list($file, $query) = explode(‘?’, $file . ‘?’);
        //取得扩展名
        $extension = strtolower(pathinfo($file, PATHINFO_EXTENSION));
        //
        $file = str_replace(‘\\’, ‘/’, $file);
        //取得当前控制器名
        global $class;
        if ($class == null) exit(‘can not get class name’);
        $className = strtolower($class);
 
        //此处的规则是这样:
        //例如,如果不加 / ,Home控制器对应的格式是: index.css,那么 此处的路径会变成css/home/index.css
        //假如有 / ,控制器的格式可以是 /main.css,那么此处的路径会变成 css/main.css(公用的css类)
        if (‘/’ !== $file[0]) {
            //index.css => css/home/index.css
            $object = $extension .’/’. $className .’/’ . $file;
        } else {
            // /css/main.css 或者 /main.css => css/main.css
            $object = substr($file, 1);
 
            //若object是 main.css ,则自动加上 扩展名目录 => css/main.css
            if (0 !== strncasecmp($extension, $object, strlen($extension))) {
                $object = $extension . ‘/’ . $object;
            }
        }
        //资源真实路径
        $filepath = WEBROOT.’www/’.$object;
 
        //替换压缩版本,这部分逻辑与文件压缩逻辑对应
        if (in_array($extension, array(‘css’, ‘js’))) {
            if(!str_start_with($object, ‘min/’) && file_exists(APPPATH.’libraries/ResMinifier.php’)) {
                require_once APPPATH.’libraries/ResMinifier.php’;
                $resminifier = new ResMinifier();
                //获取存放资源版本的文件的数组变量
                $resState = $resminifier->getResState();
                //计算得到当前文件版本号
                $state = $resminifier->_getResStateVersion($filepath);
                //判断该版本号是否存在
                if (isset($resState[$object])) {
                    //判断是否是.min.css或.min.js结尾
                    if (str_end_with($object, ‘.min.’.$extension)) {
                        //将版本号拼接上去,然后得到min的文件路径
                        $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension) – 4) . $state . ‘.’ . $extension;
                    } else {
                        //将版本号拼接上去,然后得到min的文件路径
                        $minObject = ‘min/’.substr($object, 0, strlen($object) – strlen($extension)) . $state . ‘.’ . $extension;
                    }
                    //判断min的路径是否存在在$resState里面
                     if (isset($resState[$minObject])) {
                        $object = $minObject;
                        $query = ”;
                     }
                }
 
            }
 
            $file = RES_BASE_URL . $object;
        }
 
        return ($query == null) ? $file : ($file .’?’. $query);
 
    }
 
    /**
     * 判断 subject 是否以 search开头, 参数指定是否忽略大小写
     * @param  [type]  $subject     [description]
     * @param  [type]  $search      [description]
     * @param  boolean $ignore_case [description]
     * @return [type]               [description]
     */
    function str_start_with($subject, $search, $ignore_case = false) {
        $len2 = strlen($search);
        if (0 === $len2) return true;
        $len1 = strlen($subject);
        if ($len1 < $len2) return false;
        if ($ignore_case) {
            return 0 === strncmp($subject, $search, $len2);
        } else {
            return 0 === strncasecmp($subject, $search, $len2);
        }
    }
 
    /**
     * 判断 subject 是否以 search结尾, 参数指定是否忽略大小写
     * @param  [type]  $subject     [description]
     * @param  [type]  $search      [description]
     * @param  boolean $ignore_case [description]
     * @return [type]               [description]
     */
    function str_end_with($subject, $search, $ignore_case = false) {
        $len2 = strlen($search);
        if (0 === $len2) return true;
        $len1 = strlen($subject);
        if ($len2 > $len1) return false;
        if ($ignore_case) {
            return 0 === strcmp(substr($subject, $len1 – $len2), $search);
        } else {
            return 0 === strcasecmp(substr($subject, $len1 – $len2), $search);
        }
    }
 
点击打开

$resState.php(里面包车型地铁代码是自动生成的)

XHTML

<?php $resState = array( ‘css/home/index.css’ => ‘gwy933’,
‘js/echarts-all.min.js’ => ‘wqrf1c’, ‘js/home/index.js’ =>
‘s2z6f5’, ‘js/icon.js’ => ‘pgcyih’, ‘js/icon_home.js’ =>
‘zhl9iu’, ‘js/ion.rangeSlider.min.js’ => ‘akq381’,
‘js/jquery-ui-autocomplete.js’ => ‘8nzacv’, ‘js/jquery-ui.min.js’
=> ‘i6tw8z’, ‘js/jquery.all.min.js’ => ‘d2w76v’,
‘js/jquery.city.js’ => ‘toxdrf’, ‘js/jquery.easydropdown.min.js’
=> ‘2ni3i0’, ‘js/jquery.matrix.js’ => ‘3vrqkk’,
‘js/jquery.mobile.all.min.js’ => ‘ernu7r’, ‘js/jquery.qrcode.min.js’
=> ‘yuhnsj’, ‘js/jquery.tinyscrollbar.min.js’ => ‘oakk3c’,
‘js/mobiscroll.custom.min.js’ => ‘kn8h2e’, ‘js/store.min.js’ =>
‘n50jwr’, ‘js/swiper.animate1.0.2.min.js’ => ‘mm27zc’,
‘js/swiper.min.js’ => ‘jicwhh’, ‘min/css/home/index.6a4e83eb.css’
=> ”, ‘min/css/home/index.gwy933.css’ => ”,
‘min/css/home/index.puzbnf.css’ => ”,
‘min/css/home/index.thv8x7.css’ => ”,
‘min/js/echarts-all.76025ee0.js’ => ”,
‘min/js/echarts-all.wqrf1c.js’ => ”, ‘min/js/home/index.65363d41.js’
=> ”, ‘min/js/home/index.s2z6f5.js’ => ”,
‘min/js/icon.5bbd4db9.js’ => ”, ‘min/js/icon.pgcyih.js’ => ”,
‘min/js/icon_home.7fe74076.js’ => ”, ‘min/js/icon_home.zhl9iu.js’
=> ”, ‘min/js/ion.rangeSlider.261d8ed1.js’ => ”,
‘min/js/ion.rangeSlider.akq381.js’ => ”,
‘min/js/jquery-ui-autocomplete.1f3bb62f.js’ => ”,
‘min/js/jquery-ui-autocomplete.8nzacv.js’ => ”,
‘min/js/jquery-ui.418e9683.js’ => ”, ‘min/js/jquery-ui.i6tw8z.js’
=> ”, ‘min/js/jquery.all.2f248267.js’ => ”,
‘min/js/jquery.all.d2w76v.js’ => ”, ‘min/js/jquery.city.6b036feb.js’
=> ”, ‘min/js/jquery.city.toxdrf.js’ => ”,
‘min/js/jquery.easydropdown.2ni3i0.js’ => ”,
‘min/js/jquery.easydropdown.98fa138.js’ => ”,
‘min/js/jquery.matrix.3vrqkk.js’ => ”,
‘min/js/jquery.matrix.dfe2a44.js’ => ”,
‘min/js/jquery.mobile.all.3539ebb7.js’ => ”,
‘min/js/jquery.mobile.all.ernu7r.js’ => ”,
‘min/js/jquery.qrcode.7d9738b3.js’ => ”,
‘min/js/jquery.qrcode.yuhnsj.js’ => ”,
‘min/js/jquery.tinyscrollbar.578e4cb8.js’ => ”,
‘min/js/jquery.tinyscrollbar.oakk3c.js’ => ”,
‘min/js/mobiscroll.custom.4a684f66.js’ => ”,
‘min/js/mobiscroll.custom.kn8h2e.js’ => ”,
‘min/js/store.536545cb.js’ => ”, ‘min/js/store.n50jwr.js’ => ”,
‘min/js/swiper.4650ad75.js’ => ”,
‘min/js/swiper.animate1.0.2.517f82e8.js’ => ”,
‘min/js/swiper.animate1.0.2.mm27zc.js’ => ”,
‘min/js/swiper.jicwhh.js’ => ”, ); 点击张开

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
<?php
 
$resState = array(
     ‘css/home/index.css’ => ‘gwy933’,
     ‘js/echarts-all.min.js’ => ‘wqrf1c’,
     ‘js/home/index.js’ => ‘s2z6f5’,
     ‘js/icon.js’ => ‘pgcyih’,
     ‘js/icon_home.js’ => ‘zhl9iu’,
     ‘js/ion.rangeSlider.min.js’ => ‘akq381’,
     ‘js/jquery-ui-autocomplete.js’ => ‘8nzacv’,
     ‘js/jquery-ui.min.js’ => ‘i6tw8z’,
     ‘js/jquery.all.min.js’ => ‘d2w76v’,
     ‘js/jquery.city.js’ => ‘toxdrf’,
     ‘js/jquery.easydropdown.min.js’ => ‘2ni3i0’,
     ‘js/jquery.matrix.js’ => ‘3vrqkk’,
     ‘js/jquery.mobile.all.min.js’ => ‘ernu7r’,
     ‘js/jquery.qrcode.min.js’ => ‘yuhnsj’,
     ‘js/jquery.tinyscrollbar.min.js’ => ‘oakk3c’,
     ‘js/mobiscroll.custom.min.js’ => ‘kn8h2e’,
     ‘js/store.min.js’ => ‘n50jwr’,
     ‘js/swiper.animate1.0.2.min.js’ => ‘mm27zc’,
     ‘js/swiper.min.js’ => ‘jicwhh’,
     ‘min/css/home/index.6a4e83eb.css’ => ”,
     ‘min/css/home/index.gwy933.css’ => ”,
     ‘min/css/home/index.puzbnf.css’ => ”,
     ‘min/css/home/index.thv8x7.css’ => ”,
     ‘min/js/echarts-all.76025ee0.js’ => ”,
     ‘min/js/echarts-all.wqrf1c.js’ => ”,
     ‘min/js/home/index.65363d41.js’ => ”,
     ‘min/js/home/index.s2z6f5.js’ => ”,
     ‘min/js/icon.5bbd4db9.js’ => ”,
     ‘min/js/icon.pgcyih.js’ => ”,
     ‘min/js/icon_home.7fe74076.js’ => ”,
     ‘min/js/icon_home.zhl9iu.js’ => ”,
     ‘min/js/ion.rangeSlider.261d8ed1.js’ => ”,
     ‘min/js/ion.rangeSlider.akq381.js’ => ”,
     ‘min/js/jquery-ui-autocomplete.1f3bb62f.js’ => ”,
     ‘min/js/jquery-ui-autocomplete.8nzacv.js’ => ”,
     ‘min/js/jquery-ui.418e9683.js’ => ”,
     ‘min/js/jquery-ui.i6tw8z.js’ => ”,
     ‘min/js/jquery.all.2f248267.js’ => ”,
     ‘min/js/jquery.all.d2w76v.js’ => ”,
     ‘min/js/jquery.city.6b036feb.js’ => ”,
     ‘min/js/jquery.city.toxdrf.js’ => ”,
     ‘min/js/jquery.easydropdown.2ni3i0.js’ => ”,
     ‘min/js/jquery.easydropdown.98fa138.js’ => ”,
     ‘min/js/jquery.matrix.3vrqkk.js’ => ”,
     ‘min/js/jquery.matrix.dfe2a44.js’ => ”,
     ‘min/js/jquery.mobile.all.3539ebb7.js’ => ”,
     ‘min/js/jquery.mobile.all.ernu7r.js’ => ”,
     ‘min/js/jquery.qrcode.7d9738b3.js’ => ”,
     ‘min/js/jquery.qrcode.yuhnsj.js’ => ”,
     ‘min/js/jquery.tinyscrollbar.578e4cb8.js’ => ”,
     ‘min/js/jquery.tinyscrollbar.oakk3c.js’ => ”,
     ‘min/js/mobiscroll.custom.4a684f66.js’ => ”,
     ‘min/js/mobiscroll.custom.kn8h2e.js’ => ”,
     ‘min/js/store.536545cb.js’ => ”,
     ‘min/js/store.n50jwr.js’ => ”,
     ‘min/js/swiper.4650ad75.js’ => ”,
     ‘min/js/swiper.animate1.0.2.517f82e8.js’ => ”,
     ‘min/js/swiper.animate1.0.2.mm27zc.js’ => ”,
     ‘min/js/swiper.jicwhh.js’ => ”,
);
 
点击打开

 

除此以外附上JShrink那个PHP类的链接给我们下载 

假使咱们要么认为相当不够OK的话,我直接将那些试验项目打包供大家下载下来学习和精晓:

四、结语

最后本身来享受大家线上项目标实际实现方案:

小编们的花色分线上情况、开垦条件和测量检验意况,在开荒和测量试验情状中,大家每三次访谈都会调用压缩文件的接口,然后再对转移的财富文件的大小是要做判别的,借使削减后文件过小,就要求将该财富文件的代码归并到任何能源文件里去,以此减弱不要求的HTTP要求(因为文件太小,能源的下载时间远远低于HTTP央浼响应所成本的时日);另二个是图片的管理,全部图片都要通过压缩技术通过(举个例子在: 
那个网站去降低图片),在PC端,倘诺是小Logo的话,使用图片合併的法子开展优化,实际情况可参照本人的那篇博文:http://www.cnblogs.com/it-cen/p/4618954.html   
而在wap端的图样管理利用的是base64编码格局来管理图片,详细的情况能够参照本人的那篇博文: 
,当页面输出时,会使用redis来缓存页面(为何用内部存款和储蓄器来缓存并非利用页面缓存,那么些未来再享受给大家)。倘若是线上境况,每发壹回版本,才会调用一下财富文件减少这一个接口,何况线上的静态能源(css、js、图片)是存放在阿里云的OSS里的,与大家的应用服务器是抽离的。那是我们线上项指标黄金时代局地优化解决方案,当然了,还应该有越来越多优化本事,笔者会在这里后各种总括和享用出来,方便我们一同念书和沟通。

这次博文就享受到此,多谢观望此博文的心上大家。

1 赞 1 收藏
评论

图片 7

文件上传例子

 代码如下

<?php
header(‘content-type:text/html;charset=utf-8’);
require(‘uploadFile.php’);

if(isset($_POST[‘submit’])){
$uploads = $_FILES[‘file’];
$num_file = count($uploads[‘name’]);

$up = new UploadFile($uploads,’uploads’,1024);
$num = $up->upload();

if($num == $num_file ){
echo ‘全体文件上传成功’;
exit;
}else{
echo $num,’个文件上传成功<br/>’;
echo $up->showErrorInfo();
exit;
}
}

?>

<!DOCTYPE html PUBLIC “-//W3C//DTD XHTML 1.0 Transitional//EN”
“;
<html xmlns=” 1999/xhtml”>
<head>
<meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″
/>
<title>无标题文书档案</title>
</head>

<body>
<form action=”uup.php” method=”post”
enctype=”multipart/form-data”>
<p><input name=”file[]” type=”file” /></p>
<p><input name=”file[]” type=”file” /></p>
<p><input name=”file[]” type=”file” /></p>
<p><input name=”file[]” type=”file” /></p>
<input name=”submit” type=”submit” />
</form>
</body>
</html>

文本上传类代码

 代码如下

<?php
/*————*/
class UploadFile
{
var $user_post_file  = array();
var $save_file_path  = ”;
var $max_file_size   = ”;
var $allow_type      =
array(‘gif’,’jpg’,’png’,’zip’,’rar’,’txt’,’doc’,’pdf’);
var $final_file_path = ”;
var $save_info       = array();
var $error_info      = array();

/**
*构造函数,用于起头化音信。
*
*@param Array $file
*@param String $path
*@param Integer $size
*@param Array $type
*/
function __construct($file,$path,$size = 2097152,$type=”)
{
$this->user_post_file   = $file;
$this->save_file_path   = $path;
$this->max_file_size    = $size;
if(!$type=”){
$this->allow_type[] = $type;
}
}

/**
*
*
*@access public
*@return int
*/
function upload()
{
for($i=0;$i<count($this->user_post_file[‘name’]);$i++)
{
if($this->user_post_file[‘error’][$i] ==
0){//上传文件状态平常
//获取当前文件名,有时文件名,大小,类型,扩充名
$name     = $this->user_post_file[‘name’][$i];
$tmp_name = $this->user_post_file[‘tmp_name’][$i];
$size     = $this->user_post_file[‘size’][$i];
$type     = $this->user_post_file[‘type’][$i];
$ext_name = $this->getExtName($name);

//文件大小
if(!$this->checkSize($size)){
$this->error_info[] = ‘您上传的公文:’.$name.’太大’;
continue;
}
//扩展名
if(!$this->checkType($ext_name)){
$this->error_info[] = ‘您上传的文本:’.$name.’非法’;
continue;
}
//违规上传
if(!is_uploaded_file($tmp_name)){
$this->error_info[] = ‘您上传的公文:’.$name.’属于非法提交’;
continue;
}

//
$basename = $this->getBaseName($name,”.”.$ext_name);
$final_filename =
$basename.’-‘.time().’-‘.rand(1,10000).’.’.$ext_name;
$this->final_file_path =
$this->save_file_path.’/’.$final_filename;

if(!move_uploaded_file($tmp_name,$this->final_file_path)){
$this->error_info = $this->user_post_file[‘error’][$i];
continue;
}

//
$this->save_info[] = array(
“name” => $name,
“ext_name” => $ext_name,
          “type” => $type,
                            “size” => $size,
“final_filename” => $final_filename,
                            “path” => $this->final_file_path
);
}
}

return count($this->save_info);
}

/*
 *检查顾客上传文件的深浅时候合法
 *
 *@param Integer $size
 *@access private
 *@return boolean
 */
function checkSize($size)
{
if($size > $this->max_file_size){
return FALSE;
}

return TRUE;
}

/*
 *检查顾客上传文件的花色是还是不是合法
 *
 *@access private
 *@return boolean
 */
function checkType($extension)
{
foreach($this->allow_type
as $type){
if(strcasecmp($extension,$type) == 0){
return TRUE;
}
}

return FALSE;
}

/*
 *猎取文件的恢弘名
 *
 *@param string $filename
 *@access private
 *@return string
 */
function getExtName($filename)
{
$p = pathinfo($filename);

return $p[‘extension’];
}

/*
 *得到文件名(不满含扩张名)
 *
 *@param string $filename
 *@param string $type
 *@access private
 *@return boolean
 */
function getBaseName($filename,$ext_name)
{
$basename = basename($filename,$ext_name);

return $basename;
}

/*
 *
 *
 *
 */
function showErrorInfo()
{
if(count($this->error_info) != 0){
//echo ‘error…<br/>’;
foreach($this->error_info as $k=>$v){
echo ($k+1),’:’,$v,'<br/>’;
}
}
}

function getSaveInfo()
{
return $this->save_info;
}
}

//$upload = new UploadFile(”,”);
//$upload = new UploadFile();
//$upload->showErrorInfo();

?>

发表评论

电子邮件地址不会被公开。 必填项已用*标注

网站地图xml地图