我使用php / twig / webpack工具创建传统网站(不是单页面应用程序)。几乎每个站点都有自己的入口脚本。还有vendor
和common
个js文件。
如何在我的twig文件中注入带有哈希的入口块(以处理浏览器缓存)?这些存储在templates
文件夹中,应该保留在那里(不要转到public
文件夹,因为它们被PHP使用)。如何将脚本标签注入twig文件?
这是我的twig一般布局文件:
{% block html %}
<!DOCTYPE html>
<html lang="pl">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<base href="/">
<title>
{% block title %}{% endblock %}
</title>
<link href="css/style.css" rel="stylesheet">
<script src="js/vendor.js"></script>
<script src="js/common.js"></script>
</head>
<body>
{% block body %}
{% endblock %}
{% block scripts %}
{% endblock %}
</body>
</html>
{% endblock %}
和twig例如联系页面:
{% extends "layout/bootstrap.twig" %}
{% block scripts %}
<script src="js/entry-contact.js"></script>
{% endblock %}
{% block body %}
<h1>Contact form</h1>
{% endblock %}
答案 0 :(得分:5)
如Webpack documentation中所述,可以从编译统计中提取文件哈希值。
module.exports = {
/*...*/
plugins: [
function() {
this.plugin("done", function(stats) {
require("fs").writeFileSync(
"stats.json",
JSON.stringify(stats.toJson())
);
});
}
]
};
但使用其中一个插件更容易:webpack-manifest-plugin或assets-webpack-plugin。例如,WebpackManifestPlugin
创建一个简单的JSON文件manifest.json
,其中包映射到实际文件名:
{
"main.js": "main.155567618f4367cd1cb8.js",
"vendor.js": "vendor.c2330c22cd2decb5da5a.js"
}
现在您需要阅读它并更改模板中的路径。
例如,我们可以创建一个简单的Twig extension:
use Twig_Extension;
use Twig_SimpleFilter;
class WebpackAssetsExtension extends Twig_Extension
{
private $manifest;
public function __construct()
{
// ONLY FOR EXAMPLE! Code is intentionally simplified.
// In real world you should not parse this JSON in production.
// Do it at the container building step (in bundle extensions,
// compiler passes, etc) or at the cache warming.
$jsonContents = file_get_contents('manifest.json');
$this->manifest = json_decode($jsonContents, true);
}
public function getFilters()
{
return [
new Twig_SimpleFilter('webpack_asset', function (string $name): string {
return $this->manifest[$name];
}),
];
}
}
并在模板中应用此过滤器:
<script src="{{ 'vendor.js'|webpack_asset }}"></script>