前后端分离 Vue+springBoot+springSecurity获取不到登录用户名和密码的问题
文章目录前言一、问题描述二、查找原因三、解决总结前言最近手上有个项目,采用前后端分离的模式开发,前端使用vue 后端采用springBoot+springSecurity。最近开发就遇到个十分简单,但是由困了我两天的问题。我本着不掉光头发誓不罢休的原则,开始了苦逼的找bug日常。一、问题描述springSecurity自定义的登录框,获取不到用户名和密码。实际开发中我们不太可能使用springSe
前言
最近手上有个项目,采用前后端分离的模式开发,前端使用vue 后端采用springBoot+springSecurity。最近开发就遇到个十分简单,但是由困了我两天的问题。我本着不掉光头发誓不罢休的原则,开始了苦逼的找bug日常。
一、问题描述
springSecurity自定义的登录框,获取不到用户名和密码。
实际开发中我们不太可能使用springSecurity自带的登录界面,所以我们一般会使用自定义的登录界面。为了展示效果,我简单的写了一个极其丑陋的登录界面,如下
<template>
<div id="app" style="align-content: center">
<span><h1>登录</h1></span>
<el-form :label-position="labelPosition" label-width="80px" :model="formLabelAlign">
<el-form-item label="用户名">
<el-input v-model="formLabelAlign.username" style="width:300px"></el-input>
</el-form-item>
<el-form-item label="密码">
<el-input v-model="formLabelAlign.password" style="width:300px"></el-input>
</el-form-item>
<el-form-item>
<el-button type="primary" @click="onSubmit">登录</el-button>
</el-form-item>
</el-form>
</div>
</template>
还有个点击事件—点击登录发起的请求
onSubmit() {
this.$axios.post("http://localhost:8082/login", this.formLabelAlign,{
headers:{
'Content-Type':'application/x-www-form-urlencoded'
}
}).then(res => {
console.log(res);
})
在webSecurityConfig中配置拦截规则
protected void configure(HttpSecurity http) throws Exception {
http.cors().and()
.authorizeRequests()
.antMatchers("/login").permitAll()
.antMatchers("/**").hasRole("nomal")
.and().formLogin().loginProcessingUrl("/login").permitAll()
.successHandler(new AuthenticationSuccessHandlerImpl())
.failureHandler(new AuthenticationFailureHandlerImpl())
.and().logout().logoutUrl("/logout").permitAll()
.logoutSuccessHandler(new LogoutSuccessHandlerImpl())
.and().csrf().disable().exceptionHandling();
}
进过一番的配置,之后开心地去测试。每次都登录失败。
为了测试,我在自定义的provider中加入了打印登录的信息。
package com.yzm.spring_secrurity;
import com.yzm.spring_secrurity.pojo.UserInfo;
import com.yzm.spring_secrurity.service.MyUserDetailService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.stereotype.Component;
import java.util.Collection;
@Component
public class MyAuthenticationProvider implements AuthenticationProvider {
@Autowired
private MyUserDetailService myUserDetailService;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
String name = authentication.getName();
String password = (String) authentication.getCredentials();
System.out.println("name is "+name);
System.out.println("password is "+password);
UserInfo userInfo = (UserInfo) myUserDetailService.loadUserByUsername(name);
if (userInfo == null){
throw new BadCredentialsException("用户名不存在");
}
if (!userInfo.getPassword().equals(password)){
throw new BadCredentialsException("密码错误");
}
Collection<? extends GrantedAuthority> authorities = userInfo.getAuthorities();
return new UsernamePasswordAuthenticationToken(userInfo,password,authorities);
}
@Override
public boolean supports(Class<?> aClass) {
return true;
}
}
输入用户名和密码后,后台打印结果
二、查找原因
我知道,登录验证的是由 UsernamePasswordAuthenticationFilter处理的
在这个过滤器中我们可以看到参数名如果自己没有配置就必须是(username,password),登录必须是post请求,并且请求路径一定是login(当然可以修改)。我们还看到了获取用户名和密码的方法obtainUsername、obtainPassword,点进去看了一,我彻底懵了(醒悟了)。
这居然是我学javaWeb用的最多的方法request.getParameter(),post怎么获取不到呢???,查了无数的资料,他们说contentType的原因。但是可以看到,我修改了的,不起效(这我不知道原因),后来有人说用qs可以,将参数以&连接到网址后面。这样就可以获取到。
三、解决
安装qs
npm install qs
在main.js中添加
import qs from 'qs'
Vue.prototype.$qs=qs
最后修改请求
onSubmit() {
this.$axios.post("http://localhost:8082/login", this.$qs.stringify(this.formLabelAlign),{
headers:{
'Content-Type':'application/x-www-form-urlencoded'
}
}).then(res => {
console.log(res);
})
}
在此点击登录,就可看到后台获取到了用户名和密码
总结
使用request.getParameter获取参数值,这样方式在get请求中屡试不爽,而且非常好用,因为get的参数就是url后面,可以和方便的取到,但是post请求里面的参数是不一样的,要么使用qs进行转换,要么就自己封装下。最后还是说一句,读源码实在是太重要了,如果没看到源码,这个问题不知道要困我多久。
更多推荐
所有评论(0)