vue,vuex的后台管理项目架子structure-admin,后端服务nodejs
之前写过一篇vue初始化项目,构建vuex的后台管理项目架子,这个structure-admin-web所拥有的功能
接下来,针对structure-admin-web的不足,进行了补充,开发了具有登陆的structure-admin项目,技术站:主要是node+vue+redis+mysql+es6
欢迎访问structure-admin源码:structure-admin
欢迎访问weekly源码:weekly
项目地址演示地址:http://weekly.mwcxs.top
- (公司负责人)账号:testadmin,密码:123456
- (部门经理)账号:test,密码:123456
- (成员)账号:teststaff,密码:123456
PS:添加的成员的默认密码是123456
接下来:
一、后端服务nodejs,thinjs的redis配置,操作数据库
二、前端vue+vuex全局路由守卫,axios请求拦截
三、项目启动必读
一、后端服务nodejs,thinjs的redis配置,操作数据库
我使用的是thinkjs,一个nodejs的框架。
1、首先介绍登陆的控制
逻辑:
(1)已经登陆的,直接根据的路由跳到相应页面;
(2)已经登陆的,不能跳到登陆页面,跳到首页;
(3)没有登陆的,输入url必须跳到登陆页;
(4)退出系统的,必须回到登陆页,状态是未登录
1.1 thinkjs的redis的配置文件adapter.js
exports.session = { type: 'redis', common: { cookie: { name: 'thinkjs', keys: ['werwer', 'werwer'], signed: true } }, redis: { handle: redisSession, host: '127.0.0.1', port: 6379, password: 'a123456' } };
设置的由redis的服务地址host,端口,以及redis的密码,redis的搭建和配置,参考安装window下的redis,redis可视化管理工具(Redis Desktop Manager)安装,基础使用,实例化项目这篇文章。
1.2 在每一次前端请求的路由的时候,都会去redis服务器中去取userInfo的信息
如果为空,返回前端data为空,前端在路由过滤中,跳到登陆页,如果有值就正常返回。
async __before() { let user = await this.session("userInfo"); if(user) { this.user = user; } else { this.user = ''; } }
这个在nodejs的控制器controller里,在每一次前端的请求发送到后端的时候,都会去redis的取userInfo的值,
let user = await this.session("userInfo");
这个userInfo的值也是自己在登陆的时候,把登陆成功之后的个人信息加入到redis服务中
1.3 在登陆成功的时候讲个人信息加到redis服务中
async loginAction() { let {username, password} = this.post();try { let user = await this.model('user').where({ username, }).find(); if(user.password && user.password == password) { // login success await this.session('userInfo',{username, userId:user.id}); return this.success("登陆成功"); } else { return this.fail("用户名或密码错误") } } catch(e) { console.log(e); return this.fail("登录失败") }
这个就是将个人信息加入到redis中
await this.session('userInfo',{username, userId:user.id});
WEB 请求中经常通过 session 来维持会话的,框架通过 think-session 和 Adapter 来支持 session 功能。
2、介绍登出(退出)的控制
async logoutAction() { try { await this.session(null); return this.success("登出成功"); } catch(e) { return this.fail(`登出失败${e}`) } }
这个就是前端发的请求登出,直接将redis的置空,根据前端路由跳转到登陆页,这时候redis的服务中没有值,就不会跳转到其他页面
3、数据库的配置adapter.js
exports.model = { type: 'mysql', common: { logConnect: true, logSql: true, logger: msg => think.logger.info(msg) }, mysql: { handle: mysql, database: 'example', prefix: 'example_', encoding: 'utf8', host: '127.0.0.1', port: '3306', user: 'root', password: '123456', dateStrings: true } };
common部分是配置是否将sql的语句的操作日志打出来,这样便于我们在开发的时候的调试和修改bug
4、操作数据库
项目开发中,经常需要操作数据库(如:增删改查等功能),手工拼写 SQL 语句非常麻烦,同时还要注意 SQL 注入等安全问题。为此框架提供了模型功能,方便操作数据库。
Mysql 的 Adapter 为 think-model-mysql,底层基于 mysql 库实现,使用连接池的方式连接数据库,默认连接数为 1。
拿登陆的接口来说明:this.model说明使用封装好的model,find是查找单条数据,在user的这张表中查找username值为前端传来的username的值,返回的值赋给user中。
async loginAction() { let {username, password} = this.post(); try { let user = await this.model('user').where({ username, }).find(); if(user.password && user.password == password) { // login success await this.session('userInfo',{username, userId:user.id}); return this.success("登陆成功"); } else { return this.fail("用户名或密码错误") } } catch(e) { console.log(e); return this.fail("登录失败") }
think.Model 基类提供了丰富的方法进行 CRUD 操作,下面来一一介绍。
查询数据
模型提供了多种方法来查询数据,如:
- find 查询单条数据
- select 查询多条数据
- count 查询总条数
- countSelect 分页查询数据
- max 查询字段的最大值
- avg 查询字段的平均值
- min 查询字段的最小值
- sum 对字段值进行求和
- getField 查询指定字段的值
同时模型支持通过下面的方法指定 SQL 语句中的特定条件,如:
- where 指定 SQL 语句中的 where 条件
- limit / page 指定 SQL 语句中的 limit
- field / fieldReverse 指定 SQL 语句中的 field
- order 指定 SQL 语句中的 order
- group 指定 SQL 语句中的 group
- join 指定 SQL 语句中的 join
- union 指定 SQL 语句中的 union
- having 指定 SQL 语句中的 having
- cache 设置查询缓存
添加数据
模型提供了下列的方法来添加数据:
更新数据
模型提供了下列的方法来更新数据:
- update 更新单条数据
- updateMany 更新多条数据
- thenUpdate 条件式更新
- increment 字段增加值
- decrement 字段减少值
删除数据
模型提供了下列的方法来删除数据:
- delete 删除数据
用项目的代码举栗子:
(1)查询单条数据,用find(),条件为:工号(usernum)为180909,用户名(username)为saucxs ,并且填写时间(time)为这周的时间范围的时间戳,返回的是对象object
let weekly = await this.model('week').where({ usernum: '180909',
username: 'saucxs',
time: {'>': startWeekStamp, '<': endWeekStamp} }).find();
解读:model('week')的意思,取得是week的数据表
(2)查询多条数据,用select(),条件:公司id(company_id)为data的数据,返回的是数组array
let department = await this.model('department').where({company_id: 'data'}).select();
(3)查询表中的具体的列数据,用field()
departmentMemberList = await this.model('user').field('id, company_id, company_name, department_id, department_name, email, role, role_name, username, usernum,telephone').where({ company_id: this.user.company_id, role: {'>=': this.user.role} }).find();
解读:this.user.company_id取的是登陆用户的公司id,{'>=': this.user.role}为比登陆用户的角色
(4)分页查询,用page(page, pagesize)和countSelect(),返回的数据是对象
departmentMemberList = await this.model('user').field('id, company_id, company_name, department_id, department_name, email, role, role_name, username, usernum,telephone').where({ company_id: this.user.company_id, role: {'>=': this.user.role} }).order("department_id asc , role asc").page(page, pagesize).countSelect();
解读:返回的对象,如下图所示:(count是总条数,currentPage为当前页,data是数据的数组,pageSize为每一页展示几条,totalPages为总共有多少页)
(5)排序,倒序(desc)和正序(asc),用order("参数1 asc,参数2 desc”)
departmentMemberList = await this.model('user').field('id, company_id, company_name, department_id, department_name, email, role, role_name, username, usernum,telephone').where({ company_id: this.user.company_id, role: {'>=': this.user.role} }).order("department_id asc , role asc").page(page, pagesize).countSelect();
(6)删除,用delete(),条件用where
await this.model('department').where({company_id, department_id}).delete();
(7)新增,用add(),没有where
await this.model('department').add({ company_id: this.user.company_id, company_name: this.user.company_name, department_id, department_name });
(8)改,用update(),条件where
await this.model('user').where({id}).update({ usernum, username, telephone, role, role_name,email, company_id, company_name, department_id, department_name });
手动执行 SQL 语句
有时候模型包装的方法不能满足所有的情况,这时候需要手工指定 SQL 语句,可以通过下面的方法进行:
具体的可以参考thinkJS的官方文档的数据操作这块:https://thinkjs.org/zh-cn/doc/3.0/relation_model.html
二、前端vue+vuex全局路由守卫,axios请求拦截
刚才简单的说了一下nodejs的后端启动的服务,封装的接口,而前端调用这个接口使用的是url是:模块名/控制器名/方法名,这个可以在配置文件中修改定义的方法
1、全局路由守卫
全局路由守卫是每一次都会判断是否登陆(也就是判断redis服务中是否有值)。已经登陆(后端返回的用户权限信息),则判断当前要跳转的路由,用户是否有权限访问,可以考虑在用户登陆之后将用户权限把路由过滤一遍生成菜单,菜单保存到vuex中。
/*路由处理*/ router.beforeEach((to, from, next) => { let menuId; let auditResult; let applicationVerifyFlag; let key = to.meta.key; if (key) { store.dispatch("getUserInfo", {}).then(response => {if(!response.data){ if (to.path !== '/login') { return next('/login'); } next(); }else{ if (to.path == '/login') { return next('/writeWeekly'); } store.commit("USER_INFO", response.data); next(); } }); } else { next(); } });
根据这个key来判断是否有权限,取得是路由中meta的key的值。
routes: [ { path: '/login', name: 'login', meta: { key: '0' }, component: login }, { path: '/', name: 'home', component: home, children: [{ path: '/writeWeekly', name: 'writeWeekly', meta: { key: '1' }, component: writeWeekly }] } ]
2、axios请求拦截
统一处理所有的http请求和响应的,通过配置http request interceptors为http头部增加Authorization字段,其内容为Token,通过配置http response interceptors,当后端接口返回401 Unauthorized(未授权),让用户重新登录。
// 开发环境调试用户信息 axios.interceptors.request.use(config => { if (process.env.NODE_ENV === 'development') { config.headers["username"] = "189090909"; } return config; }); axios.interceptors.response.use( response => { let data = response.data; console.log(data, 'data'); if (!data.data) { // 登陆成功的回调地址 return data; } else { return data; } }, error => ({ code: -1, msg: "网络异常" }) );
对所有的请求进行了封装。
// get请求配置 let getConfig = { url: '', baseURL: serveUrl, headers: { 'X-Requested-With': 'XMLHttpRequest' }, paramsSerializer(params) { return Qs.stringify(params, { arrayFormat: 'brackets' }) }, timeout: 5000 } // post请求配置 let postConfig = { url: '', baseURL: serveUrl, headers: { 'Content-Type': 'application/json', 'X-Requested-With': 'XMLHttpRequest' }, transformRequest: [function (data) { return JSON.stringify(data.params || {}) }], timeout: 5000 } export { serveUrl, getConfig, postConfig, }
三、项目启动必读
1、首先你的环境是nodejs,不会安装配置参考:http://www.mwcxs.top/page/420.html
2、clone下来项目
git clone https://github.com/saucxs/structure-admin.git
3、分别针对前端vue的structure-admin-web的文件夹和node后端structure-admin-node,安装相应依赖
npm install
4、安装redis(可以考虑安装RedisDesktopManager)
参考:安装window下的redis,redis可视化管理工具(Redis Desktop Manager)安装,基础使用,实例化项目
5、安装mysql,这个就不赘述
6、修改nodejs的后端的配置文件adapter.js,config.js这两个文件中
adapter.js
exports.cache = { type: 'redis', common: { timeout: 24 * 60 * 60 * 1000 // millisecond }, redis: { handle: redisCache, host: '127.0.0.1', port: 6379, password: 'a123456' //redis安装时候设置的秘密 } };
//
//
exports.model = {
type: 'mysql',
common: {
logConnect: true,
logSql: true,
logger: msg => think.logger.info(msg)
},
mysql: {
handle: mysql,
database: 'weekly',
prefix: 'week_',
encoding: 'utf8',
host: '127.0.0.1', //本地数据库
port: '3306', //数据库端口
user: 'root', //数据库的用户名
password: '123456', //数据库该用户名的密码
dateStrings: true
}
};
7、分别对前后端分离的项目启动
(1)前端vue的structure-admin-web的启动
npm run dev
(2)和node后端structure-admin-node的启动
npm start
8、这样就可以启动
(1)登陆页
(2)写周报页面
9、该项目架子搭的周报企业管理系统
在PC端,欢迎访问:http://weekly.mwcxs.top,
- (公司负责人)账号:testadmin,密码:123456
- (部门经理)账号:test,密码:123456
- (成员)账号:teststaff,密码:123456
如若转载,请注明出处:sau交流学习社区-power by saucxs(程新松)(/page/427.html)
- 记录一次nginx故障:recv() failed (104: Connection reset by peer) while reading response header from upstream,
- 微信小程序初体验,入门练手项目--通讯录,部署上线(二)
- 微信小程序初体验,入门练手项目--通讯录,后台是阿里云服务器(一)
- thinkjs性能优化之nginx配置
- 开学AI登场!南京高校用人脸识别查考勤管理学生,还敢逃课、玩手机?姚AI变脸热到爆!开源换脸工具FakeSwap今登GitHub排行榜第二位,ICLR飞升,IJCAI降级:清华的新版AI顶会评级引发学术圈热议,意外!已获6700万美元投资的自动驾驶LiDAR创业公司关门了
标签云
图文推荐
“深度学习”这十年:52篇大神级论文再现AI荣与光,12岁上大学、31岁成最年轻IEEE Fellow,前百度总裁张亚勤加盟清华,全球女性福音!DeepHealth深度学习模型检测乳腺癌完胜5名放射科医师,读博无门,就业碰壁,孤独当了7个月“民科”后,我的论文中了顶会Spotlight
saucxs 2020-01-03 10:04:09
1200 万部手机、500 亿实时位置数据,上帝视角还原特朗普全天行踪,自动驾驶玩漂移 斯坦福最新研究:《头文字D》无人车版来了,印度裔又要统领美国科学界?特朗普提名他领导美国国家科学基金会,GitHub排名第一!免费最强“抢票神器”在手,程序员抢票再不用跪求加速包
saucxs 2019-12-25 10:08:05
蝉联AI专业全球冠军!清华力压CMU再夺CSRankings高校AI排行王座,波士顿动力CEO:不排斥军方订单,就想你粗暴地对待机器狗,亚马逊Alexa突然发疯,读着论文教主人自杀:你活着地球人口会过剩,图神经网络的ImageNet?斯坦福大学等开源百万量级OGB基准测试数据集
saucxs 2019-12-24 09:57:45
2020 AAAI Fellow名单出炉!深度学习先驱Bengio和LeCun双双入选,李世石最后一战不敌AI“韩豆”!唯一战胜过AlphaGo的男人正式退役,GAN和PS合体会怎样?东京大学图像增强新研究:无需配对图像,增强效果还可解释,2019年最受关注的100项研究,AI“复活”蒙娜丽莎排第一
saucxs 2019-12-23 09:58:10
这家AI公司用面具破解中国人脸识别系统!微信、支付宝、火车站无一幸免,OpenAI公开Dota 2论文:胜率99.4%,「手术」工具连续迁移训练,9岁神童大学毕业前突然退学,转赴美国攻读电气工程博士,Reddit热议:15岁高中生用神经网络建立生命进化“新宇宙”
saucxs 2019-12-17 09:45:30
- 东方财富
- saucxs博客园
- weekly周报
- loveBook
- 前端博客
- 技术交流学习社区
- saucxs
- segmentfault
- saucxs的博客
- haorooms
- luckyscript
- 东方财富期货
- 峰云就她了
- binlive
- songEagle
- 且听风吟
- (TX)Heying Ye
- CG Online Judge
- Chris's Blog
- vueRouter
- 龙恩0707
- 鑫空间,鑫生活
- 木易杨
- MDN-js
- Cherry's Blog
- InterviewMap
- 安安哥的小戏台
- xiaojun1994-cat
- JavaScript-Garden
- junruchen-daily
- 秋天爱美丽
- web-summary-daily
- w3cplus-tb
- 潜行者m
- 于江水
- KieSun-git
- cnodejs
- aerminBlog
- fex_bd
- gwuhaolin-git
- Deboy's Blog
- react-china
- react.docschina
- Vuejs社区
- vuejsDoc
- cdnSocketIo
- shuaihuaCC
- colorize
- stazhu
- 前端学习
- IBM Dev社区
- linux运维笔记
- webpackDoc
- sayskyGithub
- 前端里
- 996.ICU
- electronjs
- CS-Notes
- mqyqingfengBlog
- beego官方
- 编码规范
- 阮一峰个人网站
- sessionstack
- damonareGoUp
- 咀嚼之味
- fe-interview
- xd-tayde/blog
- css-tricks
- ghmagical个人中心
- markyunp6
- hellogithub
- 霜序廿
- rin部落
- 建站素材
- 前端资源网
- CSS开发手册
- web技术交流
- 程新松个人网站
- wangEditor
- 小松博客
- 交流学习社区