From 4673b541a6275f563919046a6a0b2b8a6ac61c2c Mon Sep 17 00:00:00 2001 From: yutent Date: Fri, 3 Jan 2025 15:34:42 +0800 Subject: [PATCH] =?UTF-8?q?=E8=B0=83=E6=95=B4session=E7=9A=84=E8=B0=83?= =?UTF-8?q?=E7=94=A8=E6=96=B9=E5=BC=8F;=E5=A2=9E=E5=8A=A0index.d.ts?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- index.d.ts | 38 ++++++++++++++ index.js | 125 +++++++++++++++++++++++---------------------- lib/redis-store.js | 3 +- package.json | 5 +- 4 files changed, 106 insertions(+), 65 deletions(-) create mode 100644 index.d.ts diff --git a/index.d.ts b/index.d.ts new file mode 100644 index 0000000..23f4ce4 --- /dev/null +++ b/index.d.ts @@ -0,0 +1,38 @@ +/** + * {} + * @author yutent + * @date 2025/01/03 10:39:13 + */ + +declare interface RedisConfig { + host: string + port: number + db: number +} + +declare interface SessionConfig { + ttl?: number + domain?: string + level?: 0 | 2 | 4 | 6 + secret: string + db: RedisConfig +} + +declare class Store { + update(ssid: string): void + + get(ssid: string, key?: string): Promise + + set(ssid: string, key: string, val: string): void + + unset(ssid: string, key: string): void + + clear(ssid: string): void +} + +declare interface Session { + name: 'session' + install(conf?: SessionConfig): Store +} + +export function createSession(): Session diff --git a/index.js b/index.js index a28406f..cf19a97 100644 --- a/index.js +++ b/index.js @@ -6,11 +6,11 @@ import { uuid, sha1 } from 'crypto.js' -import RedisStore from './lib/redis-store.js' +import Store from './lib/redis-store.js' const DEFAULT_CONFIG = { ttl: 3600 * 24 * 7, - domain: '', // NODESSID域, 默认等于domain + domain: '', // NODESSID域 level: 0, // 校验级别, 0: 不校验客户端, 2: ua, 4: ip, 6: ua + ip secret: 'it_is_secret_key', // jwt密钥, 使用时请修改 db: { @@ -20,71 +20,74 @@ const DEFAULT_CONFIG = { } } -// 会话安装包 -export const SessionModule = { - name: 'session', - install(conf = {}) { - if (!conf.secret) { - console.warn( - new Error( - 'You must set a `secret` key for session, or it will use the default key.' - ) - ) - } - let session = Object.assign({}, DEFAULT_CONFIG, conf) - this.set({ session }) - // 这里只创建session的存储器, 而初始化操作在中间件中进行 - return new RedisStore(session) +function sessionMiddleware(req, res, next) { + let opt = this.get('session') + let cache = req.cookie('NODESSID') + let deviceID = '' + let ssid + + // options请求不处理会话 + if (req.method === 'OPTIONS') { + return next() } + + // 校验UA + if (opt.level & 2) { + deviceID += req.header('user-agent') + } + + // 校验IP + if (opt.level & 4) { + deviceID += req.ip() + } + + if (deviceID) { + deviceID = sha1(deviceID) + + // ssid 最后16位是指纹 + if (cache) { + if (cache.slice(-16) === deviceID.slice(-16)) { + ssid = cache + } else { + ssid = uuid('') + deviceID.slice(-16) + } + } + } else { + ssid = cache || sha1(uuid()) + } + + res.cookie('NODESSID', ssid, { + maxAge: opt.ttl, + httpOnly: true, + domain: opt.domain + }) + // 缓存ssid到req上 + req.ssid = ssid + this.$$session.update(ssid) + + next() } // 会话中间件 export function createSession() { - return function (req, res, next) { - let opt = this.get('session') - let cache = req.cookie('NODESSID') - let deviceID = '' - let ssid - - // options请求不处理会话 - if (req.method === 'OPTIONS') { - return next() - } - - // 校验UA - if (opt.level & 2) { - deviceID += req.header('user-agent') - } - - // 校验IP - if (opt.level & 4) { - deviceID += req.ip() - } - - if (deviceID) { - deviceID = sha1(deviceID) - - // ssid 最后16位是指纹 - if (cache) { - if (cache.slice(-16) === deviceID.slice(-16)) { - ssid = cache - } else { - ssid = uuid('') + deviceID.slice(-16) - } + return { + name: 'session', + install(conf = {}) { + if (!conf.secret) { + console.warn( + new Error( + 'You must set a `secret` key for session, or it will use the default key.' + ) + ) } - } else { - ssid = cache || sha1(uuid()) + let session = Object.assign({}, DEFAULT_CONFIG, conf) + this.set({ session }) + + // 注册中间件 + this.use(sessionMiddleware) + + // 这里只创建session的存储器, 而初始化操作在中间件中进行 + return new Store(session) } - - res.cookie('NODESSID', ssid, { - maxAge: opt.ttl, - httpOnly: true, - domain: opt.domain - }) - // 缓存ssid到req上 - req.ssid = ssid - this.$$session.update(ssid) - - next() } } diff --git a/lib/redis-store.js b/lib/redis-store.js index 6437287..fdac9d5 100644 --- a/lib/redis-store.js +++ b/lib/redis-store.js @@ -6,8 +6,7 @@ import 'es.shim' import Ioredis from 'ioredis' -export default class Session { - +export default class Store { #store = null #ttl = 60 diff --git a/package.json b/package.json index 3f16a87..1808122 100644 --- a/package.json +++ b/package.json @@ -1,10 +1,11 @@ { "name": "@gm5/session", - "version": "2.0.0", + "version": "3.0.0", "type": "module", "description": "会话中间件。", - "main": "index.js", "author": "yutent ", + "main": "index.js", + "types": "index.d.ts", "keywords": [ "fivejs", "gm5",