boke | 前后端分离中使用JWT保持前端数据的持久化,并自动登录

在boke后台登录系统中实现了自动登录的功能,这也是前后端分离的开发模式中最常见的一个问题,如何保持登录状态的持久化。今天就来通过实现自动登录来一步步理清前端数据持久化的思路。

一 实现思路

当用户首次登录时,输入用户名和密码,服务器先校验用户名和密码,如果正确,则根据一定的规则生成一个token并返回给前端,前端将这个token存到locationStorage中,等下次登录时或者进行其他请求时,可以将token传到后台服务器,服务器后先验证token是否有效,有效则进行下一步请求,无效则返回token无效的消息给前端,前端判断之后决定跳转页面。

二 使用的框架和技术

前端使用的是angular4,后台使用JWT来生成token和验证token。

三 代码

@RequestMapping("/login")
   @ResponseBody
   public Object login(@RequestBody User user) {
	   Result result = null;
	   Map data = new HashMap();
	   
		try {
			if(loginService.login(user.getUsername(), user.getPassword())) {
				String token = JWT.createJWT(user.getUsername(), user.getPassword(), 24*60*60*1000);
				data.put("token", token);
				result= new Result(SysConstant.STATE_SUCCESS,"login success",data); 
			}else {
				result= new Result(SysConstant.STATE_FAILURE,"login failure",false); 
			}
		} catch (Exception e) {
			result= new Result(SysConstant.STATE_FAILURE,"login failure",false); 
			e.printStackTrace();
		}
		 return JSONUtil.toJSON(result);
   } 
   
   @RequestMapping("/autoLogin")
   @ResponseBody 
   public Object autoLogin(@RequestParam("token") String token) {
	   Result result = null;
	   try {
		   CheckResult  cr = JWT.validateJWT(token);
		   if(cr.isSuccess()) {
			   result= new Result(SysConstant.STATE_SUCCESS,"auto login success",true);
		   } else {
			   result= new Result(SysConstant.STATE_FAILURE,"auto login failure",false);
		   }
	   } catch (Exception e) {
		   result= new Result(SysConstant.STATE_FAILURE,"auto login failure",false);
		   e.printStackTrace();
	   }
	 return JSONUtil.toJSON(result);
   }

下面是前端的代码:

@Component({
  selector: 'app-login',
  templateUrl: './login.component.html',
  styleUrls: ['./login.component.css']
})
export class LoginComponent implements OnInit {

  constructor(private route: Router, private loginService: LoginService, private articleService: ArticleService) { }

  ngOnInit() {
    this.loginService.autoLogin().then(response=>{
      if(response.code === 0){
        this.route.navigate(['/home']);
      }
    })
    
  }
  formSubmit(value) {
    this.loginService.doLogin(value).then(data=>{
      if(data.code === 0){
        localStorage.setItem("token",data.data.token);
        this.route.navigate(['/home']);
      }else{
        console.log("登录失败");
      }
    });
  }
}
@Injectable()
export class LoginService {
  constructor(private http: HttpClient, private router: Router) { }
  doLogin(value) :Promise {
    const body = {
      username: value.username,
      password: value.password
    };

    return this.http.post(`/blog/manager/login`, body)
      .toPromise()
      .then(res => res);
  }

  autoLogin(): Promise {
    const headers = new HttpHeaders();
    headers.append('Content-Type', 'application/x-www-form-urlencoded');
    const param = new HttpParams().set("token",localStorage.getItem("token"));
    return this.http.post(`/blog/manager/autoLogin`, param,{
      headers:headers
    })
    .toPromise()
    .then(res => res);
  }
}

在login组件初始化的时候先去自动登录验证token,如果token验证通过直接进入home页面,如果是第一次登录或者token过期,那么还是在login页面。

四 总结

上面需要注意的几个点:

在java中使用jwt时使用的是jjwt,需要引入jar包。你可以在这里下载 jjwt.jar

上面的代码不全,不能直接粘贴复制,只是提供了实现的关键代码。

That's all for today.

你可能感兴趣的:(web前端,js)