Springsecurity之SwitchUserFilter切換用戶

    使用的版本是Springsecurity的4.2.x版本。java

    業務場景是這樣的,系統中存在不少用戶,超級管理員要有個功能,就是能夠切換用戶,好比超級管理員,能夠切換爲系統中的任何一個用戶。Spingsecurity提供了一個SwitchUserFilter,咱們就用這個來實現功能。web

1、先來看怎麼使用

    List-1.1spring

<bean id="switchUserFilter" class="org.springframework.security.web.authentication.switchuser.SwitchUserFilter">
    <property name="userDetailsService" ref="userService"/>
    <property name="usernameParameter" value="userNo"/>
    <property name="switchUserUrl" value="/switch/user"/>
</bean>
  1. 定義switchUserFilter這個bean,以下List-1所示。用過Springsecurity的,應該知道UserDetailsService,這裏就再也不細講。
  2. usernameParameter的值是userNo,會從HttpServletRequest中獲取key爲userNo的值,以後用這個值從UserDetailsService中得到UserDetails。
  3. switchUserUrl,SwitchUserFilter是個Filter,會攔截請求,以後判斷請求的url是不是switchUserUrl,若是是就執行SwitchUserFilter裏面的邏輯,若是不是,就將請求轉給後面的Filter。

    List-1.1以後,將SwitchUserFilter放在FILTER_SECURITY_INTERCEPTOR以後,爲何呢?由於accessDecisionManager在FILTER_SECURITY_INTERCEPTOR中,即判斷是否有訪問資源的權限是在FILTER_SECURITY_INTERCEPTOR中,判斷過權限以後纔到SwitchUserFilter。ui

    List-1.2this

<security:http >
    ...
    <security:custom-filter ref="switchUserFilter" after="FILTER_SECURITY_INTERCEPTOR"/>
    ...
</security:http>

2、SwitchUserFilter的源碼

             

                                                                                        圖2.1url

    如2.1所示,SwitchUserFilter繼承了GenericFilterBean,它是Springframework中的類。SwitchUserFilter的doFilte方法以下List-2.1所示spa

    List-2.1debug

public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)
		throws IOException, ServletException {
	HttpServletRequest request = (HttpServletRequest) req;
	HttpServletResponse response = (HttpServletResponse) res;

	// check for switch or exit request
	if (requiresSwitchUser(request)) {
		// if set, attempt switch and store original
		try {
			Authentication targetUser = attemptSwitchUser(request);

			// update the current context to the new target user
			SecurityContextHolder.getContext().setAuthentication(targetUser);

			// redirect to target url
			this.successHandler.onAuthenticationSuccess(request, response,
					targetUser);
		}
		catch (AuthenticationException e) {
			this.logger.debug("Switch User failed", e);
			this.failureHandler.onAuthenticationFailure(request, response, e);
		}

		return;
	}
...
  1. List-2.1中,requiresSwitchUser會判斷request是不是switchUserUrl對應的請求。
  2. 獲取Authentication只會,會將其設置到SecurityContextHolder.getContext()。
相關文章
相關標籤/搜索