zuul入門(3)開發zuul的過濾器


1、編寫Zuul過濾器(Java&Groovy)

理解過濾器類型和請求生命周期后,我們來編寫一個Zuul過濾器。編寫Zuul的過濾器非常簡單,我們只需繼承抽象類ZuulFilter,然后實現幾個抽象方法就可以了。

那么現在,我們來編寫一個簡單的Zuul過濾器,讓該過濾器打印請求日志。

(1) 復制項目microservice-gateway-zuul,將ArtifactId修改為microservice-gateway-zuul-filter。

(2) 編寫自定義Zuul過濾器

 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
public class PreRequestLogFilter extends ZuulFilter {
  private static final Logger LOGGER = LoggerFactory.getLogger(PreRequestLogFilter. class );
  @Override
  public String filterType() {
  return "pre" ;
  }
  @Override
  public int filterOrder() {
  return 1 ;
  }
  @Override
  public boolean shouldFilter() {
  return true ;
  }
  @Override
  public Object run() {
  RequestContext ctx = RequestContext.getCurrentContext();
  HttpServletRequest request = ctx.getRequest();
  PreRequestLogFilter.LOGGER.info(String.format( "send %s request to %s" , request.getMethod(), request.getRequestURL().toString()));
  return null ;
  }
}

由代碼可知,自定義的Zuul Filter需實現以下幾個方法:

  1. filterType:返回過濾器的類型。有pre、route、post、error等幾種取值,分別對應上文的幾種過濾器。詳細可以參考com.netflix.zuul.ZuulFilter.filterType() 中的注釋。
  2. filterOrder:返回一個int值來指定過濾器的執行順序,不同的過濾器允許返回相同的數字。
  3. shouldFilter:返回一個boolean值來判斷該過濾器是否要執行,true表示執行,false表示不執行。
  4. run:過濾器的具體邏輯。本例中,我們讓它打印了請求的HTTP方法以及請求的地址。

(2) 修改啟動類,為啟動類添加以下內容:

 
1
2
3
4
@Bean
public PreRequestLogFilter preRequestLogFilter() {
  return new PreRequestLogFilter();
}

3、測試Zuul過濾器

(1) 啟動microservice-discovery-eureka。

(2) 啟動microservice-provider-user。

(3) 啟動microservice-gateway-zuul-filter。

(4) 訪問http://localhost:8040/microservice-provider-user/1 ,可獲得類似如下的日志。

 
1
[nio- 8040 -exec- 6 ] c.i.c.s.filters.pre.PreRequestLogFilter : send GET request to http: //localhost:8040//microservice-provider-user/1

說明我們編寫的自定義Zuul過濾器被執行了。

4、禁用Zuul過濾器

Spring Cloud默認為Zuul編寫並啟用了一些過濾器,例如DebugFilter、FormBodyWrapperFilter、PreDecorationFilter等。這些過濾器都存放在spring-cloud-netflix-core這個Jar包的org.springframework.cloud.netflix.zuul.filters包中。

一些場景下,我們想要禁用掉部分過濾器,此時該怎么辦呢?

答案非常簡單,只需設置zuul.<SimpleClassName>.<filterType>.disable=true ,即可禁用SimpleClassName所對應的過濾器。

以過濾器org.springframework.cloud.netflix.zuul.filters.post.SendResponseFilter為例,只需設置zuul.SendResponseFilter.post.disable=true ,即可禁用該過濾器。

5、幾個過濾器的例子

5.1、根據用戶名來過濾

通過繼承ZuulFilter然后覆寫上面的4個方法,實現一個簡單的過濾器:

filterType:返回一個字符串代表過濾器的類型,在zuul中定義了四種不同生命周期的過濾器類型,具體如下:

  • pre:可以在請求被路由之前調用
  • route:在路由請求時候被調用
  • post:在route和error過濾器之后被調用
  • error:處理請求時發生錯誤時被調用

Zuul的主要請求生命周期包括“pre”,“route”和“post”等階段。對於每個請求,都會運行具有這些類型的所有過濾器。 

filterOrder:通過int值來定義過濾器的執行順序

shouldFilter:返回一個boolean類型來判斷該過濾器是否要執行,所以通過此函數可實現過濾器的開關。在上例中,我們直接返回true,所以該過濾器總是生效

run:過濾器的具體邏輯。需要注意,這里我們通過ctx.setSendZuulResponse(false)令zuul過濾該請求,不對其進行路由,然后通過ctx.setResponseStatusCode(401)設置了其返回的錯誤碼

過濾器間的協調
    過濾器沒有直接的方式來訪問對方。 它們可以使用RequestContext共享狀態,這是一個類似Map的結構,具有一些顯式訪問方法用於被認為是Zuul的原語,內部是使用ThreadLocal實現的。

5.2、根據密碼來過濾

5.3、post過濾器


免責聲明!

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



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