Skip to content

Commit 25381b9

Browse files
authored
[DROOLS-7576] Add benchmarks for secondary super cache issue (#270)
* [DROOLS-7576] Add benchmarks for secondary super cache issue - ConcurrentUpdateRightTupleBenchmark calls RightTupleImpl.getTupleSink() a lot - ConcurrentUpdateLeftTupleBenchmark calls LeftTuple.getTupleSink() a lot * - add comment
1 parent 0ddde0a commit 25381b9

File tree

5 files changed

+318
-1
lines changed

5 files changed

+318
-1
lines changed

drools-benchmarks-parent/drools-benchmarks-common/src/main/java/org/drools/benchmarks/common/model/A.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,4 +29,14 @@ public A(final int value) {
2929
public A(final long id, final int value) {
3030
super(id, value);
3131
}
32+
33+
private int value2;
34+
35+
public int getValue2() {
36+
return value2;
37+
}
38+
39+
public void setValue2(int value2) {
40+
this.value2 = value2;
41+
}
3242
}

drools-benchmarks-parent/drools-benchmarks-common/src/main/java/org/drools/benchmarks/common/model/B.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,4 +29,14 @@ public B(final int value) {
2929
public B(final long id, final int value) {
3030
super(id, value);
3131
}
32+
33+
private int value2;
34+
35+
public int getValue2() {
36+
return value2;
37+
}
38+
39+
public void setValue2(int value2) {
40+
this.value2 = value2;
41+
}
3242
}

drools-benchmarks-parent/drools-benchmarks-common/src/main/java/org/drools/benchmarks/common/providers/RulesWithJoinsProvider.java

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,8 @@ public class RulesWithJoinsProvider implements DRLProvider {
3636
private String rootConstraintValueOperator = ">";
3737
private String joinConstraintValueOperator = ">";
3838

39+
private boolean withNot = false;
40+
3941
public RulesWithJoinsProvider() { }
4042

4143
public RulesWithJoinsProvider(final int numberOfJoins, final boolean withCep, final boolean withImports ) {
@@ -96,6 +98,11 @@ public RulesWithJoinsProvider withGeneratedConsequence(boolean withGeneratedCons
9698
return this;
9799
}
98100

101+
public RulesWithJoinsProvider withNot(boolean withNot) {
102+
this.withNot = withNot;
103+
return this;
104+
}
105+
99106
public RulesWithJoinsProvider withPrioritizedBySalience(boolean prioritizedBySalience) {
100107
this.prioritizedBySalience = prioritizedBySalience;
101108
return this;
@@ -170,7 +177,13 @@ private String getJoinConstraintsCep(int index) {
170177
}
171178

172179
private String getJoinConstraints(int index) {
173-
return " $" + (char)('b'+index) + " : " + (char)('B'+index) + "( value " + joinConstraintValueOperator + " $" + (char)('a'+index) + ".value )\n";
180+
String pattern = " $" + (char)('b'+index) + " : " + (char)('B'+index) + "( value " + joinConstraintValueOperator + " $" + (char)('a'+index) + ".value )\n";
181+
if (withNot) {
182+
String notPattern = " not " + (char)('B'+index) + "( value < $" + (char)('a'+index) + ".value )\n";
183+
return notPattern + pattern;
184+
} else {
185+
return pattern;
186+
}
174187
}
175188

176189
private String generateConsequence() {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,142 @@
1+
/*
2+
* Copyright 2023 Red Hat, Inc. and/or its affiliates.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package org.drools.benchmarks.concurrent;
18+
19+
import java.util.ArrayList;
20+
import java.util.List;
21+
import java.util.concurrent.ExecutorService;
22+
import java.util.concurrent.Executors;
23+
import java.util.concurrent.TimeUnit;
24+
25+
import org.drools.benchmarks.common.AbstractBenchmark;
26+
import org.drools.benchmarks.common.model.A;
27+
import org.drools.benchmarks.common.model.B;
28+
import org.drools.benchmarks.common.model.C;
29+
import org.drools.benchmarks.common.model.D;
30+
import org.drools.benchmarks.common.providers.RulesWithJoinsProvider;
31+
import org.drools.benchmarks.common.util.BuildtimeUtil;
32+
import org.drools.benchmarks.common.util.RuntimeUtil;
33+
import org.drools.kiesession.session.StatefulKnowledgeSessionImpl;
34+
import org.kie.api.conf.EventProcessingOption;
35+
import org.kie.api.runtime.KieSession;
36+
import org.kie.internal.conf.ParallelExecutionOption;
37+
import org.openjdk.jmh.annotations.Benchmark;
38+
import org.openjdk.jmh.annotations.Level;
39+
import org.openjdk.jmh.annotations.Measurement;
40+
import org.openjdk.jmh.annotations.Param;
41+
import org.openjdk.jmh.annotations.Setup;
42+
import org.openjdk.jmh.annotations.TearDown;
43+
import org.openjdk.jmh.annotations.Warmup;
44+
45+
@Warmup(iterations = 20)
46+
@Measurement(iterations = 20)
47+
public class ConcurrentUpdateLeftTupleBenchmark extends AbstractBenchmark {
48+
49+
@Param({"32"})
50+
private int rulesNr;
51+
52+
@Param({"15"})
53+
private int factsNr;
54+
55+
@Param({"3"})
56+
private int joinsNr;
57+
58+
private static final int SESSIONS_NR = 20;
59+
60+
private List<KieSession> kieSessions = new ArrayList<>(); // Do not use kieSession in AbstractBenchmark
61+
62+
@Setup
63+
public void setupKieBase() {
64+
final RulesWithJoinsProvider drlProvider = new RulesWithJoinsProvider(joinsNr, false, true)
65+
.withNot(true)
66+
.withGeneratedConsequence(false)
67+
.withConsequence(" $a.setValue2($a.getValue2() + 1);\n" +
68+
" update($a);\n"); // this update triggers LeftInputAdapterNode.modifyObject -> LeftTuple.getTupleSink
69+
//System.out.println(drlProvider.getDrl(rulesNr));
70+
kieBase = BuildtimeUtil.createKieBaseFromDrl(drlProvider.getDrl(rulesNr),
71+
ParallelExecutionOption.SEQUENTIAL,
72+
EventProcessingOption.CLOUD);
73+
//ReteDumper.dumpRete(kieBase);
74+
}
75+
76+
@Setup(Level.Iteration)
77+
@Override
78+
public void setup() {
79+
for (int n = 0; n < SESSIONS_NR; n++) {
80+
StatefulKnowledgeSessionImpl session = (StatefulKnowledgeSessionImpl) RuntimeUtil.createKieSession(kieBase);
81+
A a = new A(rulesNr + 1);
82+
83+
session.insert(a);
84+
85+
for (int i = 0; i < factsNr; i++) {
86+
87+
session.insert(new B(rulesNr + i + 3));
88+
if (joinsNr > 1) {
89+
session.insert(new C(rulesNr + factsNr + i + 3));
90+
}
91+
if (joinsNr > 2) {
92+
session.insert(new D(rulesNr + factsNr * 2 + i + 3));
93+
}
94+
}
95+
kieSessions.add(session);
96+
}
97+
}
98+
99+
@TearDown(Level.Iteration)
100+
public void tearDoneIter() {
101+
for (int n = 0; n < SESSIONS_NR; n++) {
102+
kieSessions.get(n).dispose();
103+
}
104+
kieSessions.clear();
105+
}
106+
107+
@Benchmark
108+
public int test() {
109+
ExecutorService executor = Executors.newFixedThreadPool(SESSIONS_NR);
110+
111+
for (int n = 0; n < SESSIONS_NR; n++) {
112+
final int index = n;
113+
executor.execute(new Runnable() {
114+
115+
public void run() {
116+
int fired = kieSessions.get(index).fireAllRules();
117+
// System.out.println(fired);
118+
}
119+
});
120+
}
121+
122+
executor.shutdown();
123+
try {
124+
executor.awaitTermination(300, TimeUnit.SECONDS);
125+
} catch (InterruptedException e) {
126+
throw new RuntimeException(e);
127+
}
128+
return kieSessions.size();
129+
}
130+
131+
public static void main(String[] args) {
132+
ConcurrentUpdateLeftTupleBenchmark benchmark = new ConcurrentUpdateLeftTupleBenchmark();
133+
134+
benchmark.rulesNr = 32;
135+
benchmark.factsNr = 15;
136+
benchmark.joinsNr = 3;
137+
138+
benchmark.setupKieBase();
139+
benchmark.setup();
140+
benchmark.test();
141+
}
142+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,142 @@
1+
/*
2+
* Copyright 2023 Red Hat, Inc. and/or its affiliates.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package org.drools.benchmarks.concurrent;
18+
19+
import java.util.ArrayList;
20+
import java.util.List;
21+
import java.util.concurrent.ExecutorService;
22+
import java.util.concurrent.Executors;
23+
import java.util.concurrent.TimeUnit;
24+
25+
import org.drools.benchmarks.common.AbstractBenchmark;
26+
import org.drools.benchmarks.common.model.A;
27+
import org.drools.benchmarks.common.model.B;
28+
import org.drools.benchmarks.common.model.C;
29+
import org.drools.benchmarks.common.model.D;
30+
import org.drools.benchmarks.common.providers.RulesWithJoinsProvider;
31+
import org.drools.benchmarks.common.util.BuildtimeUtil;
32+
import org.drools.benchmarks.common.util.RuntimeUtil;
33+
import org.drools.kiesession.session.StatefulKnowledgeSessionImpl;
34+
import org.kie.api.conf.EventProcessingOption;
35+
import org.kie.api.runtime.KieSession;
36+
import org.kie.internal.conf.ParallelExecutionOption;
37+
import org.openjdk.jmh.annotations.Benchmark;
38+
import org.openjdk.jmh.annotations.Level;
39+
import org.openjdk.jmh.annotations.Measurement;
40+
import org.openjdk.jmh.annotations.Param;
41+
import org.openjdk.jmh.annotations.Setup;
42+
import org.openjdk.jmh.annotations.TearDown;
43+
import org.openjdk.jmh.annotations.Warmup;
44+
45+
@Warmup(iterations = 20)
46+
@Measurement(iterations = 20)
47+
public class ConcurrentUpdateRightTupleBenchmark extends AbstractBenchmark {
48+
49+
@Param({"32"})
50+
private int rulesNr;
51+
52+
@Param({"15"})
53+
private int factsNr;
54+
55+
@Param({"3"})
56+
private int joinsNr;
57+
58+
private static final int SESSIONS_NR = 20;
59+
60+
private List<KieSession> kieSessions = new ArrayList<>(); // Do not use kieSession in AbstractBenchmark
61+
62+
@Setup
63+
public void setupKieBase() {
64+
final RulesWithJoinsProvider drlProvider = new RulesWithJoinsProvider(joinsNr, false, true)
65+
.withNot(true)
66+
.withGeneratedConsequence(false)
67+
.withConsequence(" $b.setValue2($b.getValue2() + 1);\n" +
68+
" update($b);\n"); // this update triggers BetaNode.modifyObject -> RightTupleImpl.getTupleSink
69+
//System.out.println(drlProvider.getDrl(rulesNr));
70+
kieBase = BuildtimeUtil.createKieBaseFromDrl(drlProvider.getDrl(rulesNr),
71+
ParallelExecutionOption.SEQUENTIAL,
72+
EventProcessingOption.CLOUD);
73+
//ReteDumper.dumpRete(kieBase);
74+
}
75+
76+
@Setup(Level.Iteration)
77+
@Override
78+
public void setup() {
79+
for (int n = 0; n < SESSIONS_NR; n++) {
80+
StatefulKnowledgeSessionImpl session = (StatefulKnowledgeSessionImpl) RuntimeUtil.createKieSession(kieBase);
81+
A a = new A(rulesNr + 1);
82+
83+
session.insert(a);
84+
85+
for (int i = 0; i < factsNr; i++) {
86+
87+
session.insert(new B(rulesNr + i + 3));
88+
if (joinsNr > 1) {
89+
session.insert(new C(rulesNr + factsNr + i + 3));
90+
}
91+
if (joinsNr > 2) {
92+
session.insert(new D(rulesNr + factsNr * 2 + i + 3));
93+
}
94+
}
95+
kieSessions.add(session);
96+
}
97+
}
98+
99+
@TearDown(Level.Iteration)
100+
public void tearDoneIter() {
101+
for (int n = 0; n < SESSIONS_NR; n++) {
102+
kieSessions.get(n).dispose();
103+
}
104+
kieSessions.clear();
105+
}
106+
107+
@Benchmark
108+
public int test() {
109+
ExecutorService executor = Executors.newFixedThreadPool(SESSIONS_NR);
110+
111+
for (int n = 0; n < SESSIONS_NR; n++) {
112+
final int index = n;
113+
executor.execute(new Runnable() {
114+
115+
public void run() {
116+
int fired = kieSessions.get(index).fireAllRules();
117+
// System.out.println(fired);
118+
}
119+
});
120+
}
121+
122+
executor.shutdown();
123+
try {
124+
executor.awaitTermination(300, TimeUnit.SECONDS);
125+
} catch (InterruptedException e) {
126+
throw new RuntimeException(e);
127+
}
128+
return kieSessions.size();
129+
}
130+
131+
public static void main(String[] args) {
132+
ConcurrentUpdateRightTupleBenchmark benchmark = new ConcurrentUpdateRightTupleBenchmark();
133+
134+
benchmark.rulesNr = 32;
135+
benchmark.factsNr = 15;
136+
benchmark.joinsNr = 3;
137+
138+
benchmark.setupKieBase();
139+
benchmark.setup();
140+
benchmark.test();
141+
}
142+
}

0 commit comments

Comments
 (0)