SpringCloud之Zuul

什麼是網關

API Gateway,是系統的唯一對外的入口,介於客戶端和服務器端之間的中間層,處理非業務功能 提供路由請求、鑑權、監控、緩存、限流等功能

什麼是Zuul

Spring Cloud Zuul是整合Netflix公司的Zuul開源項目實現的微服務網關,它實現了請求路由、負載均衡、校驗過 慮等 功能。

Zuul與Nginx怎麼配合使用

在這裏插入圖片描述
Nginx的作用是反向代理、負載均衡,Zuul的作用是保障微服 務的安全訪問,攔截微服務請求,校驗合法性及負載均衡。

實際運用
在這裏插入圖片描述
客戶端請求網關/api/learning,通過路由轉發到/learning
客戶端請求網關/api/course,通過路由轉發到/course

pom依賴

	 <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-zuul</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>

Zuul配置

zuul:
  routes:
    manage-course:
      path: /course/**
      serviceId: xc-service-manage-course #微服務名稱,網關會從eureka中獲取該服務名稱下的服務實例的地址
      # 例子:將請求轉發到http://localhost:31200/course
      #url: http://www.baidu.com #也可指定url,此url也可以是外網地址\
      strip-prefix: false #true:代理轉發時去掉前綴,false:代理轉發時不去掉前綴
      sensitiveHeaders:  #默認zuul會屏蔽cookie,cookie不會傳到下游服務,這裏設置爲空則取消默認的黑名單,如果設置了具體的頭信息則不會傳到下游服務
      #   ignoredHeaders: 默認爲空表示不過慮任何頭
    xc-service-learning:  #路由名稱,名稱任意,保持所有路由名稱唯一
      path: /learning/**
      serviceId: xc-service-learning #指定服務id,從Eureka中找到服務的ip和端口
      strip-prefix: false
      sensitiveHeaders:
  • manage-course:爲路由名稱,名稱任意,保持所有路由名稱唯一
  • path:代理的請求
  • serviceId:微服務名稱,網關會從eureka中獲取該服務名稱下的服務實例的地址,轉發到該地址
  • strip-prefix:是否去掉前綴,true:代理轉發時去掉前綴,false:代理轉發時不去掉前綴,例如,爲true請 求/course/coursebase/get/…,代理轉發到/coursebase/get/,如果爲false則代理轉發到/course/coursebase/get
  • sensitiveHeaders:敏感頭設置,默認會過慮掉cookie,這裏設置爲空表示不過慮
  • ignoredHeaders:可以設置過慮的頭信息,默認爲空表示不過慮任何頭

啓動類

@SpringBootApplication
@EnableZuulProxy//此工程是一個zuul網關
public class GatewayApplication {

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

@EnableZuulProxy:表明此工程是一個zuul網關

過慮器

我們要定義一個過濾器繼承ZuulFilter,重寫其方法來實現身份校驗,請求過濾

filterType :返回的字符代表過濾器類型,

  • pre:請求在被路由之前調用,我們可以利用這種過濾器實現身份驗證,在集羣中選擇請求的爲服務、記錄調試信息等。
  • routing:將請求路由到爲服務。構建發送給微服務的請求
  • post:這種過濾器在routing和error過濾器後調用,可以爲響應添加標準的http header、收集信息的指標
  • error:處理請求時發生錯誤調用

filterOrder:此方法返回整形數值,通過此數值來定義過濾器的執行順序,數字越小優先級越高
shouldFilter:返回一個Boolean值,判斷該過濾器是否需要執行
run:過濾器的業務邏輯

@Component
public class LoginFilter extends ZuulFilter {

    @Autowired
    private AuthService authService;

    private static final Logger LOG = LoggerFactory.getLogger(LoginFilter.class);

    @Override
    public String filterType() {
        return "pre";
    }

    @Override
    public int filterOrder() {
        return 3;
    }

    @Override
    public boolean shouldFilter() {
        return true;
    }

    /**
     * 身份校驗
     *
     * @return
     * @throws ZuulException
     */
    @Override
    public Object run() throws ZuulException {
//        獲取請求容器
        RequestContext currentContext = RequestContext.getCurrentContext();
        HttpServletRequest request = currentContext.getRequest();
        HttpServletResponse response = currentContext.getResponse();

//        獲取token
        String token = authService.getTokenFromCookie(request);
        if (StringUtils.isEmpty(token)){
            access_denied();
        }
//        查詢jwt
        String jwt = authService.getJwtFromHeader(request);
        if (StringUtils.isEmpty(jwt)){
            access_denied();
        }
//        從redis中校驗身份令牌是否過期
        long expire = authService.getExpire(token);
        if (expire<0){
            access_denied();
        }
        return null;
    }

    private void access_denied() {
        RequestContext currentContext = RequestContext.getCurrentContext();
        //           拒絕請求
        currentContext.setSendZuulResponse(false);
//            設置響應狀態碼
        currentContext.setResponseStatusCode(200);
        ResponseResult result = new ResponseResult(CommonCode.FAIL);
        String jsonString = JSON.toJSONString(result);
        currentContext.setResponseBody(jsonString);
        currentContext.getResponse().setContentType("application/json;charset=UTF-8");
    }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章