Skip to content

Commit 5ba51d5

Browse files
JerryChintaz
authored and
taz
committed
Apply volatile modifier for fields in FlowRuleManager while keep concurrency semantics intact (alibaba#2107)
- Revert alibaba#1783
1 parent 5f0a08b commit 5ba51d5

File tree

1 file changed

+17
-18
lines changed

1 file changed

+17
-18
lines changed

sentinel-core/src/main/java/com/alibaba/csp/sentinel/slots/block/flow/FlowRuleManager.java

+17-18
Original file line numberDiff line numberDiff line change
@@ -16,14 +16,12 @@
1616
package com.alibaba.csp.sentinel.slots.block.flow;
1717

1818
import java.util.ArrayList;
19-
import java.util.Collections;
19+
import java.util.HashMap;
2020
import java.util.List;
2121
import java.util.Map;
22-
import java.util.concurrent.ConcurrentHashMap;
2322
import java.util.concurrent.Executors;
2423
import java.util.concurrent.ScheduledExecutorService;
2524
import java.util.concurrent.TimeUnit;
26-
import java.util.concurrent.atomic.AtomicReference;
2725

2826
import com.alibaba.csp.sentinel.concurrent.NamedThreadFactory;
2927
import com.alibaba.csp.sentinel.config.SentinelConfig;
@@ -50,7 +48,7 @@
5048
*/
5149
public class FlowRuleManager {
5250

53-
private static final AtomicReference<Map<String, List<FlowRule>>> flowRules = new AtomicReference<Map<String, List<FlowRule>>>();
51+
private static volatile Map<String, List<FlowRule>> flowRules = new HashMap<>();
5452

5553
private static final FlowPropertyListener LISTENER = new FlowPropertyListener();
5654
private static SentinelProperty<List<FlowRule>> currentProperty = new DynamicSentinelProperty<List<FlowRule>>();
@@ -60,11 +58,10 @@ public class FlowRuleManager {
6058
new NamedThreadFactory("sentinel-metrics-record-task", true));
6159

6260
static {
63-
flowRules.set(Collections.<String, List<FlowRule>>emptyMap());
6461
currentProperty.addListener(LISTENER);
6562
startMetricTimerListener();
6663
}
67-
64+
6865
/**
6966
* <p> Start the MetricTimerListener
7067
* <ol>
@@ -79,12 +76,12 @@ private static void startMetricTimerListener() {
7976
if (flushInterval <= 0) {
8077
RecordLog.info("[FlowRuleManager] The MetricTimerListener isn't started. If you want to start it, "
8178
+ "please change the value(current: {}) of config({}) more than 0 to start it.", flushInterval,
82-
SentinelConfig.METRIC_FLUSH_INTERVAL);
79+
SentinelConfig.METRIC_FLUSH_INTERVAL);
8380
return;
8481
}
8582
SCHEDULER.scheduleAtFixedRate(new MetricTimerListener(), 0, flushInterval, TimeUnit.SECONDS);
8683
}
87-
84+
8885
/**
8986
* Listen to the {@link SentinelProperty} for {@link FlowRule}s. The property is the source of {@link FlowRule}s.
9087
* Flow rules can also be set by {@link #loadRules(List)} directly.
@@ -108,7 +105,7 @@ public static void register2Property(SentinelProperty<List<FlowRule>> property)
108105
*/
109106
public static List<FlowRule> getRules() {
110107
List<FlowRule> rules = new ArrayList<FlowRule>();
111-
for (Map.Entry<String, List<FlowRule>> entry : flowRules.get().entrySet()) {
108+
for (Map.Entry<String, List<FlowRule>> entry : flowRules.entrySet()) {
112109
rules.addAll(entry.getValue());
113110
}
114111
return rules;
@@ -124,19 +121,19 @@ public static void loadRules(List<FlowRule> rules) {
124121
}
125122

126123
static Map<String, List<FlowRule>> getFlowRuleMap() {
127-
return flowRules.get();
124+
return flowRules;
128125
}
129126

130127
public static boolean hasConfig(String resource) {
131-
return flowRules.get().containsKey(resource);
128+
return flowRules.containsKey(resource);
132129
}
133130

134131
public static boolean isOtherOrigin(String origin, String resourceName) {
135132
if (StringUtil.isEmpty(origin)) {
136133
return false;
137134
}
138135

139-
List<FlowRule> rules = flowRules.get().get(resourceName);
136+
List<FlowRule> rules = flowRules.get(resourceName);
140137

141138
if (rules != null) {
142139
for (FlowRule rule : rules) {
@@ -152,18 +149,20 @@ public static boolean isOtherOrigin(String origin, String resourceName) {
152149
private static final class FlowPropertyListener implements PropertyListener<List<FlowRule>> {
153150

154151
@Override
155-
public void configUpdate(List<FlowRule> value) {
152+
public synchronized void configUpdate(List<FlowRule> value) {
156153
Map<String, List<FlowRule>> rules = FlowRuleUtil.buildFlowRuleMap(value);
157-
//the rules was always not null, it's no need to check nullable
158-
//remove checking to avoid IDE warning
159-
flowRules.set(rules);
154+
if (rules != null) {
155+
flowRules = rules;
156+
}
160157
RecordLog.info("[FlowRuleManager] Flow rules received: {}", rules);
161158
}
162159

163160
@Override
164-
public void configLoad(List<FlowRule> conf) {
161+
public synchronized void configLoad(List<FlowRule> conf) {
165162
Map<String, List<FlowRule>> rules = FlowRuleUtil.buildFlowRuleMap(conf);
166-
flowRules.set(rules);
163+
if (rules != null) {
164+
flowRules = rules;
165+
}
167166
RecordLog.info("[FlowRuleManager] Flow rules loaded: {}", rules);
168167
}
169168
}

0 commit comments

Comments
 (0)