mm_os
Version:
MM_OS服务端架构,用于快速构建应用程序,支持网站建设、小程序后台、AI应用、物联网(IOT/AIOT)、游戏服务端等多种场景。
201 lines (188 loc) • 4.7 kB
JavaScript
/**
* Oauth身份验证驱动类
* @class
*/
class Oauth {
static config = {
// 是否登录
'sign_in': false,
// 要求会员级别
'vip': 0,
// 要求管理级别
'gm': 0,
// 要求商户级别
'mc': 0,
// 要求用户组
'user_group': [],
// 要求管理组
'user_admin': [],
// 文件路径, 当调用函数不存在时,会先从文件中加载
'main': ''
};
/**
* 构造函数
* @param {string} config 当前路径
* @class
*/
constructor(config) {
// 配置参数
this.config = { ...Oauth.config, ...config };
}
}
/**
* 加载配置对象
* @param {object} obj 配置对象
*/
Oauth.prototype.loadObj = function (obj) {
$.push(this.config, obj);
var f = this.config.main;
if (f) {
var file = f.fullname(this.getDir());
if (file.hasFile()) {
var cs = require(file);
if (cs) {
$.push(this, cs);
}
}
}
};
/**
* 身份验证主程序
* @param {object} ctx HTTP请求上下文
* @returns {object} 验证失败返回错误提示,验证通过返回null
*/
Oauth.prototype.main = async function (ctx) {
return null;
};
/**
* 小校验
* @param {object} ctx HTTP请求上下文
*/
Oauth.prototype.checkSub = async function (ctx) {
};
/**
* 验证身份
* @param {object} ctx HTTP请求上下文
* @returns {object} 验证失败返回错误提示,验证通过返回null
*/
Oauth.prototype.check = async function (ctx) {
// 无需登录则不验证身份和权限
var cg = this.config;
var user = await this._getUser(ctx);
if (!cg.sign_in) {
return null;
}
var error = await this.main(ctx);
if (error) {
return error;
}
if (!user) {
return {
code: 60000,
message: '账户未登录!'
};
}
if (await this._checkAccess(user, cg)) {
return {
code: 70000,
message: '没有访问权限'
};
}
return null;
};
/**
* 获取用户信息
* @param {object} ctx HTTP请求上下文
* @returns {object|null} 用户信息
* @private
*/
Oauth.prototype._getUser = async function (ctx) {
var user = ctx.session?.user;
if (user) {
return user;
}
var token = ctx.headers[$.dict.token];
if (!token) {
return null;
}
var u = await $.cache.get($.dict.session_id + '_' + token);
if (!u) {
return null;
}
var user_info = this._extractUserFromCache(u);
if (user_info) {
ctx.session.user = user_info;
}
return user_info;
};
/**
* 从缓存中提取用户信息
* @param {object|string} u 缓存数据
* @returns {object|null} 用户信息
* @private
*/
Oauth.prototype._extractUserFromCache = function (u) {
var type = typeof (u);
if (type === 'string') {
var o = u.toJson();
return o.user;
} else if (type === 'object' && Object.keys(u).length > 0) {
return u.user;
}
return null;
};
/**
* 检查用户访问权限
* @param {object} user 用户信息
* @param {object} config 配置信息
* @returns {boolean} 是否无权限
* @private
*/
Oauth.prototype._checkAccess = function (user, config) {
return this._checkAccessLevels(user, config) ||
this._checkUserGroups(user, config) ||
this._checkAdminGroups(user, config);
};
/**
* 检查用户级别权限
* @param {object} user 用户信息
* @param {object} config 配置信息
* @returns {boolean} 是否无权限
* @private
*/
Oauth.prototype._checkAccessLevels = function (user, config) {
return (config.gm !== 0 && user.gm < config.gm) ||
(config.vip !== 0 && user.vip < config.vip) ||
(config.mc !== 0 && user.mc < config.mc);
};
/**
* 检查用户组权限
* @param {object} user 用户信息
* @param {object} config 配置信息
* @returns {boolean} 是否无权限
* @private
*/
Oauth.prototype._checkUserGroups = function (user, config) {
if (config.user_group.length === 0) {
return false;
}
var user_groups = user.user_group.split(',');
var has_group = config.user_group.some(group => user_groups.includes(group));
return !has_group;
};
/**
* 检查管理组权限
* @param {object} user 用户信息
* @param {object} config 配置信息
* @returns {boolean} 是否无权限
* @private
*/
Oauth.prototype._checkAdminGroups = function (user, config) {
if (config.user_admin.length === 0) {
return false;
}
var admin_groups = user.user_admin.split(',');
var has_admin = config.user_admin.some(group => admin_groups.includes(group));
return !has_admin;
};
module.exports = Oauth;