日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Node工程-构建优秀的Session机制

發布時間:2024/9/21 编程问答 32 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Node工程-构建优秀的Session机制 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

我們公司的大佬 串串,搭建了一套基于koa2的node框架,雖然說是重復造輪子,但適用當前場景的輪子才是最好的,何況很多人還造不出輪子呢~ 大佬搭建的框架命名為 Sponse,其中有很多出色的設計,這里對 session 的設計做個總結(其實是為了自己加深印象,學習大佬的設計)

Sponse意思是海綿,而我們這套框架就如同海綿一樣,通過不斷吸收其他框架的優秀設計豐滿自己

cookie 與 session

做開發的小伙伴對這兩個應該在熟悉不過了,這兩個一起構建起前后端狀態的聯系,常見的如維護用戶登錄狀態,用戶登錄后,需要在服務端記錄下該用戶的登錄狀態,前端才可以使用需要登錄態的接口,此時,瀏覽器中的 cookie 就是查詢用戶是否登錄的憑證,在服務端,通常是將用戶狀態信息存儲在緩存中,簡單說,就是基于 cookie的session

調用方式

優秀的架構中,調用方式必須是友好的

期望能夠通過上下文直接調用,如:獲取session對象 ctx.session ; 設置session的值 ctx.session.name = name

邏輯圖

整體實現邏輯如下

實現

  • koa提供了操作cookie的api,開箱即用,官方截圖如下
  • 緩存基于redis實現
  • 詳細代碼如下:

    Session 對象

    首先構建一個session對象

    核心方法:

  • save 用于同步cookie
  • changed 用于檢測session對象是否發生修改,為了同步更新緩存中的值
  • export class Session {private _ctx;isNew: boolean;_json; // session對象的json串,用于比較session對象是否發生變化constructor(ctx, obj) {this._ctx = ctx;if (!obj) this.isNew = true;else {for (const k in obj) {this[k] = obj[k];}}}/*** Save session changes by* performing a Set-Cookie.** @api private*/save() {const ctx = this._ctx;const json = this._json || JSON.stringify(this.inspect());const sid = ctx.sessionId;const opts = ctx.cookieOption;const key = ctx.sessionKey;if (ctx.cookies.get(key) !== sid) {// 設置cookies的值ctx.cookies.set(key, sid, opts);}return json;};/*** JSON representation of the session.** @return {Object}* @api public*/inspect() {const self = this;const obj = {};Object.keys(this).forEach(function (key) {if ('isNew' === key) return;if ('_' === key[0]) return;obj[key] = self[key];});return obj;}/*** Check if the session has changed relative to the `prev`* JSON value from the request.** @param {String} [prev]* @return {Boolean}* @api private*/changed(prev) {if (!prev) return true;this._json = JSON.stringify(this.inspect());return this._json !== prev;};} 復制代碼

    SessionEngine koa中間件

    koa 當然是離不開中間件了,洋蔥模型酷炫到不行,非常方便的解決了session對象與緩存的同步

    decorator(app) {app.keys = ['signed-key'];const CONFIG = {key: app.config.name + '.sess', /** (string) cookie key (default is koa:sess) */cookie: {// maxAge: 1000, /** (number) maxAge in ms (default is 1 days) */overwrite: false, /** (boolean) can overwrite or not (default true) */httpOnly: true, /** (boolean) httpOnly or not (default true) */signed: true, /** (boolean) signed or not (default true) */}};app.use(async (ctx, next) => {let sess: Session;let sid;let json;ctx.cookieOption = CONFIG.cookie;ctx.sessionKey = CONFIG.key;ctx.sessionId = null;// 獲取cookie 對應的值, 即sessionID,就是緩存中的keysid = ctx.cookies.get(CONFIG.key, ctx.cookieOption);// 獲取session值if (sid) {try {// 若key存在,則從緩存中獲取對應的值json = await app.redisClient.get(sid);} catch (e) {console.log('從緩存中讀取session失敗: %s\n', e);json = null;}}// 實例化sessionif (json) {// 若緩存中有值,則基于緩存中的值構建session對象ctx.sessionId = sid;try {sess = new Session(ctx, json);} catch (err) {if (!(err instanceof SyntaxError)) throw err;sess = new Session(ctx, null);}} else {sid = ctx.sessionId = sid || Uuid.gen();sess = new Session(ctx, null);}// 為了便于使用,將session掛載到上下文,這樣就可以 ctx.session 這么使用了Object.defineProperty(ctx, 'session', {get: function () {return sess;},set: function (val) {if (null === val) return sess = null;if ('object' === typeof val) return sess = new Session(this, val);throw new Error('this.session can only be set as null or an object.');}});try {await next();} catch (err) {throw err;} finally {if (null === sess) {// 設置session=null表示清空sessionctx.cookies.set(CONFIG.key, '', ctx.cookieOption);} else if (sess.changed(json)) {// 檢查 session 是否發生變化,若有變化,更新緩存中的值json = sess.save();await app.redisClient.set(sid, json);app.redisClient.ttl(sid);// 設置redis值過期時間為60分鐘app.redisClient.expire(sid, 7200);} else {// session 續期app.redisClient.expire(sid, 7200);}}}); 復制代碼

    小結

    多多學習~ 點點進步~



    原文發布時間:2018年06月29日 作者:小黎也
    本文來源掘金如需轉載請緊急聯系作者

    總結

    以上是生活随笔為你收集整理的Node工程-构建优秀的Session机制的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。