<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.koolyun</groupId>
<artifactId>Mcht-Service-Client</artifactId>
<packaging>war</packaging>
<version>0.0.1-SNAPSHOT</version>
<name>Mcht-Service-Client Maven Webapp</name>
<url>http://maven.apache.org</url>
<properties>
<!-- spring版本号 -->
<spring.version>3.2.18.RELEASE</spring.version>
<!-- 3.0.3.RELEASE< -->
<log4j.version>1.2.17</log4j.version>
<!-- mybatis版本号 -->
<mybatis.version>3.3.0</mybatis.version>
</properties>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>3.8.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>cglib</groupId>
<artifactId>cglib</artifactId>
<version>2.2</version>
</dependency>
<dependency>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
<version>1.2</version>
</dependency>
<dependency>
<groupId>commons-lang</groupId>
<artifactId>commons-lang</artifactId>
<version>2.6</version>
</dependency>
<!-- spring核心包 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${spring.version}</version>
<exclusions>
<exclusion>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-oxm</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>${spring.version}</version>
</dependency>
<!-- spring security start -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-acl</artifactId>
<version>2.0.5.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-core</artifactId>
<version>2.0.5.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-core-tiger</artifactId>
<version>2.0.5.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-taglibs</artifactId>
<version>2.0.5.RELEASE</version>
</dependency>
<!-- 日志文件管理包 -->
<!-- log start -->
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>${log4j.version}</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version>
</dependency>
<dependency>
<groupId>net.sf.ezmorph</groupId>
<artifactId>ezmorph</artifactId>
<version>1.0.6</version>
</dependency>
<dependency>
<groupId>net.sf.json-lib</groupId>
<artifactId>json-lib</artifactId>
<version>2.4</version>
<classifier>jdk15</classifier>
</dependency>
<!-- 映入JSON -->
<dependency>
<groupId>org.codehaus.jackson</groupId>
<artifactId>jackson-mapper-asl</artifactId>
<version>1.9.13</version>
</dependency>
<!-- funee -->
<dependency>
<groupId>org.funee.framework</groupId>
<artifactId>funee</artifactId>
<version>1.0.0</version>
</dependency>
<!-- https://mvnrepository.com/artifact/commons-pool/commons-pool -->
<dependency>
<groupId>commons-pool</groupId>
<artifactId>commons-pool</artifactId>
<version>1.6</version>
</dependency>
</dependencies>
<build>
<finalName>Mcht-Service-Client</finalName>
<pluginManagement>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.7</source>
<target>1.7</target>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<configuration>
<port>8080</port>
<path>/</path>
</configuration>
</plugin>
</plugins>
</pluginManagement>
</build>
</project>
There is a point in this, I use web.xml to intercept .do requests. This also lays a pit for the subsequent configuration of Spring to intercept login requests.
Spring intercepts the /j_spring_security_check request by default. In principle, you only need to configure the from action as /j_spring_security_check in the form of the page to enter the Spring Security processing flow when logging in. However, because only .do requests are configured, so this It needs to be configured in the xml of spring_security: login-processing-url="/j_spring_security_check.do", and the logou request also needs to be specified separately: <s:logout logout-success-url="/login/index.do" logout -url="/j_spring_security_logout.do"/>
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaeehttp://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" id="WebApp_1515646461031" version="3.0">
<display-name>Archetype Created Web Application</display-name>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring-mybatis.xml,classpath:spring-security.xml</param-value>
</context-param>
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<async-supported>true</async-supported>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<listener>
<listener-class>org.springframework.web.util.IntrospectorCleanupListener</listener-class>
</listener>
<context-param>
<param-name>log4jConfigLocation</param-name>
<param-value>classpath:log4j.properties</param-value>
</context-param>
<context-param>
<param-name>log4jRefreshInterval</param-name>
<param-value>6000</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.util.Log4jConfigListener</listener-class>
</listener>
<servlet>
<servlet-name>SpringMVC</servlet-name>
<servlet-class>com.koolyun.common.utils.UriScanDispatchServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring-mvc.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
<async-supported>true</async-supported>
</servlet>
<servlet-mapping>
<servlet-name>SpringMVC</servlet-name>
<url-pattern>*.do</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.js</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.css</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.gif</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.png</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.jpg</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.swf</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.woff</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.ttf</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.ico</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.woff2</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>default</servlet-name>
<url-pattern>*.html</url-pattern>
</servlet-mapping>
<context-param>
<param-name>webAppRoot</param-name>
<param-value>lightnote.root</param-value>
</context-param>
<welcome-file-list>
<welcome-file>/login.jsp</welcome-file>
</welcome-file-list>
<!-- <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 Security JCaptcha filter -->
<filter>
<filter-name>jcaptchaFilter</filter-name>
<filter-class>com.koolyun.security.service.impl.JCaptchaFilter</filter-class>
<init-param>
<param-name>failureUrl</param-name>
<param-value>/login/error.do?error=1</param-value>
</init-param>
</filter>
<!-- jcaptcha图片生成URL. -->
<filter-mapping>
<filter-name>jcaptchaFilter</filter-name>
<url-pattern>/commons/jcaptcha.jpg</url-pattern>
</filter-mapping>
<!-- jcaptcha登录表单处理URL.
必须放在springSecurityFilter的filter-mapping定义之前 -->
<filter-mapping>
<filter-name>jcaptchaFilter</filter-name>
<url-pattern>/j_spring_security_check.do</url-pattern>
</filter-mapping>
<!--Spring Security 2-->
<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>
</web-app>
The form-login attribute is explained in detail as follows:
form-login is a tag for configuring login-related information in the spring security namespace, and it contains the following attributes:
1. login-page custom login page url, the default is /login
2. login-processing-url The url intercepted by the login request, that is, the action specified when the form is submitted
3. default-target-url is the default URL to redirect after successful login
4. Always-use-default-target Whether to always use the default redirect url after successful login
5. authentication-failure-url URL redirected after login failure
6. The request field of username-parameter username defaults to userName
7. The password-parameter password request field defaults to password
8. authentication-success-handler-ref points to an AuthenticationSuccessHandler for handling successful authentication requests, and cannot be used at the same time as default-target-url and always-use-default-target
9. authentication-success-forward-url 用于authentication-failure-handler-ref
10. authentication-failure-handler-ref points to an AuthenticationFailureHandler for handling failed authentication requests
11. authentication-failure-forward-url 用于authentication-failure-handler-ref
12. authentication-details-source-ref points to an AuthenticationDetailsSource, used in the authentication filter
The following is the spring_security, xml file:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:s="http://www.springframework.org/schema/security" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beanshttp://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/securityhttp://www.springframework.org/schema/security/spring-security-2.0.4.xsd"
default-autowire="byType">
<description>SpringSecurity安全配置</description>
<!-- http安全配置 -->
<s:http auto-config="true" access-decision-manager-ref="accessDecisionManager"
access-denied-page="/commons/403.jsp">
<s:intercept-url pattern="/commons/**" filters="none" />
<s:intercept-url pattern="/images/**" filters="none" />
<s:intercept-url pattern="/saas/**" filters="none" />
<s:intercept-url pattern="/scripts/**" filters="none" />
<s:intercept-url pattern="/assets/**" filters="none" />
<s:intercept-url pattern="/styles/**" filters="none" />
<s:intercept-url pattern="/widgets/**" filters="none" />
<!-- <s:intercept-url pattern="/api/**" filters="none" /> -->
<s:intercept-url pattern="/mobile/**" filters="none" />
<s:intercept-url pattern="/wx-download/**" filters="none" />
<s:intercept-url pattern="/coupon/c/**" filters="none" />
<s:intercept-url pattern="/coupon/mm/**" filters="none" />
<s:intercept-url pattern="/koolcoupon/**" filters="none" />
<s:intercept-url pattern="/pay/Notify/**" filters="none" />
<!--<s:intercept-url pattern="/pay/NotifyTest/**" filters="none" />-->
<s:form-login login-page="/login/index.do" login-processing-url="/j_spring_security_check.do" authentication-failure-url="/login/error.do?error=true" default-target-url="/login/target.do" always-use-default-target="true" />
<s:logout logout-success-url="/login/index.do" logout-url="/j_spring_security_logout.do"/>
<s:concurrent-session-control expired-url="/login/sessionExpired.do" />
</s:http>
<!-- 认证配置 -->
<s:authentication-provider user-service-ref="userDetailsService">
<!-- 可设置hash使用sha1或md5散列密码后再存入数据库 -->
<s:password-encoder hash="md5" />
</s:authentication-provider>
<!-- 项目实现的用户查询服务 -->
<bean id="userDetailsService" class="com.koolyun.security.utils.UserDetailsServiceImpl"/>
<!--
重新定义的FilterSecurityInterceptor,使用databaseDefinitionSource提供的url-授权关系定义
-->
<bean id="filterSecurityInterceptor" class="org.springframework.security.intercept.web.FilterSecurityInterceptor">
<s:custom-filter before="FILTER_SECURITY_INTERCEPTOR" />
<property name="accessDecisionManager" ref="accessDecisionManager" />
<property name="objectDefinitionSource" ref="databaseDefinitionSource" />
</bean>
<!-- DefinitionSource工厂,使用resourceDetailsService提供的URL-授权关系. -->
<bean id="databaseDefinitionSource" class="com.koolyun.security.utils.DefinitionSourceFactoryBean">
<property name="resourceDetailsService" ref="resourceDetailsService" />
</bean>
<!-- 项目实现的URL-授权查询服务 -->
<bean id="resourceDetailsService" class="com.koolyun.security.service.ResourceDetailsServiceImpl" />
<!-- 授权判断配置, 将授权名称的默认前缀由ROLE_ -->
<bean id="accessDecisionManager" class="org.springframework.security.vote.AffirmativeBased">
<property name="decisionVoters">
<list>
<bean class="org.springframework.security.vote.RoleVoter">
<property name="rolePrefix" value="ROLE_" />
</bean>
<bean class="org.springframework.security.vote.AuthenticatedVoter" />
</list>
</property>
</bean>
</beans>
From the configuration, we can see that the bean userDetailsService is a processing class that handles password verification and permission verification.
public UserDetails loadUserByUsername(String userName)
throws UsernameNotFoundException, DataAccessException {
CsUser user;
String loginType = userName.split("~~~")[0];
String username = userName.split("~~~")[1];
// 查询用户是否存在
user = securityService.findUserByLoginName(userName);
if (user == null) {
throw new UsernameNotFoundException("用户" + userName + " 不存在");
}
org.springframework.security.userdetails.User userdetail = new org.springframework.security.userdetails.User(
authName, user.getPassword(), enabled, accountNonExpired,
credentialsNonExpired, accountNonLocked, grantedAuths);
return userdetail;
}
The password verification process is not specified here, and here comes the default password verification process of Spring Security.
<form action='/j_spring_security_check.do' method="post">
<div class="form-group org">
<label class="control-label visible-ie8 visible-ie9">客户号</label>
<input class="form-control form-control-solid placeholder-no-fix" type="text" autocomplete="on" placeholder=" 客户号" name="orgId" id="orgId" maxlength="15" autofocus="autofocus"/>
</div>
<div class="form-group">
<label class="control-label visible-ie8 visible-ie9">用户名</label>
<input class="form-control form-control-solid placeholder-no-fix" type="text" autocomplete="on" placeholder=" 用户名" name="j_username_tmp" id="j_username_tmp"/>
</div>
<div class="form-group">
<label class="control-label visible-ie8 visible-ie9">密码</label>
<input class="form-control form-control-solid placeholder-no-fix" type="password" autocomplete="off" placeholder=" 密码" name="j_password" id="password"/>
</div>
<div class="form-group clearfix">
<input type="text" id="j_captcha" name="j_captcha" placeholder="验证码" class="form-control form-control-yzm pull-left" size="8" maxlength="4">
<img src='<c:url value="/commons/jcaptcha.jpg"></c:url>' class="yzm-pic pull-left" id="captchaImg">
</form>