注
- 參考: https://segmentfault.com/a/1190000006843916 系列文章
為什麼要用webpack建構多頁應用
- 考慮到SEO的存在,我們需要開發一個多頁項目
- 前後端分離模式下,用後端模闆引擎處理多頁時候的前端的窘境
- gulp、grunt、fis3随着時代的遠去,webpack比它們更适合新的時代
- rollup、parcel等新時代的打包自動化工具生态圈不如webpack
談一談傳統後端模闆引擎下前端開發多頁應用時候的窘境
- 強依賴後端環境,很多時候可能還需要自己啟動後端項目
- 需要對後端模闆引擎比較熟悉,有很多甚至有自己的标簽文法(jsp的jstl,Struts2的标簽)
- 由于模闆文法的局限性,很多業務在這些模闆引擎裡面寫起來非常費力
然而
上面的這些窘境用gulp還是用webpack都依舊存在,依舊無解,但是新時代的前端工程師,對項目進行工程化還是很有必要的。。。
進入正題
用webpack建構一個純前端的多頁應用
建立項目multi-page-app,并初始化項目:
npm init
安裝對應的依賴:
npm install --save-dev webpack webpack-cli
在項目根目錄下建立webpack.config.js,配置如下:
module.exports = {
mode: "development",
entry: __dirname + "/index.js",
output: {
path: __dirname + "/dist",
filename: "bundle.js"
},
};
再建立index.js:
alert('This is index')
建立index.html:
<!DOCTYPE html>
<html >
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
</head>
<body>
<script src="./dist/bundle.js"></script>
</body>
</html>
控制台執行:
npx webpack
顯示:
則為打包成功,在浏覽器裡面打開index.html
出現上圖就是webpack搭建成功
下面我們來建立多頁項目的基本骨架
建立page和static目錄,并分别建立admin和index目錄:
然後下載下傳依賴:
npm install --save-dev html-webpack-plugin
修改webpack.config.js的配置如下:
const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
mode: "development",
entry: {
index: __dirname + "/static/index/entry.js",
admin: __dirname + "/static/admin/entry.js"
},
output: {
path: __dirname + "/dist",
filename: "static/[name]/bundle.js"
},
plugins: [
new HtmlWebpackPlugin({
chunks: ["admin"],
filename: "admin.html",
template: __dirname + "/page/admin/content.html"
}),
new HtmlWebpackPlugin({
chunks: ["index"],
filename: "index.html",
template: __dirname + "/page/index/content.html"
})
]
};
上面增加了兩個入口js,以及兩個對應的html,然後讓我們分别建立對應的入口js以及html:
然後執行webpack編譯指令,可以看到生成的dist檔案夾:
打開index.html或者admin.html,就可以看到他們打包好的html内容以及js引用的情況,最基本的多頁應用就完成了,你可以在兩個html裡面随意寫入後端的模闆引擎的文法來進行開發,通過:
webpack --watch
來不斷的更新輸出到後端的模闆以及靜态資源目錄,就可以保證正常開發了,但是到了這裡我們還是應該繼續優化一下這些模闆,比如增加一些公共模闆的套用,公共元件的複用等等。
優化
繼續上面的項目,讓我們引入幾個npm依賴:
npm install --save-dev ejs-compiled-loader ejs ejs-loader
這裡為什麼要引入ejs呢,ejs就是一個前端的模闆引擎,可供前端以及node使用,但是若是其他語言的模闆引擎并沒有任何用處。而這裡引入的主要作用是,為了使用這些模闆引擎本身擁有的文法以及loader來實作公共模闆的套用、元件的複用等等。讓我們在page下面建立common目錄,并分别建立html.ejs、header.ejs、footer.ejs:
<!-- html.ejs -->
<!DOCTYPE html>
<html >
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
</head>
<body>
<header>
<%= header %>
</header>
<main>
<%= main %>
</main>
<footer>
<%= footer %>
</footer>
</body>
</html>
<!-- header.ejs -->
<div class="header">This is header</div>
<!-- footer.ejs -->
<div class="footer">This is footer</div>
然後在page下面的admin以及index下面新增page.js,内容如下:
// page.js
const content = require('./content.html'),
html = require('../common/html.ejs'),
header = require('../common/header.ejs'),
footer = require('../common/footer.ejs');
module.exports = html({
header: header(),
main: content(),
footer: footer()
})
修改webpack配置如下:
const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
mode: "development",
entry: {
index: __dirname + "/static/index/entry.js",
admin: __dirname + "/static/admin/entry.js"
},
output: {
path: __dirname + "/dist",
filename: "static/[name]/bundle.js"
},
module: {
rules: [
{
test: /\.ejs|html$/,
loader: "ejs-loader"
}
]
},
plugins: [
new HtmlWebpackPlugin({
chunks: ["admin"],
filename: "admin.html",
template: __dirname + "/page/admin/page.js"
}),
new HtmlWebpackPlugin({
chunks: ["index"],
filename: "index.html",
template: __dirname + "/page/index/page.js"
})
]
};
執行webpack編譯指令就可以得到最終編譯合成一樣的admin.html:
這裡通過ejs模闆,通過ejs模闆引擎通過ejs-loader的編譯最終通過html-webpack-plugin輸出了整個html模闆,當然我們也可以再裡面寫入任意的後端模闆引擎的代碼。
這裡主要是直接輸出整合了後端的模闆引擎的代碼,通過編譯直接生成了最終的html,而不是像後端一般模闆引擎的做法在去采用extends以及include的形式在服務端在進行一定的io操作最終編譯代碼,可以提高一定的效率,雖然這個效率可能微乎其微,但是性能本身就是一點點的堆疊,這裡快一點那裡快一點,整個網站的整體性能就上去了。