1.登录实现流程
单一服务器模式登录(1)使用seession对象实现 --session.setAttribute()后判断是否能获取值
分布式服务器无法使用session:单点登录(SSO )可以适配集群分布式服务器部署,在任何一个模块上登录了,可以在任何其他的模块上访问。
单点登录三种常见的方式
1.session的广播机制实现
--session复制(早期方式) 容易造成数据重复
2.使用cookie + redis实现
--cookie 客户端技术,每次发送请求带着cookie发送
(1)在项目中的任何一个模块进行登录,登陆后,把数据放到redis和cookie中
redis: key:生成唯一随机值 value:用户数据 可以设置过期时间
cookie:把redis里面生成的key值放到cookie中。
(2)访问项目中其他模块,发送带着cookie进行发送 ,获取cookie值,拿着cookie做事
把cookie获取值,到redis进行查询,根据key进行查询,查询到的值就是登录
3.使用token实现
--token定义: 按照一定的规则生成的字符串,字符串可以包含用户信息如:(192.1.1.1#username$password)。 设置过期时间
(1).在项目中的某个模块进行登录,按照规则生成字符串,把登录之后的用户包含生成的字符串里面,把字符串返回(可以把字符串通过cookie返回 或 通过地址栏进行返回)
(2)再去访问项目中的其他模块,每次访问在地址栏带着生成的字符串,根据字符串 获取用户的信息,如果可以获取到就是登录。
2.注册接口
(1).整合jwt
*token是按照一定该规则生成字符串,包含用户信息
*规则是怎么样的自己定义
*一般采用通用的规则,官方规则 jwt
*jwt就是给我们规定好了规则,使用jwt规则可以生成字符串,包含用户信息
jwt生成的三部分:1.头部门 2.有效载荷 包含主体信息(用户信息)3.签名哈希 防伪标识
(2).整合阿里云的短信服务
3.登录和注册接口和token接口(登陆后页面应该显示的是头像用户名等信息。在token中得到)
(1).登录接口
service层会返回给前端个token
//登录的方法 @Override public String login(UcenterMember member) throws UnsupportedEncodingException, NoSuchAlgorithmException { //获取登录的手机号和密码 String mobile = member.getMobile(); String password = member.getPassword(); //先判断手机号和密码空的话返回错误 if (StringUtils.isEmpty(mobile)||StringUtils.isEmpty(password)){ throw new MyException(20001,"登录失败"); } //判断手机号是否正确 QueryWrapper<UcenterMember> wrapper = new QueryWrapper<>(); wrapper.eq("mobile",mobile); UcenterMember mobileMember = baseMapper.selectOne(wrapper); if (mobileMember == null){ throw new MyException(20001,"手机号不存在"); } //判断密码是否正确 //数据库中的密码都是加密的 输入的密码进行加密后在进行比较 //加密方式MD5 --只能加密不能解密 if (!MD5Util.encrypt(password).equals(mobileMember.getPassword())){ throw new MyException(20001,"密码不正确"); } //判断账号是否被禁用 if (mobileMember.getIsDisabled()){ throw new MyException(20001,"账号被禁用"); } //登录成功 生成token字符串 String token = JwtUtils.getJwtToken(mobileMember.getId(), mobileMember.getNickname()); return token; }
(2).注册接口
1.创建实体类用于注册账号
2.在controller和service中创建注册方法
public String login(UcenterMember member) throws UnsupportedEncodingException, NoSuchAlgorithmException { //获取登录的手机号和密码 String mobile = member.getMobile(); String password = member.getPassword(); //先判断手机号和密码空的话返回错误 if (StringUtils.isEmpty(mobile)||StringUtils.isEmpty(password)){ throw new MyException(20001,"登录失败"); } //判断手机号是否正确 QueryWrapper<UcenterMember> wrapper = new QueryWrapper<>(); wrapper.eq("mobile",mobile); UcenterMember mobileMember = baseMapper.selectOne(wrapper); if (mobileMember == null){ throw new MyException(20001,"手机号不存在"); } //判断密码是否正确 //数据库中的密码都是加密的 输入的密码进行加密后在进行比较 //加密方式MD5 --只能加密不能解密 if (!MD5Util.encrypt(password).equals(mobileMember.getPassword())){ throw new MyException(20001,"密码不正确"); } //判断账号是否被禁用 if (mobileMember.getIsDisabled()){ throw new MyException(20001,"账号被禁用"); } //登录成功 生成token字符串 String token = JwtUtils.getJwtToken(mobileMember.getId(), mobileMember.getNickname()); return token; }
(3)登录页面的右上角在登录与未登录状态是不同的
@GetMapping("gertMemberInfo") public R gegertMemberInfo(HttpServletRequest request){ //根据request获取token信息 String memberId = JwtUtils.getMemberIdByJwtToken(request); //根据id查询数据库查到我们需要的条件 UcenterMember member = memberService.getById(memberId); return R.ok().data("userIndo",member); }
4.注册和登录的前端实现
1.安装插件
npm install element-ui
npm install vue-qriously --以后使用微信生成二维码的插件
2.修改配置文件 nuxt-swiper-plugin.js,使用插件
import Vue from 'vue'
import VueAwesomeSwiper from 'vue-awesome-swiper/dist/ssr'
import VueQriously from 'vue-qriously'
import ElementUI from 'element-ui' //element-ui的全部组件
import 'element-ui/lib/theme-chalk/index.css'//element-ui的css
Vue.use(ElementUI) //使用elementUI
Vue.use(VueQriously)
Vue.use(VueAwesomeSwiper)
3.整合注册页面
1.在layouts文件中创建登录注册页面布局(也就是页面的头部尾部)
2.修改登录注册的超链接 --在layout文件夹啊下的default.vue
细节:
获取验证码后右侧倒计时60秒:setInterVal( 执行操作 , 每隔多久);
timeDowm(){
let result = setInterval(()=>{
--this.second;
this.codeTest = this.second
if(this.second < 1){
clearInterval(result);
this.sending = true;
this.second = 60;
this.codeTest = "获取验证码"
}
})
}
4.整合登录前端
1.安装js-cookie插件
npm install js-cookie
2.
3.登录和登录成功后页面显示数据的实现和分析过程
1.调用接口登录返回token字符串
2.第一步返回token字符串放到coikie中
loginApi.submitLogin(this.user).then(response=>{
//获取token字符串 1.名称 2.信息 3.作用范围
cookie.set('guli_token',response.data.data.token,{domain:'localhost'})
})
3.创建拦截器 --判断cookie中是否有cookie字符串,如果有九八token字符串放到header请求头中
service.interceptors.request.use(
config => {
//debugger
if (cookie.get('guli_token')) {
config.headers['token'] = cookie.get('guli_token');
}
return config
},
err => {
return Promise.reject(err);
})
4. 根据token值去调用接口,查看用户的信息并放到cookie中
loginApi.getLoginUserInfo().then(response=>{
this.loginInfo = response.data.data.userInfo
//获取返回的 用户信息 也放在cookie中
cookie.set('guli_ucenter',JSON.stringify(this.loginInfo),{domain:'localhost'})
})
5.在cookie中获取信息,并显示到页面上。(default.vue页面上登录时显示用户信息,不登录时显示登录和注册 在cookie中获取用户的基本信息)
data(){
return{
token:'',
loginInfo:{
id: '',
age: '',
avatar: '',
mobile: '',
nickname: '',
sex: ''
}
}
},
created(){
this.showInfo()
},
methods:{
//创建方法在cookie中获取信息
showInfo(){
//重cookie中获取信息
var userStr = cookie.get('guli_ucenter')
//字符串转换为json对象的形式
if(userStr){
this.loginInfo = JSON.parse(userStr)
}
}
}
页面样式
<ul class="h-r-login">
<li v-if="!loginInfo.id" id="no-login">
<a href="/login" title="登录">
<em class="icon18 login-icon"> </em>
<span class="vam ml5">登录</span>
</a>
|
<a href="/register" title="注册">
<span class="vam ml5">注册</span>
</a>
</li>
<li v-if="loginInfo.id" id="is-login-one" class="mr10">
<a id="headerMsgCountId" href="#" title="消息">
<em class="icon18 news-icon"> </em>
</a>
<q class="red-point" style="display: none"> </q>
</li>
<li v-if="loginInfo.id" id="is-login-two" class="h-r-user">
<a href="/ucenter" title>
<img
:src="loginInfo.avatar"
width="30"
height="30"
class="vam picImg"
alt
>
<span id="userName" class="vam disIb">{{ loginInfo.nickname }}</span>
</a>
<a href="javascript:void(0);" title="退出" @click="logout()" class="ml5">退出</a>
</li>
<!-- /未登录显示第1 li;登录后显示第2,3 li -->
</ul>