目錄
1.1 form-login元素介紹
1.1.1 使用自定義登錄頁面
1.1.2 指定登錄后的頁面
1.1.3 指定登錄失敗后的頁面
1.2 http-basic
1.1 form-login元素介紹
http元素下的form-login元素是用來定義表單登錄信息的。當我們什么屬性都不指定的時候Spring Security會為我們生成一個默認的登錄頁面。如果不想使用默認的登錄頁面,我們可以指定自己的登錄頁面。
1.1.1 使用自定義登錄頁面
自定義登錄頁面是通過login-page屬性來指定的。提到login-page我們不得不提另外幾個屬性。
- username-parameter:表示登錄時用戶名使用的是哪個參數,默認是“j_username”。
- password-parameter:表示登錄時密碼使用的是哪個參數,默認是“j_password”。
- login-processing-url:表示登錄時提交的地址,默認是“/j-spring-security-check”。這個只是Spring Security用來標記登錄頁面使用的提交地址,真正關於登錄這個請求是不需要用戶自己處理的。
所以,我們可以通過如下定義使Spring Security在需要用戶登錄時跳轉到我們自定義的登錄頁面。
<security:http auto-config="true">
<security:form-login login-page="/login.jsp"
login-processing-url="/login.do" username-parameter="username"
password-parameter="password" />
<!-- 表示匿名用戶可以訪問 -->
<security:intercept-url pattern="/login.jsp" access="IS_AUTHENTICATED_ANONYMOUSLY"/>
<security:intercept-url pattern="/**" access="ROLE_USER" />
</security:http>
需要注意的是,我們之前配置的是所有的請求都需要ROLE_USER權限,這意味着我們自定義的“/login.jsp”也需要該權限,這樣就會形成一個死循環了。解決辦法是我們需要給“/login.jsp”放行。通過指定“/login.jsp”的訪問權限為“IS_AUTHENTICATED_ANONYMOUSLY”或“ROLE_ANONYMOUS”可以達到這一效果。此外,我們也可以通過指定一個http元素的安全性為none來達到相同的效果。如:
<security:http security="none" pattern="/login.jsp" />
<security:http auto-config="true">
<security:form-login login-page="/login.jsp"
login-processing-url="/login.do" username-parameter="username"
password-parameter="password" />
<security:intercept-url pattern="/**" access="ROLE_USER" />
</security:http>
它們兩者的區別是前者將進入Spring Security定義的一系列用於安全控制的filter,而后者不會。當指定一個http元素的security屬性為none時,表示其對應pattern的filter鏈為空。從3.1開始,Spring Security允許我們定義多個http元素以滿足針對不同的pattern請求使用不同的filter鏈。當為指定pattern屬性時表示對應的http元素定義將對所有的請求發生作用。
根據上面的配置,我們自定義的登錄頁面的內容應該是這樣子的:
<form action="login.do" method="post">
<table>
<tr>
<td>用戶名:</td>
<td><input type="text" name="username"/></td>
</tr>
<tr>
<td>密碼:</td>
<td><input type="password" name="password"/></td>
</tr>
<tr>
<td colspan="2" align="center">
<input type="submit" value="登錄"/>
<input type="reset" value="重置"/>
</td>
</tr>
</table>
</form>
1.1.2 指定登錄后的頁面
通過default-target-url指定
默認情況下,我們在登錄成功后會返回到原本受限制的頁面。但如果用戶是直接請求登錄頁面,登錄成功后應該跳轉到哪里呢?默認情況下它會跳轉到當前應用的根路徑,即歡迎頁面。通過指定form-login元素的default-target-url屬性,我們可以讓用戶在直接登錄后跳轉到指定的頁面。如果想讓用戶不管是直接請求登錄頁面,還是通過Spring Security引導過來的,登錄之后都跳轉到指定的頁面,我們可以通過指定form-login元素的always-use-default-target屬性為true來達到這一效果。
通過authentication-success-handler-ref指定
authentication-success-handler-ref對應一個AuthencticationSuccessHandler實現類的引用。如果指定了authentication-success-handler-ref,登錄認證成功后會調用指定AuthenticationSuccessHandler的onAuthenticationSuccess方法。我們需要在該方法體內對認證成功做一個處理,然后返回對應的認證成功頁面。使用了authentication-success-handler-ref之后認證成功后的處理就由指定的AuthenticationSuccessHandler來處理,之前的那些default-target-url之類的就都不起作用了。
以下是自定義的一個AuthenticationSuccessHandler的實現類。
publicclass AuthenticationSuccessHandlerImpl implements
AuthenticationSuccessHandler {
publicvoid onAuthenticationSuccess(HttpServletRequest request,
HttpServletResponse response, Authentication authentication)
throws IOException, ServletException {
response.sendRedirect(request.getContextPath());
}
}
其對應使用authentication-success-handler-ref屬性的配置是這樣的:
<security:http auto-config="true">
<security:form-login login-page="/login.jsp"
login-processing-url="/login.do" username-parameter="username"
password-parameter="password"
authentication-success-handler-ref="authSuccess"/>
<!-- 表示匿名用戶可以訪問 -->
<security:intercept-url pattern="/login.jsp"
access="IS_AUTHENTICATED_ANONYMOUSLY" />
<security:intercept-url pattern="/**" access="ROLE_USER" />
</security:http>
<!-- 認證成功后的處理類 -->
<bean id="authSuccess" class="com.xxx.AuthenticationSuccessHandlerImpl"/>
1.1.3 指定登錄失敗后的頁面
除了可以指定登錄認證成功后的頁面和對應的AuthenticationSuccessHandler之外,form-login同樣允許我們指定認證失敗后的頁面和對應認證失敗后的處理器AuthenticationFailureHandler。
通過authentication-failure-url指定
默認情況下登錄失敗后會返回登錄頁面,我們也可以通過form-login元素的authentication-failure-url來指定登錄失敗后的頁面。需要注意的是登錄失敗后的頁面跟登錄頁面一樣也是需要配置成在未登錄的情況下可以訪問,否則登錄失敗后請求失敗頁面時又會被Spring Security重定向到登錄頁面。
<security:http auto-config="true">
<security:form-login login-page="/login.jsp"
login-processing-url="/login.do" username-parameter="username"
password-parameter="password"
authentication-failure-url="/login_failure.jsp"
/>
<!-- 表示匿名用戶可以訪問 -->
<security:intercept-url pattern="/login*.jsp*"
access="IS_AUTHENTICATED_ANONYMOUSLY" />
<security:intercept-url pattern="/**" access="ROLE_USER" />
</security:http>
通過authentication-failure-handler-ref指定
類似於authentication-success-handler-ref,authentication-failure-handler-ref對應一個用於處理認證失敗的AuthenticationFailureHandler實現類。指定了該屬性,Spring Security在認證失敗后會調用指定AuthenticationFailureHandler的onAuthenticationFailure方法對認證失敗進行處理,此時authentication-failure-url屬性將不再發生作用。
1.2 http-basic
之前介紹的都是基於form-login的表單登錄,其實Spring Security還支持彈窗進行認證。通過定義http元素下的http-basic元素可以達到這一效果。
<security:http auto-config="true">
<security:http-basic/>
<security:intercept-url pattern="/**" access="ROLE_USER" />
</security:http>
此時,如果我們訪問受Spring Security保護的資源時,系統將會彈出一個窗口來要求我們進行登錄認證。效果如下:
當然此時我們的表單登錄也還是可以使用的,只不過當我們訪問受包含資源的時候Spring Security不會自動跳轉到登錄頁面。這就需要我們自己去請求登錄頁面進行登錄。
需要注意的是當我們同時定義了http-basic和form-login元素時,form-login將具有更高的優先級。即在需要認證的時候Spring Security將引導我們到登錄頁面,而不是彈出一個窗口。