From 73188b46b78223c5d075b2cb9444a87efec192f0 Mon Sep 17 00:00:00 2001 From: "tao.zhang" Date: Fri, 8 Nov 2019 22:27:59 +0800 Subject: [PATCH] Fix the bug that the Zuul adapter does not exit the entry with parameters (#1148) --- .../gateway/zuul/filters/EntryHolder.java | 41 +++++++++++++++++++ .../zuul/filters/SentinelEntryUtils.java | 29 +++++++------ .../zuul/filters/SentinelZuulPreFilter.java | 17 ++++---- 3 files changed, 67 insertions(+), 20 deletions(-) create mode 100644 sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/EntryHolder.java diff --git a/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/EntryHolder.java b/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/EntryHolder.java new file mode 100644 index 00000000..c67708b5 --- /dev/null +++ b/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/EntryHolder.java @@ -0,0 +1,41 @@ +/* + * Copyright 1999-2019 Alibaba Group Holding Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.alibaba.csp.sentinel.adapter.gateway.zuul.filters; + +import com.alibaba.csp.sentinel.Entry; + +/** + * @author wavesZh + */ +class EntryHolder { + + final private Entry entry; + + final private Object[] params; + + public EntryHolder(Entry entry, Object[] params) { + this.entry = entry; + this.params = params; + } + + public Entry getEntry() { + return entry; + } + + public Object[] getParams() { + return params; + } +} diff --git a/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelEntryUtils.java b/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelEntryUtils.java index 8c93a1b7..48e91e38 100644 --- a/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelEntryUtils.java +++ b/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelEntryUtils.java @@ -17,7 +17,7 @@ package com.alibaba.csp.sentinel.adapter.gateway.zuul.filters; import java.util.Deque; -import com.alibaba.csp.sentinel.AsyncEntry; +import com.alibaba.csp.sentinel.Entry; import com.alibaba.csp.sentinel.Tracer; import com.alibaba.csp.sentinel.adapter.gateway.zuul.constants.ZuulConstant; import com.alibaba.csp.sentinel.context.ContextUtil; @@ -34,11 +34,11 @@ final class SentinelEntryUtils { static void tryExitFromCurrentContext() { RequestContext ctx = RequestContext.getCurrentContext(); if (ctx.containsKey(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY)) { - Deque asyncEntries = (Deque) ctx.get(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY); - AsyncEntry entry; - while (!asyncEntries.isEmpty()) { - entry = asyncEntries.pop(); - entry.exit(); + Deque holders = (Deque) ctx.get(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY); + EntryHolder holder; + while (!holders.isEmpty()) { + holder = holders.pop(); + exit(holder); } ctx.remove(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY); } @@ -50,17 +50,22 @@ final class SentinelEntryUtils { static void tryTraceExceptionThenExitFromCurrentContext(Throwable t) { RequestContext ctx = RequestContext.getCurrentContext(); if (ctx.containsKey(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY)) { - Deque asyncEntries = (Deque) ctx.get(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY); - AsyncEntry entry; - while (!asyncEntries.isEmpty()) { - entry = asyncEntries.pop(); - Tracer.traceEntry(t, entry); - entry.exit(); + Deque holders = (Deque) ctx.get(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY); + EntryHolder holder; + while (!holders.isEmpty()) { + holder = holders.pop(); + Tracer.traceEntry(t, holder.getEntry()); + exit(holder); } ctx.remove(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY); } ContextUtil.exit(); } + static void exit(EntryHolder holder) { + Entry entry = holder.getEntry(); + entry.exit(1, holder.getParams()); + } + private SentinelEntryUtils() {} } diff --git a/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelZuulPreFilter.java b/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelZuulPreFilter.java index 6887e1ab..649ffa19 100644 --- a/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelZuulPreFilter.java +++ b/sentinel-adapter/sentinel-zuul-adapter/src/main/java/com/alibaba/csp/sentinel/adapter/gateway/zuul/filters/SentinelZuulPreFilter.java @@ -89,7 +89,7 @@ public class SentinelZuulPreFilter extends ZuulFilter { } private void doSentinelEntry(String resourceName, final int resType, RequestContext requestContext, - Deque asyncEntries) throws BlockException { + Deque holders) throws BlockException { Object[] params = paramParser.parseParameterFor(resourceName, requestContext, new Predicate() { @Override @@ -98,8 +98,9 @@ public class SentinelZuulPreFilter extends ZuulFilter { } }); AsyncEntry entry = SphU.asyncEntry(resourceName, ResourceTypeConstants.COMMON_API_GATEWAY, - EntryType.IN, params); - asyncEntries.push(entry); + EntryType.IN, params); + EntryHolder holder = new EntryHolder(entry, params); + holders.push(holder); } @Override @@ -108,12 +109,12 @@ public class SentinelZuulPreFilter extends ZuulFilter { String origin = parseOrigin(ctx.getRequest()); String routeId = (String)ctx.get(ZuulConstant.PROXY_ID_KEY); - Deque asyncEntries = new ArrayDeque<>(); + Deque holders = new ArrayDeque<>(); String fallBackRoute = routeId; try { if (StringUtil.isNotBlank(routeId)) { ContextUtil.enter(GATEWAY_CONTEXT_ROUTE_PREFIX + routeId, origin); - doSentinelEntry(routeId, RESOURCE_MODE_ROUTE_ID, ctx, asyncEntries); + doSentinelEntry(routeId, RESOURCE_MODE_ROUTE_ID, ctx, holders); } Set matchingApis = pickMatchingApiDefinitions(ctx); @@ -122,7 +123,7 @@ public class SentinelZuulPreFilter extends ZuulFilter { } for (String apiName : matchingApis) { fallBackRoute = apiName; - doSentinelEntry(apiName, RESOURCE_MODE_CUSTOM_API_NAME, ctx, asyncEntries); + doSentinelEntry(apiName, RESOURCE_MODE_CUSTOM_API_NAME, ctx, holders); } } catch (BlockException ex) { ZuulBlockFallbackProvider zuulBlockFallbackProvider = ZuulBlockFallbackManager.getFallbackProvider( @@ -140,8 +141,8 @@ public class SentinelZuulPreFilter extends ZuulFilter { } finally { // We don't exit the entry here. We need to exit the entries in post filter to record Rt correctly. // So here the entries will be carried in the request context. - if (!asyncEntries.isEmpty()) { - ctx.put(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY, asyncEntries); + if (!holders.isEmpty()) { + ctx.put(ZuulConstant.ZUUL_CTX_SENTINEL_ENTRIES_KEY, holders); } } return null;