aboutsummaryrefslogtreecommitdiffstats
path: root/subprojects/store-query/src/test/java/tools/refinery/store/query/rewriter/InputParameterResolverTest.java
diff options
context:
space:
mode:
Diffstat (limited to 'subprojects/store-query/src/test/java/tools/refinery/store/query/rewriter/InputParameterResolverTest.java')
-rw-r--r--subprojects/store-query/src/test/java/tools/refinery/store/query/rewriter/InputParameterResolverTest.java228
1 files changed, 228 insertions, 0 deletions
diff --git a/subprojects/store-query/src/test/java/tools/refinery/store/query/rewriter/InputParameterResolverTest.java b/subprojects/store-query/src/test/java/tools/refinery/store/query/rewriter/InputParameterResolverTest.java
new file mode 100644
index 00000000..ef0077e4
--- /dev/null
+++ b/subprojects/store-query/src/test/java/tools/refinery/store/query/rewriter/InputParameterResolverTest.java
@@ -0,0 +1,228 @@
1/*
2 * SPDX-FileCopyrightText: 2023 The Refinery Authors <https://refinery.tools/>
3 *
4 * SPDX-License-Identifier: EPL-2.0
5 */
6package tools.refinery.store.query.rewriter;
7
8import org.junit.jupiter.api.BeforeEach;
9import org.junit.jupiter.api.Test;
10import tools.refinery.store.query.dnf.Dnf;
11import tools.refinery.store.query.dnf.Query;
12import tools.refinery.store.query.term.ParameterDirection;
13import tools.refinery.store.query.term.Variable;
14import tools.refinery.store.query.view.AnySymbolView;
15import tools.refinery.store.query.view.KeyOnlyView;
16import tools.refinery.store.representation.Symbol;
17
18import java.util.List;
19
20import static org.hamcrest.MatcherAssert.assertThat;
21import static org.hamcrest.Matchers.is;
22import static tools.refinery.store.query.literal.Literals.not;
23import static tools.refinery.store.query.tests.QueryMatchers.structurallyEqualTo;
24
25class InputParameterResolverTest {
26 private final static Symbol<Boolean> person = Symbol.of("Person", 1);
27 private final static Symbol<Boolean> friend = Symbol.of("friend", 2);
28 private final static AnySymbolView personView = new KeyOnlyView<>(person);
29 private final static AnySymbolView friendView = new KeyOnlyView<>(friend);
30
31 private InputParameterResolver sut;
32
33 @BeforeEach
34 void beforeEach() {
35 sut = new InputParameterResolver();
36 }
37
38 @Test
39 void inlineSingleClauseTest() {
40 var dnf = Dnf.of("SubQuery", builder -> {
41 var x = builder.parameter("x", ParameterDirection.OUT);
42 builder.clause(friendView.call(x, Variable.of()));
43 });
44 var query = Query.of("Actual", (builder, x) -> builder.clause(
45 dnf.call(x),
46 personView.call(x)
47 ));
48
49 var actual = sut.rewrite(query);
50
51 var expected = Query.of("Expected", (builder, x) -> builder.clause(
52 friendView.call(x, Variable.of()),
53 personView.call(x)
54 ));
55
56 assertThat(actual.getDnf(), structurallyEqualTo(expected.getDnf()));
57 }
58
59 @Test
60 void inlineSingleClauseWIthInputTest() {
61 var dnf = Dnf.of("SubQuery", builder -> {
62 var x = builder.parameter("x", ParameterDirection.IN);
63 builder.clause(not(friendView.call(x, Variable.of())));
64 });
65 var query = Query.of("Actual", (builder, x) -> builder.clause(
66 dnf.call(x),
67 personView.call(x)
68 ));
69
70 var actual = sut.rewrite(query);
71
72 var expected = Query.of("Expected", (builder, x) -> builder.clause(
73 personView.call(x),
74 not(friendView.call(x, Variable.of()))
75 ));
76
77 assertThat(actual.getDnf(), structurallyEqualTo(expected.getDnf()));
78 }
79
80 @Test
81 void singleLiteralDemandSetTest() {
82 var dnf = Dnf.of("SubQuery", builder -> {
83 var x = builder.parameter("x", ParameterDirection.IN);
84 builder.clause(not(friendView.call(x, Variable.of())));
85 builder.clause(not(friendView.call(Variable.of(), x)));
86 });
87 var query = Query.of("Actual", (builder, x) -> builder.clause(
88 dnf.call(x),
89 personView.call(x)
90 ));
91
92 var actual = sut.rewrite(query);
93
94 var expectedSubQuery = Dnf.of("ExpectedSubQuery", builder -> {
95 var x = builder.parameter("x", ParameterDirection.OUT);
96 builder.clause(
97 personView.call(x),
98 not(friendView.call(x, Variable.of()))
99 );
100 builder.clause(
101 personView.call(x),
102 not(friendView.call(Variable.of(), x))
103 );
104 });
105 var expected = Query.of("Expected", (builder, x) -> builder.clause(
106 personView.call(x),
107 expectedSubQuery.call(x)
108 ));
109
110 assertThat(actual.getDnf(), structurallyEqualTo(expected.getDnf()));
111 }
112
113 @Test
114 void multipleLiteralDemandSetTest() {
115 var dnf = Dnf.of("SubQuery", builder -> {
116 var x = builder.parameter("x", ParameterDirection.IN);
117 var y = builder.parameter("y", ParameterDirection.IN);
118 builder.clause(not(friendView.call(x, y)));
119 builder.clause(not(friendView.call(y, x)));
120 });
121 var query = Query.of("Actual", (builder, p1) -> builder.clause(p2 -> List.of(
122 not(dnf.call(p1, p2)),
123 personView.call(p1),
124 personView.call(p2)
125 )));
126
127 var actual = sut.rewrite(query);
128
129 var context = Dnf.of("Context", builder -> {
130 var x = builder.parameter("x", ParameterDirection.OUT);
131 var y = builder.parameter("y", ParameterDirection.OUT);
132 builder.clause(
133 personView.call(x),
134 personView.call(y)
135 );
136 });
137 var expectedSubQuery = Dnf.of("ExpectedSubQuery", builder -> {
138 var x = builder.parameter("x", ParameterDirection.OUT);
139 var y = builder.parameter("x", ParameterDirection.OUT);
140 builder.clause(
141 context.call(x, y),
142 not(friendView.call(x, y))
143 );
144 builder.clause(
145 context.call(x, y),
146 not(friendView.call(y, x))
147 );
148 });
149 var expected = Query.of("Expected", (builder, p1) -> builder.clause(p2 -> List.of(
150 context.call(p1, p2),
151 not(expectedSubQuery.call(p1, p2))
152 )));
153
154 assertThat(actual.getDnf(), structurallyEqualTo(expected.getDnf()));
155 }
156
157 @Test
158 void multipleParameterDemandSetTest() {
159 var dnf = Dnf.of("SubQuery", builder -> {
160 var x = builder.parameter("x", ParameterDirection.IN);
161 var y = builder.parameter("y", ParameterDirection.IN);
162 builder.clause(not(friendView.call(x, y)));
163 builder.clause(not(friendView.call(y, x)));
164 });
165 var query = Query.of("Actual", (builder, p1) -> builder.clause(
166 not(dnf.call(p1, p1)),
167 personView.call(p1)
168 ));
169
170 var actual = sut.rewrite(query);
171
172 var expectedSubQuery = Dnf.of("ExpectedSubQuery", builder -> {
173 var x = builder.parameter("x", ParameterDirection.OUT);
174 var y = builder.parameter("y", ParameterDirection.OUT);
175 builder.clause(
176 y.isEquivalent(x),
177 personView.call(x),
178 not(friendView.call(x, x))
179 );
180 });
181 var expected = Query.of("Expected", (builder, p1) -> builder.clause(
182 personView.call(p1),
183 not(expectedSubQuery.call(p1, p1))
184 ));
185
186 assertThat(actual.getDnf(), structurallyEqualTo(expected.getDnf()));
187 }
188
189 @Test
190 void eliminateDoubleNegationTest() {
191 var dnf = Dnf.of("SubQuery", builder -> {
192 var x = builder.parameter("x", ParameterDirection.IN);
193 builder.clause(not(friendView.call(x, Variable.of())));
194 });
195 var query = Query.of("Actual", (builder, p1) -> builder.clause(
196 personView.call(p1),
197 not(dnf.call(p1))
198 ));
199
200 var actual = sut.rewrite(query);
201
202 var expected = Query.of("Actual", (builder, p1) -> builder.clause(
203 personView.call(p1),
204 friendView.call(p1, Variable.of())
205 ));
206
207 assertThat(actual.getDnf(), structurallyEqualTo(expected.getDnf()));
208 }
209
210 @Test
211 void identityWhenNoWorkToDoTest() {
212 var dnf = Dnf.of("SubQuery", builder -> {
213 var x = builder.parameter("x", ParameterDirection.OUT);
214 builder.clause(
215 personView.call(x),
216 not(friendView.call(x, Variable.of()))
217 );
218 });
219 var query = Query.of("Actual", (builder, p1) -> builder.clause(
220 personView.call(p1),
221 not(dnf.call(p1))
222 ));
223
224 var actual = sut.rewrite(query);
225
226 assertThat(actual, is(query));
227 }
228}