摘要:如果需要在構造函數做一些處理,一定要有這句話,才能保證后面的使用。文件夾里面存放工具類引用拿到內置對象也就是進入這個文件頁面渲染使用的是頁面模板在里面添加添加渲染
egg.js是什么
是一個node.js的后臺web框架,類似的還有express,koa
優勢:規范、插件機制
Egg.js約定了一套代碼目錄結構
(配置config、路由router、擴展extend、中間件middleware、控制器controller)
規范的目錄結構,可以使得不同團隊的開發者使用框架寫出來的代碼風格會更一致,接手成本也會更低。
BFF層(前后端之間的中間層)、全棧、SSR(服務端渲染)
目錄結構框架約定的目錄
app/router.js 用于配置URL路由規則 app/contorller/** 用于解析用戶的輸入,處理后返回相應的結果 app/service/** 用于編寫業務邏輯層 【可選】 app/middleware/** 用于編寫中間件 【可選】 app/service/** 用于框架的擴展 【可選】 ... 自定義的目錄 app/view/** 用于防止模板文件 【可選】加載順序
Egg 將應用、框架和插件都稱為加載單元(loadUnit);
在加載過程中,Egg會遍歷所有的加載單元,加載時有一點的優先級
· 插件 => 框架 => 應用依次加載
· 依賴方先加載
· 框架按繼承順序加載,越底層越先加載
如有這樣一個應用配置了如下依賴
app | ├── plugin2 (依賴 plugin3) | └── plugin3 └── framework1 | └── plugin1 └── egg
最終的加載順序為
=> plugin1 => plugin3 => plugin2 => egg => framework1 => app
文件加載順序
package.json => config => app/extend => app.js => app/service => app/middleware => app/controller => app/router.jsrouter
首先我們需要配置路由
因為我們在實際的開發中會使用很多路由所以這里我們將路由改成分級的
在app下創建一個router文件夾用來存放路由文件home.js
//app/router/home.js "use strict" module exports = app => { const { home } = app.controller //獲取controller下的home.js app.get("/",home.index); app.get("/home/param",home.getParam); app.get("/home/postParam",home.postParam); } // app/router.js "use strict" const RouteHome = require("./router/home"); module.exports = { const {router, controller} = app; RouteHome(app); } //app/controller/home.js "use strict" const Controller = require("egg").Controller; class HomeController extends Controller { async index() { await this.ctx.render("/index",{name:"egg"}); } async getParam() { let id = await this.ctx.query.id; this.ctx.body = id; } async postParam(){ let id = await this.ctx.request.body.id; //獲取post參數 this.ctx.body = id; } } module exports = HomeController;controller
我們通過 Router 將用戶的請求基于 method 和 URL 分發到了對應的 Controller 上, Controller 負責解析用戶的輸入,處理后返回相應的結果
框架推薦 Controller 層主要對用戶的請求參數進行處理(校驗、轉換),然后調用對應的 service 方法處理業務,得到業務結果后封裝并返回
所有的 Controller 文件都必須放在 app/controller 目錄下,可以支持多級目錄
訪問的時候可以通過目錄名級聯訪問
//在app/controller目錄下 新建一個controller "use strict" const Controller = required("egg").Controller; class CustomerController extends Controller { async customIndex() { //ctx.body 是 ctx.response.body 的簡寫,不要和 ctx.request.body 混淆了 this.ctx.body = "this is my controller"; } } module.exports = CustomController; //在router.js中配置路由(訪問時請求的路徑) "use strict" module.exports = app => { //相當于拿到app文件夾下的router和controller const {router, controller} = app; router.get("/", controller.home.index); router.get("/custom",controller.customerController.customIndex); }
定義的 Controller 類,會在每一個請求訪問到 server 時實例化一個全新的對象,而項目中的 Controller 類繼承于 egg.Controller,會有下面幾個屬性掛在 this 上
- this.ctx 框架封裝好的處理當前請求的各種便捷屬性和方法 - this.app 框架提供的全局對象和方法 - this.service 訪問抽象出的業務層 相當于 this.ctx.service - this.config 運行的配置項 - this.logger 日志service
業務邏輯層
"use strict"; const Service = require("egg").Service; class customService extends Service { async show(zc, hh) { //異步防阻塞 return zc + " and " + hh; } } module.exports = UserService; //controller代碼 "use strict"; const Controller = require("egg").Controller; class CustomController extends Controller { async custonIndex() { let str = await this.ctx.service.customService.show("zc","hh"); //這里使用await來獲取異步方法的返回值 this.ctx.body = "this is my controller"+str; } } module.exports = CustomController;
一個更完整的栗子
// app/router.js module.exports = app => { app.router.get("/user/:id", app.controller.user.info); }; // app/controller/user.js const Controller = require("egg").Controller; class UserController extends Controller { async info() { const userId = ctx.params.id; const userInfo = await ctx.service.user.find(userId); ctx.body = userInfo; } } module.exports = UserController; // app/service/user.js const Service = require("egg").Service; class UserService extends Service { // 默認不需要提供構造函數。 // constructor(ctx) { // super(ctx); 如果需要在構造函數做一些處理,一定要有這句話,才能保證后面 `this.ctx`的使用。 // // 就可以直接通過 this.ctx 獲取 ctx 了 // // 還可以直接通過 this.app 獲取 app 了 // } async find(uid) { // 假如 我們拿到用戶 id 從數據庫獲取用戶詳細信息 const user = await this.ctx.db.query("select * from user where uid = ?", uid); // 假定這里還有一些復雜的計算,然后返回需要的信息。 const picture = await this.getPicture(uid); return { name: user.user_name, age: user.age, picture, }; } async getPicture(uid) { const result = await this.ctx.curl(`http://photoserver/uid=${uid}`, { dataType: "json" }); return result.data; } } module.exports = UserService; // curl http://127.0.0.1:7001/user/1234helper
app/extend文件夾里面存放工具類
//app/extend/getName.js "use strict" module.exports = { getUserName(id) { return list.find(i=>i.id===id).name; } } //app/extend/helper.js "use strict" const getName = require("./getName"); module.exports = { showName() { return getName.getUserName("2221"); } } //controller引用helper "use strict" const Controller = require("egg").Controller; class CustomController extends Controller { async customIndex() { ////this.ctx.helper拿到helper內置對象也就是進入helper.js這個文件 this.ctx.body = this.ctx.helper.showName(); } } module.exports = CustomController;頁面渲染
egg.js使用的是nunjucks頁面模板
//在config/plugin.js里面添加 "use strict" exports.nunjucks = { enable: true, package: "egg-view-nunjucks" } //config/config/default.js 添加 "use strict" ... module.exports = app => { ... config.view = { mapping: { ".html": "nunjucks" }, root: path.join(appInfo.baseDir, "app/view") } ... return config; } //app/routes/sign.js "use strict"; module.exports = (router, controller) => { router.get("/sign/modifyPassword", controller.sign.modifyPassword); }; //app/controller/sign.js "use strict"; const Controller = require("egg").Controller; class SignController extends Controller { async modifyPassword() { const { ctx } = this; //渲染view/sign/modifyPassword.html await ctx.render("sign/modifyPassword.html"); } } module.exports = SignController;
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/97733.html
摘要:因為平常開發都是前后端分離的模式,就想著使用創建后臺服務,寫一套接口配合其他的項目。復雜數據的處理,比如要展現的信息需要從數據庫獲取或者是第三方服務的調用。更新用戶信息用戶信息已更改一個簡單的應用結構就是這樣,如此便實現了用負責接口服務。 寫在前面的話 最近在學習Egg.js,它是阿里推出的基于Koa的node開發框架,為企業級框架和應用而生。Egg.js 的官方文檔已經很完善了,想學...
摘要:因為平常開發都是前后端分離的模式,就想著使用創建后臺服務,寫一套接口配合其他的項目。復雜數據的處理,比如要展現的信息需要從數據庫獲取或者是第三方服務的調用。更新用戶信息用戶信息已更改一個簡單的應用結構就是這樣,如此便實現了用負責接口服務。 寫在前面的話 最近在學習Egg.js,它是阿里推出的基于Koa的node開發框架,為企業級框架和應用而生。Egg.js 的官方文檔已經很完善了,想學...
摘要:前言之前對的整體設計有過自己的理解,在中方便的插件機制也是這個框架的一大亮點,本文主要就是從的插件開始,對后臺中的插件機制做一些分析和總結。插件的特點它包含了中間件配置框架擴展等等。插件其余部分的運行原理也是類似的。 前言 之前對egg.js的整體設計有過自己的理解,在egg.js中方便的插件機制也是這個框架的一大亮點,本文主要就是從egg.js的插件開始,對node后臺中的插件機制做...
摘要:我為了方便直接就指定了淘寶倉庫地址運行服務運行項目就比較簡單了,運行的命令在瀏覽器中打開地址,就能看到服務已經啟動完成。 傳送門:學習node.js服務開發這一篇就夠了系列文章 1.創建工程目錄 1.1 創建一個文件夾叫 my-egg-application $ mkdir my-egg-application 不熟悉命令行的同學也可以手動創建文件夾 2.初始化項目模板 2.1 進...
閱讀 738·2021-10-09 09:44
閱讀 2005·2021-09-22 15:54
閱讀 5043·2021-09-22 10:55
閱讀 1435·2019-08-29 18:41
閱讀 771·2019-08-29 11:24
閱讀 2099·2019-08-28 18:20
閱讀 1025·2019-08-26 11:51
閱讀 3044·2019-08-26 11:00