這篇文章給大家介紹Egg.js定制業(yè)務(wù)Web框架擴(kuò)展的示例分析,內(nèi)容非常詳細(xì),感興趣的小伙伴們可以參考借鑒,希望對(duì)大家能有所幫助。
10年的忠縣網(wǎng)站建設(shè)經(jīng)驗(yàn),針對(duì)設(shè)計(jì)、前端、開(kāi)發(fā)、售后、文案、推廣等六對(duì)一服務(wù),響應(yīng)快,48小時(shí)及時(shí)工作處理。營(yíng)銷(xiāo)型網(wǎng)站建設(shè)的優(yōu)勢(shì)是能夠根據(jù)用戶(hù)設(shè)備顯示端的尺寸不同,自動(dòng)調(diào)整忠縣建站的顯示方式,使網(wǎng)站能夠適用不同顯示終端,在瀏覽器中調(diào)整網(wǎng)站的寬度,無(wú)論在任何一種瀏覽器上瀏覽網(wǎng)站,都能展現(xiàn)優(yōu)雅布局與設(shè)計(jì),從而大程度地提升瀏覽體驗(yàn)。成都創(chuàng)新互聯(lián)公司從事“忠縣網(wǎng)站設(shè)計(jì)”,“忠縣網(wǎng)站推廣”以來(lái),每個(gè)客戶(hù)項(xiàng)目都認(rèn)真落實(shí)執(zhí)行。
談到Node.js Web開(kāi)發(fā),你會(huì)想到的是什么?
首先是框架選型:Express、Koa、NestJS、EggJS等,需要從繁多的框架中選擇一個(gè)適合團(tuán)隊(duì)的。
框架選好之后,需要初始化項(xiàng)目,安裝依賴(lài)、插件、中間件、配置常見(jiàn)庫(kù);
假如再一次做新項(xiàng)目,還得從頭初始化再來(lái)一次。好一點(diǎn)的可以封裝一個(gè)骨架,從骨架中生成新項(xiàng)目,周而復(fù)始。
我們先想想這樣做的缺陷是什么?
如果沒(méi)有骨架,團(tuán)隊(duì)成員技術(shù)選型不一致,變成遍地開(kāi)花;每個(gè)新項(xiàng)目維護(hù)都有學(xué)習(xí)成本。
即便有骨架,發(fā)生一些升級(jí)也需要每個(gè)項(xiàng)目都統(tǒng)一升級(jí)一遍,后續(xù)也會(huì)導(dǎo)致不統(tǒng)一。
基于以上的原因,我們考慮的解法是:基于通用框架封裝一個(gè)統(tǒng)一的業(yè)務(wù)框架,將團(tuán)隊(duì)用到的公共功能下沉到業(yè)務(wù)框架中。
主流的Web框架選型主要分為兩大流派,基于Express 和 基于Koa,他們都是由同一團(tuán)隊(duì)打造。Express和Koa在設(shè)計(jì)思路上的區(qū)別在于:
Express本身功能內(nèi)置了很多中間件,集成度高,使用省心,上手即用;
Koa使用精簡(jiǎn)的內(nèi)核,更輕量,使用需要使用者做技術(shù)選型按需搭建積木;
基于以上的設(shè)計(jì)思路上的差別,基于對(duì)靈活配置型的考慮,筆者選擇了 基于Koa 的 流派。但他們都太底層,對(duì)于搭建企業(yè)級(jí)業(yè)務(wù)框架還需要做較多定制。
基于上述的訴求,最后小編選擇了Egg.js。
Egg.js地址:https://eggjs.org/zh-cn/
Egg.js是阿里開(kāi)源的基于Koa2企業(yè)級(jí)Node.JS框架,其核心設(shè)計(jì)就是希望基于Egg.js孕育出更多上層框架。
引用官網(wǎng)的一句話
我們深知企業(yè)級(jí)應(yīng)用在追求規(guī)范和共建的同時(shí),還需要考慮如何平衡不同團(tuán)隊(duì)之間的差異,求同存異。所以我們沒(méi)有選擇社區(qū)常見(jiàn)框架的大集市模式(集成如數(shù)據(jù)庫(kù)、模板引擎、前端框架等功能),而是專(zhuān)注于提供 Web 開(kāi)發(fā)的核心功能和一套靈活可擴(kuò)展的插件機(jī)制。「——官網(wǎng)」
在開(kāi)始定制業(yè)務(wù)框架前,我們先設(shè)定一下需要定制的目標(biāo)。
擴(kuò)展Controller,添加API成功/失敗返回結(jié)果函數(shù);
設(shè)置默認(rèn)模板引擎為 pug;
擴(kuò)展ctx,添加util, 將dayjs作為統(tǒng)一日期處理庫(kù);
如果對(duì)Egg.js不太熟悉,建議可以先學(xué)習(xí)下Egg.js的基本使用。
通過(guò)以下命令,初始化項(xiàng)目。其中 --type=framework 表示框架骨架
villa-framework為框架名和項(xiàng)目文件夾名
$ npm init egg --type=framework villa-framework
以下是初始化出來(lái)的目錄
villa-framework ├── app │ ├── extend │ └── service ├── config │ ├── config.default.js │ └── plugin.js ├── lib │ └── framework.js ├── test │ ├── fixtures │ └── framework.test.js ├── README.md ├── index.js └── package.json
其中app、config目錄基本跟正常的Egg.js應(yīng)用無(wú)差異,但增加了framework.js文件,對(duì)應(yīng)用進(jìn)行擴(kuò)展。
// lib/framework.js 'use strict'; const path = require('path'); const egg = require('egg'); const EGG_PATH = Symbol.for('egg#eggPath'); class Application extends egg.Application { get [EGG_PATH]() { return path.dirname(__dirname); } } class Agent extends egg.Agent { get [EGG_PATH]() { return path.dirname(__dirname); } } module.exports = Object.assign(egg, { Application, Agent, });
// 以下是Egg.js Controller使用的代碼 const Controller = require('egg').Controller; // 未來(lái)修改為 const Controller = require('villa-framework').Controller;
由上面源碼我們知道,Controller來(lái)自egg對(duì)象,因此我們只需要替換為我們定義的Controller即可。
// lib/framework.js 增加 class Controller extends egg.Controller { ok(data) { this.ctx.body = { success: true, data, }; } fail(message, code) { this.ctx.body = { code, message, }; } } // 導(dǎo)出增加Controller module.exports = Object.assign(egg, { Application, Agent, Controller, });
這樣用戶(hù)使用的Controller就變成框架的Controller。
安裝依賴(lài)
$ npm i --save egg-view-pug
啟動(dòng)插件
// config/plugin.js exports.pug = { enable: true, package: 'egg-view-pug', };
設(shè)置view渲染
// config/config.default.js config.view = { mapping: { '.pug': 'pug', }, };
這樣應(yīng)用框架就不需要再單獨(dú)安裝配置,默認(rèn)擁有pug模板引擎能力。不同的業(yè)務(wù)可以根據(jù)自己的需求,默認(rèn)加載并配置一些默認(rèn)插件。
安裝依賴(lài)
$ npm i --save dayjs
app文件夾中新建util文件,添加day.js并導(dǎo)出
// app/util/dayjs.js 'use strict'; const dayjs = require('dayjs'); exports.dayjs = dayjs;
因?yàn)樾略龅膗til不會(huì)默認(rèn)加載,配置自定義加載器。
// config/config.default.js config.customLoader = { // 定義在 app 上的屬性名 app.util util: { directory: 'app/util', // 如果是 ctx 則使用 loadToContext inject: 'ctx', // 是否加載框架和插件的目錄 loadunit: true, }, };
這樣框架就會(huì)默認(rèn)加載util。
接下來(lái)我們創(chuàng)建應(yīng)用,使用上面的villa-framework
$ npm init egg --type=simple villa-project $ npm i --save villa-framework $ npm i $ npm run dev
package.json中egg字段中添加 "framework": "villa-framework"
"egg": { "framework": "villa-framework", },
'use strict'; // app/controller/home.js const Controller = require('villa-framework').Controller; class HomeController extends Controller { async index() { const { dayjs } = this.ctx.util.dayjs; const now = dayjs().format('YYYY-MM-DD HH:mm:ss'); await this.ctx.render('index.pug', { now }); } renderOk() { this.ok('hi, egg'); } renderFail() { this.fail('fail', 200); } } module.exports = HomeController;
'use strict'; // app/router.js /** * @param {Egg.Application} app - egg application */ module.exports = (app) => { const { router, controller } = app; router.get('/', controller.home.index); router.get('/ok', controller.home.renderOk); router.get('/fail', controller.home.renderFail); };
在app中創(chuàng)建view文件夾,并添加index.pug
html head title hello world body p hello world p #{now}
啟動(dòng)后即可看到演示的結(jié)果。
打開(kāi) http:///127.0.0.1:7001
打開(kāi) http:///127.0.0.1:7001/ok
打開(kāi) http:///127.0.0.1:7001/fail
以上通過(guò)實(shí)現(xiàn)擴(kuò)展Controller,擴(kuò)展ctx,以及添加默認(rèn)插件,演示了對(duì)Egg.js基本的擴(kuò)展。
當(dāng)然對(duì)于一個(gè)完整的業(yè)務(wù)框架,還缺少很多東西,但以上提供了一種對(duì)Egg.js的擴(kuò)展的思路,希望可以為你擴(kuò)展提供思路。
關(guān)于Egg.js定制業(yè)務(wù)Web框架擴(kuò)展的示例分析就分享到這里了,希望以上內(nèi)容可以對(duì)大家有一定的幫助,可以學(xué)到更多知識(shí)。如果覺(jué)得文章不錯(cuò),可以把它分享出去讓更多的人看到。