SpringBoot中使用Filter


1.在傳統web項目中添加filter

<filter> <filter-name>TestFilter</filter-name> <!--定義filter名稱 和filter類 --> <filter-class>com.jiafeng.filter.TestFilter</filter-class> </filter> <filter-mapping> <filter-name>TestFilter</filter-name> <url-pattern>/*</url-pattern> <!--設置filter攔截路徑 --> <init-param> <param-name>paramName</param-name> <!-- 添加初始參數 --> <param-value>paramValue</param-value> </init-param> </filter-mapping>

2.在springboot中添加filter有兩種方式

2.1代碼注冊方式

先定義Filter類:Myfilter,然后通過FilterRegistrationBean將filter注冊到調用鏈中。


@Configuration   //相當於spring中的<beans>標簽
public class WebConfiguration {

	@Bean   //相當於spring中<bean>標簽
	public FilterRegistrationBean<MyFilter> testFilterRegistration() {
		FilterRegistrationBean<MyFilter> registration = new FilterRegistrationBean<>();
		registration.setFilter(new MyFilter());
		registration.addUrlPatterns("/*");//配置過濾路徑
		registration.addInitParameter("paramName", "paramValue");//添加初始值
		registration.setName("myFilter");//設置filter名稱
		registration.setOrder(1);//請求中過濾器執行的先后順序,值越小越先執行
		return registration;
	}

	public class MyFilter implements Filter {

		@Override
		public void destroy() {
			System.out.println("銷毀MyFilter");
		}

		@Override
		public void doFilter(ServletRequest sRequest, ServletResponse sResponse, FilterChain chain)
				throws IOException, ServletException {
			HttpServletRequest request = (HttpServletRequest) sRequest;
			System.out.println("this is MyFilter url :" + request.getRequestURI());
			chain.doFilter(sRequest, sResponse);
		}

		@Override
		public void init(FilterConfig f) throws ServletException {
			System.out.println("初始化MyFilter");f.getInitParameter("");
} } }

2.2注解注冊方式

定義過濾器類:HelloFilter,在過濾器類上添加@WebFilter注解配置過濾器名稱、過濾路徑等屬性,通過@Order配置過濾器執行順序。

注意使用@WebServlet、@WebFilter、@WebListener等servlet注解時需要在springboot的啟動類上添加@ServletComponentScan注解,否則不會生效。

@WebFilter(urlPatterns="/*",filterName="helloFilter",initParams= {@WebInitParam(name="paramName",value="paramValue"),@WebInitParam(name="paramName2",value="paramValue2")})
@Order(2)
public class HelloFilter implements Filter {

	@Override
	public void destroy() {

	}

	@Override
	public void doFilter(ServletRequest request, ServletResponse response, FilterChain filterChain)
			throws IOException, ServletException {
		System.out.println("執行過濾器Hello Filter !");
		filterChain.doFilter(request, response);
	}

	@Override
	public void init(FilterConfig arg0) throws ServletException {
		System.out.println("初始化HelloFilter!");
	}

}

啟動類

@SpringBootApplication
@ServletComponentScan
public class Application {

	public static void main(String[] args) {
		SpringApplication.run(Application.class, args);
	}

}

Spring在Java Filter注入Bean為Null的問題解決

 

在Spring的自動注入中普通的POJO類都可以使用@Autowired進行自動注入,但是除了兩類:Filter和Servlet無法使用自動注入屬性。(因為這兩個歸Web容器管理)可以用init(集承自HttpServlet后重寫init方法)方法中實例化對象。

解決方法:

其中涉及到五種Spring實例化容器對象:

方法一(這種方式不符合Web工程,不要使用):在初始化時保存ApplicationContext對象

ApplicationContext ac = new FileSystemXmlApplicationContext("applicationContext.xml");
ac.getBean("beanId");

說明:這種方式適用於采用Spring框架的獨立應用程序,需要程序通過配置文件手工初始化Spring的情況。

方法二(這種方式最簡單):通過Spring提供的工具類獲取ApplicationContext對象

復制代碼
import org.springframework.web.context.support.WebApplicationContextUtils;
ApplicationContext ac1 = WebApplicationContextUtils.getRequiredWebApplicationContext(ServletContext sc); ApplicationContext ac2 = WebApplicationContextUtils.getWebApplicationContext(ServletContext sc); ac1.getBean("beanId"); ac2.getBean("beanId");
復制代碼

說明:這種方式適合於采用Spring框架的B/S系統,通過ServletContext對象獲取ApplicationContext對象,然后在通過它獲取需要的類實例。上面兩個工具方式的區別是,前者在獲取失敗時拋出異常,后者返回null。

實例:

復制代碼
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        HttpServletRequest req = (HttpServletRequest)request;
        HttpServletResponse resp = (HttpServletResponse)response;
        ServletContext sc = req.getSession().getServletContext();
        XmlWebApplicationContext cxt = (XmlWebApplicationContext)WebApplicationContextUtils.getWebApplicationContext(sc);
        
        if(cxt != null && cxt.getBean("usersService") != null && usersService == null)
            usersService = (UsersService) cxt.getBean("usersService");
        
        Users users = this.usersService.queryByOpenid(openid);
復制代碼
復制代碼
public class WeiXinFilter implements Filter{
    
    private UsersService usersService;
    
    public void init(FilterConfig fConfig) throws ServletException {
        ServletContext sc = fConfig.getServletContext(); 
        XmlWebApplicationContext cxt = (XmlWebApplicationContext)WebApplicationContextUtils.getWebApplicationContext(sc);
        
        if(cxt != null && cxt.getBean("usersService") != null && usersService == null)
            usersService = (UsersService) cxt.getBean("usersService");        
    }
復制代碼

注意:如果在Spring Boot項目上XmlWebApplicationContext可以不用要,直接使用WebApplicationContext替代。

方法三:繼承自抽象類ApplicationObjectSupport

說明:抽象類ApplicationObjectSupport提供getApplicationContext()方法,可以方便的獲取到ApplicationContext。

Spring初始化時,會通過該抽象類的setApplicationContext(ApplicationContext context)方法將ApplicationContext對象注入。

方法四:繼承自抽象類WebApplicationObjectSupport

說明:類似上面方法,調用getWebApplicationContext()獲取WebApplicationContext

方法五:實現接口ApplicationContextAware

說明:實現該接口的setApplicationContext(ApplicationContext context)方法,並保存ApplicationContext 對象。Spring初始化時,會通過該方法將ApplicationContext對象注入。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM