index.js 9.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292
  1. const jwt = require('jsonwebtoken')
  2. const pool = require('../pool.js')
  3. const { errLog } = require('../utils/err')
  4. //日志记录
  5. module.exports = {
  6. poolsEvent() {
  7. const pools = require('./pools')
  8. return pools
  9. },
  10. setToken({ uid, captcha, name = 'user' }) {
  11. let token = jwt.sign({ uid, captcha }, name, {
  12. expiresIn: '86400s' // 授权时间
  13. })
  14. return token
  15. },
  16. verToken({ token, name = 'user' }) {
  17. try {
  18. return jwt.verify(token, name)
  19. } catch (err) {
  20. return false
  21. }
  22. },
  23. /**
  24. * 判断名称是否重复
  25. * @param sql sql语句
  26. * @param name sql查询参数name
  27. * @param msg 提示语
  28. * @param req 请求主体
  29. * @param res 响应主体
  30. * */
  31. async existName({ sql, name, msg = '名称已存在!', req, res }) {
  32. if (!name) return true
  33. let { result } = await this.poolsEvent()({ sql, res, req, val: [name] })
  34. if (result.length > 0) {
  35. res.send(this.returnData({ code: -1, msg, req }))
  36. return Promise.reject(false)
  37. }
  38. return true
  39. },
  40. /**
  41. * 判断修改的名称是否和修改前的一样
  42. * @param sql sql语句
  43. * @param sqlName 修改前的属性名
  44. * @param name 修改后的值
  45. * @param id sql条件参数
  46. * @param req 请求主体
  47. * @param res 响应主体
  48. * */
  49. async judgeUserName({ sql, sqlName = 'name', name, id, req, res }) {
  50. let { result } = await this.poolsEvent()({ sql, val: [id], res, req })
  51. if (result[0][sqlName] == name) return -1
  52. return 1
  53. },
  54. /**
  55. * 响应总函数
  56. * @param code 状态码
  57. * @param msg 提示文字
  58. * @param total 查询总数量
  59. * @param data 数据
  60. * @param err 错误信息
  61. * @param req 错误信息
  62. * @param funName 错误信息记录名称
  63. * */
  64. returnData({ code = 1, msg, total = undefined, data = {}, err, req = {}, funName } = {}) {
  65. if (code == 1 && !msg) msg = '请求成功!'
  66. if (code == -1 && !msg) msg = '服务器异常!'
  67. if (code == 203 && !msg) msg = '登陆失效,请重新登陆!'
  68. let res = { code, msg, data }
  69. if (total !== undefined) res.total = total
  70. if (err) res.err = err
  71. //记录错误日志
  72. if (code != 1) errLog({ err, code, msg, req, funName })
  73. return res
  74. },
  75. /**
  76. * 获取用户信息
  77. * @param req 请求主体
  78. * @param res 响应主体
  79. * @param addMore 是否拒绝管理员添加多账户信息
  80. * */
  81. async getUserInfo({ req, res, addMore = false } = {}) {
  82. let token = req.headers.token
  83. if (!token) {
  84. res.send(this.returnData({ code: 203, req }))
  85. return Promise.reject(false)
  86. }
  87. let user = this.verToken({ token })
  88. if (!user) {
  89. res.send(this.returnData({ code: 203, req }))
  90. return Promise.reject(false)
  91. }
  92. let sql = 'SELECT id,name,status,roles_id AS rolesId,admin,more_id AS moreId,url FROM user WHERE id=?'
  93. let { result } = await this.poolsEvent()({ sql, val: [user.uid], res, req })
  94. if (result.length === 0) {
  95. res.send(this.returnData({ code: -1, msg: '用户不存在!', req }))
  96. return Promise.reject(false)
  97. }
  98. if (addMore && result[0].admin === 1) {
  99. res.send(this.returnData({ code: -1, msg: '终极管理员无权 增加多账号数据~', req }))
  100. return Promise.reject(false)
  101. }
  102. return result[0]
  103. },
  104. /**
  105. * 获取用户权限
  106. * @param req 请求主体
  107. * @param res 响应主体
  108. * */
  109. async getUserRole(req, res) {
  110. let user = await this.getUserInfo({ req, res })
  111. let userSql = 'SELECT roles,role_key FROM roles WHERE FIND_IN_SET(id,?)'
  112. let { result } = await this.poolsEvent()({ sql: userSql, val: [user.rolesId], res, req })
  113. if (result.length == 0) {
  114. res.send(this.returnData({ code: -1, msg: '获取权限失败!', req }))
  115. return Promise.reject(false)
  116. }
  117. let roles = result.map((t) => t.roles)
  118. //权限字符
  119. let roleKey = result.map((t) => t.role_key)
  120. //角色权限
  121. let roleAdmin = roleKey.some((t) => t === 'admin')
  122. return { userRole: roles.join(','), roleKey, user, roleAdmin }
  123. },
  124. /**
  125. * 菜单字符权限拦截
  126. * @param req 主体
  127. * @param res 主体
  128. * @param role 接口权限字符数组
  129. * @param admin 是否管理员也要遵守(默认否)
  130. * @param run 是否不拦截,返回结果
  131. * */
  132. async checkPermi({ req, res, role = [], admin = false, run = false }) {
  133. let userRole = await this.getUserRole(req, res)
  134. if ((userRole.roleAdmin || userRole.user.admin === 1) && !admin) return true
  135. let sql = 'SELECT role_key AS roleKey FROM router_menu WHERE FIND_IN_SET(id,?)'
  136. let { result } = await this.poolsEvent()({ sql, val: [userRole.userRole], res, req })
  137. try {
  138. let roleKeyArr = result.map((t) => t.roleKey).filter((t) => t)
  139. const hasPermission = role.some((permission) => {
  140. return roleKeyArr.includes(permission)
  141. })
  142. if (hasPermission || run) return hasPermission
  143. res.send(this.returnData({ code: -1, msg: '暂无此功能请求权限!', req }))
  144. return Promise.reject(false)
  145. } catch (e) {
  146. res.send(this.returnData({ code: -1, msg: '菜单权限判断错误!!', req }))
  147. return Promise.reject(false)
  148. }
  149. },
  150. /**
  151. * 角色权限拦截
  152. * @param req 主体
  153. * @param res 主体
  154. * @param role 角色权限数组
  155. * @param admin 是否管理员也要遵守(默认否)
  156. * @param run 是否不拦截,返回结果
  157. * */
  158. async checkRole({ req, res, role = [], admin = false, run = false }) {
  159. try {
  160. let userRole = await this.getUserRole(req, res)
  161. if ((userRole.roleAdmin || userRole.user.admin === 1) && !admin) return true
  162. let roleKeyArr = userRole.roleKey
  163. const hasPermission = role.some((permission) => {
  164. return roleKeyArr.includes(permission)
  165. })
  166. if (hasPermission || run) return hasPermission
  167. res.send(this.returnData({ code: -1, msg: '暂无对应角色请求权限!', req }))
  168. return Promise.reject(false)
  169. } catch (e) {
  170. res.send(this.returnData({ code: -1, msg: '角色权限判断错误!', err: e, req }))
  171. return Promise.reject(false)
  172. }
  173. },
  174. /**
  175. * 是否操作的是用户总管理员
  176. * @param req 请求主体
  177. * @param res 响应主体
  178. * @param id 查询条件id
  179. * */
  180. async upAdmin({ req, res, id }) {
  181. let sql = 'SELECT admin FROM user WHERE id=?'
  182. let { result } = await this.poolsEvent()({ sql, val: [id], res, req })
  183. if (result.length === 0) {
  184. res.send(this.returnData({ code: -1, msg: '管理信息判断错误!', req }))
  185. return Promise.reject(false)
  186. }
  187. if (result[0].admin === 1) {
  188. res.send(this.returnData({ code: -1, msg: '无法对《总管理》执行此操作!', req }))
  189. return Promise.reject(false)
  190. }
  191. return result
  192. },
  193. /**
  194. * 是否操作的是角色总管理员
  195. * @param req 请求主体
  196. * @param res 响应主体
  197. * @param id 查询条件id
  198. * */
  199. async upAdminRole({ req, res, id }) {
  200. let sql = 'SELECT role_key FROM roles WHERE id=?'
  201. let { result } = await this.poolsEvent()({ sql, val: [id], res, req })
  202. if (result.length === 0) {
  203. res.send(this.returnData({ code: -1, msg: '管理信息判断错误!!', req }))
  204. return Promise.reject(false)
  205. }
  206. if (result[0].role_key === 'admin') {
  207. res.send(this.returnData({ code: -1, msg: '无法对《角色总管理》执行此操作!', req }))
  208. return Promise.reject(false)
  209. }
  210. return result
  211. },
  212. /**
  213. * 通过id获取用户信息
  214. * @param req 请求主体
  215. * @param res 响应主体
  216. * @param id 查询条件id
  217. * */
  218. async getUserId({ req, res, id }) {
  219. let sql = 'SELECT admin FROM user WHERE id=?'
  220. let { result } = await this.poolsEvent()({ sql, val: [id], res, req })
  221. if (result.length === 0) {
  222. res.send(this.returnData({ code: -1, msg: '用户信息错误!!', req }))
  223. return Promise.reject(false)
  224. }
  225. return result[0]
  226. },
  227. /**
  228. * 分页页码处理
  229. * @param sql sql语句
  230. * @param page 页码
  231. * @param size 最大数量
  232. * */
  233. pageSize(sql, page, size) {
  234. if (!page) {
  235. page = 1
  236. }
  237. if (!size) {
  238. size = 10
  239. }
  240. page = (page - 1) * size
  241. size = parseInt(size)
  242. return (sql += ` LIMIT ${page},${size}`)
  243. },
  244. /**
  245. * 查询总数
  246. * @param sql sql语句
  247. * @param name 表名
  248. * @param res 响应主体
  249. * @param req 请求主体
  250. * */
  251. async getSum({ sql = '', name, res, req }) {
  252. const regex = /WHERE(.+)/
  253. const result = sql.match(regex)
  254. let where = '1=1'
  255. if (result && result[1]) where = result[1].trim()
  256. let sqlRes = `SELECT count(1) FROM ${name} WHERE ${where}`
  257. let { result: resultRes } = await this.poolsEvent()({ sql: sqlRes, res, req })
  258. return { total: resultRes[0]['count(1)'] }
  259. },
  260. /**
  261. * 将多账户id加入sql判断
  262. * @param sql sql语句
  263. * @param user 用户信息
  264. * @param name 字段名
  265. * */
  266. setMoreId(sql, user, name = 'more_id') {
  267. if (user.admin !== 1) return (sql += ` AND ${name} = ${user.moreId}`)
  268. return sql
  269. },
  270. /**
  271. * 模糊查询
  272. * @param sql sql语句
  273. * @param name 字段名
  274. * @param val 值
  275. * */
  276. setLike(sql, name = '', val = '') {
  277. if (this.exist(val)) sql += ` AND ${name} LIKE "%${val}%"`
  278. return sql
  279. },
  280. setOr(sql, name = '', val = '') {
  281. if (this.exist(val)) sql += ` or entity_id in (SELECT parent_id FROM entity where name LIKE '%${val}%')`
  282. return sql
  283. },
  284. /**
  285. * 判断是否为空
  286. * @param str any
  287. * */
  288. exist(str) {
  289. return str !== undefined && str !== '' && str !== null
  290. }
  291. }