前言
分布式微服务系统中添加登录和注册,(这里暂未完成分布式情况下用户登录信息情况记录),主要记录:一个微服务专门管理用户信息。需要通过远程调用的形式,来完成用户注册以及登录流程,同时密码采用MD5加密形式,保存到数据库。
1、注册
1.1 大致流程
- 1、用户填写基本信息
- 2、用户点击获取验证码
- 1)调用编写的第三方服务,第三方服务中有阿里云短信验证获取的接口。
- 2)阿里云短信验证将验证码发送到手机(其中验证码是自己生成设定的)
- 3、用户将验证码填写后,点击注册
- 1)后台对输入的信息以及验证进行校验
- 2) 验证码的校验,是通过redis来完成。首先将生产的验证码存入一个可过期时间的key中。注册时,再将用户输入的验证码和从redis中取出的验证码进行比对
- 3) 通过MD5对输入的明文密码进行加密
- 4、远程调用添加用户信息的接口,完成注册操作。用户信息的管理单独写成一个微服务。
1.2 核心代码
远程服务接口中的具体业务逻辑实现
@PostMapping(value = "/register")
public String register(@Valid UserRegisterVo vos, BindingResult result,
RedirectAttributes attributes) {
//如果有错误回到注册页面
if (result.hasErrors()) {
Map<String, String> errors = result.getFieldErrors().stream().collect(Collectors.toMap(FieldError::getField, FieldError::getDefaultMessage));
attributes.addFlashAttribute("errors",errors);
//效验出错回到注册页面
return "redirect:http://auth.zyz.com/reg.html";
}
//1、效验验证码
String code = vos.getCode();
//获取存入Redis里的验证码
String redisCode = stringRedisTemplate.opsForValue().get(AuthServerConstant.SMS_CODE_CACHE_PREFIX + vos.getPhone());
if (!StringUtils.isEmpty(redisCode)) {
//截取字符串
if (code.equals(redisCode.split("_")[0])) {
//删除验证码;令牌机制
stringRedisTemplate.delete(AuthServerConstant.SMS_CODE_CACHE_PREFIX+vos.getPhone());
//验证码通过,真正注册,调用远程服务进行注册
R register = memberFeignService.register(vos);
if (register.getCode() == 0) {
//成功
return "redirect:http://auth.zyz.com/login.html";
} else {
//失败
Map<String, String> errors = new HashMap<>();
errors.put("msg", register.getData("msg",new TypeReference<String>(){}));
attributes.addFlashAttribute("errors",errors);
return "redirect:http://auth.zyz.com/reg.html";
}
} else {
//效验出错回到注册页面
Map<String, String> errors = new HashMap<>();
errors.put("code","验证码错误");
attributes.addFlashAttribute("errors",errors);
return "redirect:http://auth.zyz.com/reg.html";
}
} else {
//效验出错回到注册页面
Map<String, String> errors = new HashMap<>();
errors.put("code","验证码错误");
attributes.addFlashAttribute("errors",errors);
return "redirect:http://auth.zyz.com/reg.html";
}
}
远程服务接口–用户信息注册
通过远程服务调用,调用添加用户的接口。
@Override
public void register(MemberUserRegisterVo vo) {
MemberEntity memberEntity = new MemberEntity();
//设置默认等级
MemberLevelEntity levelEntity = memberLevelDao.getDefaultLevel();
memberEntity.setLevelId(levelEntity.getId());
//设置其它的默认信息
//检查用户名和手机号是否唯一。感知异常,异常机制
checkPhoneUnique(vo.getPhone());
checkUserNameUnique(vo.getUserName());
memberEntity.setNickname(vo.getUserName());
memberEntity.setUsername(vo.getUserName());
//密码进行MD5加密
BCryptPasswordEncoder bCryptPasswordEncoder = new BCryptPasswordEncoder();
String encode = bCryptPasswordEncoder.encode(vo.getPassword());
memberEntity.setPassword(encode);
memberEntity.setMobile(vo.getPhone());
memberEntity.setGender(0);
memberEntity.setCreateTime(new Date());
//保存数据
this.baseMapper.insert(memberEntity);
}
1.3 页面效果
2、登录
2.1 登录大致流程
- 1、用户输入账号 | 手机号 ,密码。进行登录
- 2、 远程服务调用接口,对用户登录信息进行查询
2.2 核心代码
@PostMapping(value = "/login")
public String login(UserLoginVo vo, RedirectAttributes attributes, HttpSession session) {
//远程登录
R login = memberFeignService.login(vo);
if (login.getCode() == 0) {
MemberResponseVo data = login.getData("data", new TypeReference<MemberResponseVo>() {});
session.setAttribute(LOGIN_USER,data);
return "redirect:http://zyz.com";
} else {
Map<String,String> errors = new HashMap<>();
errors.put("msg",login.getData("msg",new TypeReference<String>(){}));
attributes.addFlashAttribute("errors",errors);
return "redirect:http://auth.zyz.com/login.html";
}
}
远程服务接口
远程服务调用,调用另外一个服务的接口
@Override
public MemberEntity login(MemberUserLoginVo vo) {
String loginacct = vo.getLoginacct();
String password = vo.getPassword();
//1、去数据库查询 SELECT * FROM ums_member WHERE username = ? OR mobile = ?
MemberEntity memberEntity = this.baseMapper.selectOne(new QueryWrapper<MemberEntity>()
.eq("username", loginacct).or().eq("mobile", loginacct));
if (memberEntity == null) {
//登录失败
return null;
} else {
//获取到数据库里的password
String password1 = memberEntity.getPassword();
BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
//进行密码匹配
boolean matches = passwordEncoder.matches(password, password1);
if (matches) {
//登录成功
return memberEntity;
}
}
return null;
}