原文地址:Node JS後端項目開發與生產環境總結javascript
Node JS經常使用後端框架有express、koa、sails。國產框架有個egg js,已經在cnode投入生產了,還有個think js,相似think php,在此支持一波。每一個框架在開發環境與生產環境都有所不一樣,這裏以
koa
爲例
創建在後臺模板渲染(ejs, pug)的基礎上。先後分離架構請參考webpack熱更新實現php
nodemon在js文件變化後悔從新運行程序,在package.json
的scripts
中添加:html
dev: 'nodemon server.js'
npm run dev
nodemon還有許多可選配置,具體參閱nodemon文檔前端
以koa爲例java
app.on('error', err => { log.error('server error', err) });
如若想要將錯誤拋出到瀏覽器頁面和美化錯誤頁面,express
可用express-error-handler,koa
可用onerrornode
因爲是後臺模板渲染,因此無法用webpack-dev-server
進行自動刷新。能作的就是利用webpack
的watch
在前端js改變後自動打包,固然仍是免不了手動刷新webpack
// webpack.config.js const config = { entry: { app: path.resolve(root, './modules/app.js'), about: path.resolve(root, './modules/about.js'), }, output: { path: path.resolve(root, './dist'), publicPath: path.resolve(root, './dist'), filename: '[name].js' }, module: { rules: [ { test: /(\.js)$/, use: { loader: "babel-loader", }, exclude: /node_modules/ } ] }, devtool: '#eval-source-map', watch: true, watchOptions:{ poll:1000,//監測修改的時間(ms) ignored:/node_modules/,//不監測 } };
注意必定要開啓source-map
,否則沒法定位報錯位置。爲通知webpack
是生產仍是開發環境,可使用cross-env,而後在package.json
的scripts
中添加:nginx
"watch": "cross-env NODE_ENV=development webpack --watch webpack.config.js"
開發時應運行兩個命令:git
// nodemon npm run dev // webpack npm run watch
生產環境通常使用pm2,pm2
已經幫咱們完成了進程守護和負載均衡,內部實現原理在此再也不贅述,具體參考pm2文檔。github
// 生成pm2配置文件ecosystem.config.js pm2 ecosystem
生成的配置文件已包含了生產環境的基本本質。跟多配置請參考pm2文檔,在package.json
文件的scripts
中添加
"prd": "pm2 start ecosystem.config.js --env production"
生產環境下運行
npm run prd
這時咱們能夠經過process
全局變量獲取到環境狀態,在app.js
中添加
const prdEnv = process.env.NODE_ENV == 'production'
const staticCache = require('koa-static-cache') if(prdEnv) { // 靜態緩存 app.use(staticCache(path.join(__dirname, 'public'), { maxAge: 365 * 24 * 60 * 60 })) }
const compress = require('koa-compress') if(prdEnv) { // gzip app.use(compress({ filter: function (content_type) { return /text/i.test(content_type) }, threshold: 2048, flush: require('zlib').Z_SYNC_FLUSH })) }
相似nginx
的access.log
和error.log
,利用fs
模塊的appendFile
方法來輸出日誌。首先在項目根目錄下新建文件夾logs
const fs = require('fs') const path = require('path') if(prdEnv) { // logger app.use(async(ctx, next) => { const start = new Date() await next() const ms = new Date() - start fs.appendFile(path.join(__dirname, 'logs', ctx.status < 400 ? 'access.log' : 'error.log'), `[${start.toLocaleString()}] ${ctx.status} ${ctx.method} ${ctx.url} - ${ms}ms\r\n`) }) }
// force https app.use((ctx, next) => { if(ctx.protocol == 'http') { ctx.redirect(ctx.href.replace('http', 'https')) } else { return next() } })
創建一個模板命名爲notFound.pug
,在路由以後渲染
// 404 app.use(async (ctx) => { await ctx.render('notFound') })
在webpack中添加插件
// webpack.config.js // 提取公共js new webpack.optimize.CommonsChunkPlugin({name: 'common'}) // 壓縮代碼 new webpack.optimize.UglifyJsPlugin({ sourceMap: false, parallel: true, mangle: true, compress: { warnings: false, drop_debugger: true, drop_console: true } }) // package.json "build": "cross-env NODE_ENV=production webpack --config webpack.config.js"
發佈應用時需運行
npm run build npm run prd