浏览器在加载网站静态资源是有缓存策略的,当我们修改样式或脚本后,引用的资源地址没有发生改变,那么浏览器使用的资源都是以前的缓存。
如果加上一个生成模板主题目录的MD5文件,使用静态资源的时候加上这个MD5,当主题目录任意一个文件被修改、新增、或删减都会生成一个新的MD5,通知浏览器该使用新的文件了。
<script type="text/javascript" src="__theme__/static/main.js?{System:version}"></script>
目前的实现基于ThinkPHP6的模版扩展,仅供参考。
/*
* 根据目录文件生成md5
* https://jonlabelle.com/snippets/view/php/generate-md5-hash-for-directory
* @param string $directory
* @return boolean|string
*/
public static function hashDirectory($directory) {
if (!is_dir($directory)) {
return false;
}
$files = array();
$dir = dir($directory);
while (false !== ($file = $dir->read())) {
if ($file != '.' and $file != '..') {
if (is_dir($directory . '/' . $file)) {
$files[] = self::hashDirectory($directory . '/' . $file);
} else {
$files[] = md5_file($directory . '/' . $file);
}
}
}
$dir->close();
return md5(implode('', $files));
}
/*
模板扩展
*/
protected $tags = [
'version' => ['attr' => '', 'close' => 0], //版本信息
];
public function tagVersion() {
$theme_name = Tools::themeName(); //当前主题名称
$theme_list_path = public_path() . '/theme/'; //主题列表目录
$has_file = is_file($theme_list_path . '/md5.txt');
$theme_md5 = Tools::hashDirectory($theme_list_path . $theme_name);
if ($has_file) {
$old_md5 = file_get_contents($theme_list_path . 'md5.txt');
if ($theme_md5 !== $old_md5) {
$file = fopen($theme_list_path . '/md5.txt', 'w');
fwrite($file, $theme_md5);
fclose($file);
}
} else {
$file = fopen($theme_list_path . '/md5.txt', 'w');
fwrite($file, $theme_md5);
fclose($file);
}
return $theme_md5;
}
<link rel="stylesheet/less" type="text/css" href="__style__/style.less?{System:version}">