Spring Security只通过配置即可实现基于页面的认证与Url权限控制,但默认的实现是从内存或数据库表中获取用户名与密码,如果希望与本公司用户管理系统对接,则需要重新实现UserDetailsService接口。
UserDetailsService仅有一个方法:UserDetails loadUserByUsername(String username) throws UsernameNotFoundException,根据用户名获取用户认证信息与权限信息,以UserDetails对象返回。
具体实现如下所示:
一、Maven依赖配置(pom.xml)
<span style="white-space:pre"> </span><properties>
...
<org.springframework-security-version>4.0.1.RELEASE</org.springframework-security-version>
</properties>
<dependencies>
...
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-web</artifactId>
<version>${org.springframework-security-version}</version>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-config</artifactId>
<version>${org.springframework-security-version}</version>
</dependency>
</dependencies>
二、Web.xml配置
<span style="white-space:pre"> </span><filter>
<filter-name>springSecurityFilterChain</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>
<filter-mapping>
<filter-name>springSecurityFilterChain</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
三、Spring Context配置
<?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="http://www.springframework.org/schema/security"
xmlns:beans="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/security
http://www.springframework.org/schema/security/spring-security.xsd">
<http pattern="/**/*.css" security="none" />
<http pattern="/**/*.js" security="none" />
<http pattern="/security/**">
<form-login login-page="/security/login.jsp"
login-processing-url="/security/login" default-target-url="/security/index"
always-use-default-target="false" authentication-failure-url="/security/login.jsp?error=wrong_login_data"
username-parameter="username" password-parameter="password" />
<logout logout-url="/security/logout" />
<intercept-url pattern="/security/index" access="permitAll()" />
<intercept-url pattern="/security/logout" access="permitAll()" />
<intercept-url pattern="/security/login.jsp" access="permitAll()" />
<intercept-url pattern="/**" access="hasRole('USER')" />
<csrf />
</http>
<beans:bean name="bcryptEncoder"
class="org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder" />
<authentication-manager alias="authenticationManager">
<authentication-provider user-service-ref='myUserDetailsService'>
<password-encoder ref="bcryptEncoder" />
</authentication-provider>
</authentication-manager>
<beans:bean id="myUserDetailsService"
class="com.winssage.spring.security.userdetails.WinssageUserDetailsService">
<beans:property name="bcryptPasswordEncoder" ref="bcryptEncoder" />
</beans:bean>
</beans:beans>
四、login.jsp
<%@page contentType="text/html" pageEncoding="UTF-8" isErrorPage="true"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
"http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>登录</title>
</head>
<body>
<span style="white-space:pre"> </span><c:url value="/security/login" var="loginUrl" />
<span style="white-space:pre"> </span><form action="${loginUrl}" method="post">
<span style="white-space:pre"> </span><c:if test="${param.error != null}">
<span style="white-space:pre"> </span><p>Invalid username and password.</p>
<span style="white-space:pre"> </span></c:if>
<span style="white-space:pre"> </span><c:if test="${param.logout != null}">
<span style="white-space:pre"> </span><p>You have been logged out.</p>
<span style="white-space:pre"> </span></c:if>
<span style="white-space:pre"> </span><p>
<span style="white-space:pre"> </span><label for="username">Username</label>
<span style="white-space:pre"> </span><input type="text" id="username" name="username" />
<span style="white-space:pre"> </span></p>
<span style="white-space:pre"> </span><p>
<span style="white-space:pre"> </span><label for="password">Password</label>
<span style="white-space:pre"> </span><input type="password" id="password" name="password" />
<span style="white-space:pre"> </span></p>
<span style="white-space:pre"> </span><input type="hidden" name="${_csrf.parameterName}"
<span style="white-space:pre"> </span>value="${_csrf.token}" />
<span style="white-space:pre"> </span><button type="submit" class="btn">Log in</button>
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span></form>
</body>
</html>
五、 UserDetailsService接口实现
public class WinssageUserDetailsService implements UserDetailsService {
BCryptPasswordEncoder bcryptPasswordEncoder;
@Override
public UserDetails loadUserByUsername(String username)
throws UsernameNotFoundException {
List<GrantedAuthority> grantedAuths = new ArrayList<GrantedAuthority>();
grantedAuths.add(new SimpleGrantedAuthority("ROLE_USER"));
boolean enables = true;
boolean accountNonExpired = true;
boolean credentialsNonExpired = true;
boolean accountNonLocked = true;
String password=bcryptPasswordEncoder.encode("123456");
User userdetail = new User(username, password, enables,
accountNonExpired, credentialsNonExpired, accountNonLocked,
grantedAuths);
return userdetail;
}
public BCryptPasswordEncoder getBcryptPasswordEncoder() {
return bcryptPasswordEncoder;
}
public void setBcryptPasswordEncoder(BCryptPasswordEncoder bcryptPasswordEncoder) {
this.bcryptPasswordEncoder = bcryptPasswordEncoder;
}
}
注:本UserDetailsService接口实现只为做演示作用