This is an automated email from the ASF dual-hosted git repository.

Aias00 pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/shenyu.git


The following commit(s) were added to refs/heads/master by this push:
     new ff54cd3e31 [ISSUE #7978] Skip disabled rules in the full-flow selector 
path (#7983)
ff54cd3e31 is described below

commit ff54cd3e3194ba6f2fa8e72911dc12aa88329577
Author: imDwAaY <[email protected]>
AuthorDate: Fri Oct 23 11:18:26 2026 +0800

    [ISSUE #7978] Skip disabled rules in the full-flow selector path (#7983)
    
    A FULL_FLOW selector took the highest-sort rule unconditionally and called
    doExecute, bypassing the enabled check that filterRule applies on the
    ordinary matching path. BaseDataCache keeps disabled rules in its snapshot,
    so a disabled rule could still be executed.
    
    Walk the rules from the end and take the last rule whose enabled flag is
    Boolean.TRUE. When no enabled rule remains, delegate through
    handleRuleIfNull, consistent with the ordinary path. Ordering among enabled
    rules and condition evaluation for full-flow rules are unchanged.
    
    Covered by unit tests for a disabled last rule, an all-disabled list, and
    multiple enabled rules.
---
 .../shenyu/plugin/base/AbstractShenyuPlugin.java   | 16 ++++++-
 .../plugin/base/AbstractShenyuPluginTest.java      | 54 ++++++++++++++++++++++
 2 files changed, 68 insertions(+), 2 deletions(-)

diff --git 
a/shenyu-plugin/shenyu-plugin-base/src/main/java/org/apache/shenyu/plugin/base/AbstractShenyuPlugin.java
 
b/shenyu-plugin/shenyu-plugin-base/src/main/java/org/apache/shenyu/plugin/base/AbstractShenyuPlugin.java
index 1e2957b504..77c5b2cefe 100644
--- 
a/shenyu-plugin/shenyu-plugin-base/src/main/java/org/apache/shenyu/plugin/base/AbstractShenyuPlugin.java
+++ 
b/shenyu-plugin/shenyu-plugin-base/src/main/java/org/apache/shenyu/plugin/base/AbstractShenyuPlugin.java
@@ -110,8 +110,10 @@ public abstract class AbstractShenyuPlugin implements 
ShenyuPlugin {
             return handleRuleIfNull(pluginName, exchange, chain);
         }
         if (selectorData.getType() == SelectorTypeEnum.FULL_FLOW.getCode()) {
-            //get last
-            RuleData rule = rules.get(rules.size() - 1);
+            RuleData rule = lastEnabledRule(rules);
+            if (Objects.isNull(rule)) {
+                return handleRuleIfNull(pluginName, exchange, chain);
+            }
             printLog(rule, pluginName);
             return doExecute(exchange, chain, selectorData, rule);
         }
@@ -131,6 +133,16 @@ public abstract class AbstractShenyuPlugin implements 
ShenyuPlugin {
         printLog(ruleData, pluginName);
         return doExecute(exchange, chain, selectorData, ruleData);
     }
+
+    private static RuleData lastEnabledRule(final List<RuleData> rules) {
+        for (int i = rules.size() - 1; i >= 0; i--) {
+            RuleData rule = rules.get(i);
+            if (Boolean.TRUE.equals(rule.getEnabled())) {
+                return rule;
+            }
+        }
+        return null;
+    }
     
     protected String getRawPath(final ServerWebExchange exchange) {
         return exchange.getRequest().getURI().getRawPath();
diff --git 
a/shenyu-plugin/shenyu-plugin-base/src/test/java/org/apache/shenyu/plugin/base/AbstractShenyuPluginTest.java
 
b/shenyu-plugin/shenyu-plugin-base/src/test/java/org/apache/shenyu/plugin/base/AbstractShenyuPluginTest.java
index ce7c74adeb..1f0ed5c5cd 100644
--- 
a/shenyu-plugin/shenyu-plugin-base/src/test/java/org/apache/shenyu/plugin/base/AbstractShenyuPluginTest.java
+++ 
b/shenyu-plugin/shenyu-plugin-base/src/test/java/org/apache/shenyu/plugin/base/AbstractShenyuPluginTest.java
@@ -45,7 +45,9 @@ import java.util.stream.Collectors;
 
 import static org.junit.jupiter.api.Assertions.assertEquals;
 import static org.junit.jupiter.api.Assertions.assertTrue;
+import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.never;
 import static org.mockito.Mockito.spy;
 import static org.mockito.Mockito.verify;
 import static org.mockito.Mockito.when;
@@ -260,6 +262,58 @@ public final class AbstractShenyuPluginTest {
         verify(testShenyuPlugin).doExecute(exchange, shenyuPluginChain, 
selectorData, ruleData);
     }
 
+    @Test
+    public void executeRuleFullWithMultipleEnabledRulesTest() {
+        this.selectorData.setType(SelectorTypeEnum.FULL_FLOW.getCode());
+        this.selectorData.setLogged(true);
+        RuleData secondRule = RuleData.builder()
+                .id("2")
+                .pluginName("SHENYU")
+                .selectorId("1")
+                .enabled(true)
+                .logged(true)
+                .sort(2).build();
+        BaseDataCache.getInstance().cachePluginData(pluginData);
+        BaseDataCache.getInstance().cacheSelectData(selectorData);
+        BaseDataCache.getInstance().cacheRuleData(ruleData);
+        BaseDataCache.getInstance().cacheRuleData(secondRule);
+        StepVerifier.create(testShenyuPlugin.execute(exchange, 
shenyuPluginChain)).expectSubscription().verifyComplete();
+        verify(testShenyuPlugin).doExecute(exchange, shenyuPluginChain, 
selectorData, secondRule);
+        verify(testShenyuPlugin, never()).doExecute(exchange, 
shenyuPluginChain, selectorData, ruleData);
+    }
+
+    @Test
+    public void executeRuleFullWithLastRuleDisabledTest() {
+        this.selectorData.setType(SelectorTypeEnum.FULL_FLOW.getCode());
+        this.selectorData.setLogged(true);
+        RuleData disabledRule = RuleData.builder()
+                .id("2")
+                .pluginName("SHENYU")
+                .selectorId("1")
+                .enabled(false)
+                .logged(true)
+                .sort(2).build();
+        BaseDataCache.getInstance().cachePluginData(pluginData);
+        BaseDataCache.getInstance().cacheSelectData(selectorData);
+        BaseDataCache.getInstance().cacheRuleData(ruleData);
+        BaseDataCache.getInstance().cacheRuleData(disabledRule);
+        StepVerifier.create(testShenyuPlugin.execute(exchange, 
shenyuPluginChain)).expectSubscription().verifyComplete();
+        verify(testShenyuPlugin).doExecute(exchange, shenyuPluginChain, 
selectorData, ruleData);
+    }
+
+    @Test
+    public void executeRuleFullWithAllRulesDisabledTest() {
+        this.selectorData.setType(SelectorTypeEnum.FULL_FLOW.getCode());
+        this.selectorData.setLogged(true);
+        this.ruleData.setEnabled(false);
+        BaseDataCache.getInstance().cachePluginData(pluginData);
+        BaseDataCache.getInstance().cacheSelectData(selectorData);
+        BaseDataCache.getInstance().cacheRuleData(ruleData);
+        StepVerifier.create(testShenyuPlugin.execute(exchange, 
shenyuPluginChain)).expectSubscription().verifyComplete();
+        verify(shenyuPluginChain).execute(exchange);
+        verify(testShenyuPlugin, never()).doExecute(any(), any(), any(), 
any());
+    }
+
     @Test
     public void defaultStrategySelectorMatchShouldNotLogWhenLoggingDisabled() {
         List<ConditionData> conditionDataList = 
Collections.singletonList(conditionData);

Reply via email to