一、黑名單攔截spring
二、參數驗籤數據庫
三、Api接口權限驗證設計模式
一、繼承ZuulFilter方法,實現業務邏輯api
@Component @Slf4j public class GatewayFilter extends ZuulFilter { @Override public String filterType() { return "pre"; } @Override public int filterOrder() { return 0; } @Override public boolean shouldFilter() { // 改成true,纔會走run方法 return true; } /** * 請求以前攔截處理業務邏輯 * @return * @throws ZuulException */ @Override public Object run() throws ZuulException { RequestContext ctx = RequestContext.getCurrentContext(); // 1.獲取請求對象 HttpServletRequest request = ctx.getRequest(); // 2.獲取響應對象 HttpServletResponse response = ctx.getResponse(); // 3.獲取客戶端真實ip地址 String ipAddr = IpUtil.getIpAddr(request); if (StringUtils.isEmpty(ipAddr)) { resultError(ctx, "未可以獲取到ip地址"); } // 4.動態獲取黑名單列表,判斷是黑名單,設置網關響應爲false if("127.0.0.1".equals(ipAddress)){ resultError(ctx, "ip:" + ipAddress + ",Insufficient access rights"); } // 5.傳遞參數簽名攔截 Map<String, String> verifyMap = SignUtil.toVerifyMap(request.getParameterMap(), false); if(!SignUtil.verify(verifyMap)){ resultError(ctx, "ip:" + ipAddress + ",Sign fail"); } // 6.api權限驗證 String servletPath = request.getServletPath(); String accessToken = request.getParameter("accessToken");if (StringUtils.isEmpty(accessToken)) { resultError(ctx, "AccessToken cannot be empty"); } // 調用接口驗證accessToken是否失效 BaseResponse<JSONObject> appInfo = verificaCodeServiceFeign.getAppInfo(accessToken);if (!isSuccess(appInfo)) { resultError(ctx, appInfo.getMsg()); } return null; } /** * 錯誤返回 * @param ctx * @param code * @param errorMsg */ private void resultError(RequestContext ctx, String errorMsg) { ctx.setResponseStatusCode(401); // 網關響應爲false 不會轉發服務 ctx.setSendZuulResponse(false); ctx.setResponseBody(errorMsg); }
一、基於建造者設計模式封裝: 網關權限控制app
public interface GatewayBuild { /** * 黑名單攔截 */ Boolean blackBlock(RequestContext ctx, String ipAddress, HttpServletResponse response); /** * 參數驗籤 */ Boolean paramsValidate(RequestContext ctx, String ipAddress, HttpServletRequest request); /** * api權限控制 * * @return */ Boolean apiAuthorize(RequestContext ctx, HttpServletRequest request); }
二、基於建造者設計模式封裝: 參數驗證build,業務邏輯的實現ide
@Slf4j @Component public class VerificationBuild implements GatewayBuild { @Override public Boolean blackBlock(RequestContext ctx, String ipAddress, HttpServletResponse response) { // 4.從數據庫動態讀取,判斷是黑名單,設置網關響應爲false if("127.0.0.1".equals(ipAddress)){ resultError(ctx, "ip:" + ipAddress + ",Insufficient access rights"); return false; } log.info(">>>>>>ip:{},驗證經過>>>>>>>", ipAddress); return true; } @Override public Boolean paramsValidate(RequestContext ctx, String ipAddress, HttpServletRequest request) { // 5.外網傳遞參數簽名攔截 Map<String, String> verifyMap = SignUtil.toVerifyMap(request.getParameterMap(), false); if(!SignUtil.verify(verifyMap)){ resultError(ctx, "ip:" + ipAddress + ",Sign fail"); return false; } return true; } @Override public Boolean apiAuthorize(RequestContext ctx, HttpServletRequest request) { String servletPath = request.getServletPath(); // 內部服務調用不須要accessToken驗證,若是public開頭,表示受權方訪問接口 if (!servletPath.substring(0, 7).equals("/public")) { return true; } String accessToken = request.getParameter("accessToken"); log.info(">>>>>accessToken驗證:" + accessToken); if (StringUtils.isEmpty(accessToken)) { resultError(ctx, "AccessToken cannot be empty"); return false; } // 調用接口驗證accessToken是否失效 BaseResponse<JSONObject> appInfo = verificaCodeServiceFeign.getAppInfo(accessToken); log.info(">>>>>>data:" + appInfo.toString()); if (!isSuccess(appInfo)) { resultError(ctx, appInfo.getMsg()); return false; } return true; } /** * 網關攔截 * @param ctx * @param code * @param errorMsg */ private void resultError(RequestContext ctx, String errorMsg) { ctx.setResponseStatusCode(401); // 網關響應爲false 不會轉發服務 ctx.setSendZuulResponse(false); ctx.setResponseBody(errorMsg); } }
三、基於建造者設計模式封裝: 鏈接Buildui
@Component public class GatewayDirector { @Resource(name = "VerificationBuild") private GatewayBuild gatewayBuild; /** * 鏈接建造者 * @param ctx * @param ipAddress * @param response * @param request */ public void direcot(RequestContext ctx, String ipAddress, HttpServletResponse response, HttpServletRequest request){ // 1.黑名單 Boolean boolBlackBlock = gatewayBuild.blackBlock(ctx, ipAddress, response); if(!boolBlackBlock){ return; } // 2.參數驗證 Boolean boolParamsValidate = gatewayBuild.paramsValidate(ctx, ipAddress, request); if(!boolParamsValidate){ return; } // 3.api權限控制 Boolean boolApiAuthorize = gatewayBuild.apiAuthorize(ctx, request); if(!boolApiAuthorize){ return; } } }
四、網關過濾器中調用spa
@Override public Object run() throws ZuulException { // 設計模式一: 基於建造者模式封裝 RequestContext ctx = RequestContext.getCurrentContext(); // 1.獲取請求對象 HttpServletRequest request = ctx.getRequest(); // 2.獲取響應對象 HttpServletResponse response = ctx.getResponse(); // 3.獲取客戶端真實ip地址 String ipAddr = IpUtil.getIpAddr(request); if (StringUtils.isEmpty(ipAddr)) { resultError(ctx, "未可以獲取到ip地址"); } // 4.基於建造者模式封裝: 進行請求限制 gatewayDirector.direcot(ctx,ipAddr,response,request); return null; }