View Javadoc

1   package org.kuali.student.common.messagebuilder.impl;
2   
3   import java.util.ArrayList;
4   import java.util.List;
5   
6   import org.antlr.runtime.Token;
7   import org.antlr.runtime.tree.CommonTreeAdaptor;
8   import org.junit.Assert;
9   import org.junit.Before;
10  import org.junit.Test;
11  import org.kuali.student.common.messagebuilder.booleanmessage.ast.BooleanNode;
12  import org.kuali.student.common.messagebuilder.booleanmessage.ast.parsers.BooleanFunctionParser;
13  import org.kuali.student.common.messagebuilder.impl.BooleanOperators;
14  import org.kuali.student.common.messagebuilder.impl.exceptions.MessageBuilderException;
15  
16  public class SimpleBooleanMessageBuilderTest {
17  	private final static CommonTreeAdaptor adapter = new CommonTreeAdaptor();
18  	private SimpleBooleanMessageBuilder defaultMessageBuilder;
19  	private SimpleBooleanMessageBuilder configuredMessageBuilder;
20  
21  	@Before
22  	public void setUp() throws Exception {
23  		BooleanOperators bo = new BooleanOperators("AND", "OR");
24  		defaultMessageBuilder = new SimpleBooleanMessageBuilder(bo);
25  
26  		configuredMessageBuilder = new SimpleBooleanMessageBuilder(bo);
27  		configuredMessageBuilder.setIndentCharacter(32);
28  		configuredMessageBuilder.setIndentNumberOfSpaces(4);
29  		configuredMessageBuilder.setIndentString("    ");
30  		configuredMessageBuilder.setBooleanOperatorPrefix("\n");
31  		configuredMessageBuilder.setBooleanOperatorSuffix("\n");
32  	}
33  	
34  	@Test
35  	public void testBuildMessage_DefaultConfig_SingleAndNode() throws Exception {
36  		// Rule: A AND B
37  		Token and = adapter.createToken(BooleanFunctionParser.AND, "*");
38  		Token a = adapter.createToken(BooleanFunctionParser.ALPHA, "A");
39  		Token b = adapter.createToken(BooleanFunctionParser.ALPHA, "B");
40  		
41  		BooleanNode andNode = new BooleanNode(and);
42  		
43  		BooleanNode aNode = new BooleanNode(a);
44  		aNode.setParent(andNode);
45  		aNode.setNodeMessage("MATH101");
46  
47  		BooleanNode bNode = new BooleanNode(b);
48  		bNode.setParent(andNode);
49  		bNode.setNodeMessage("MATH201");
50  		
51  		andNode.addChild(aNode); // left node
52  		andNode.addChild(bNode); // right node
53  		
54  		String msg = defaultMessageBuilder.buildMessage(andNode);
55  		
56  		Assert.assertEquals("MATH101 AND MATH201", msg);
57  	}
58  
59  	@Test
60  	public void testBuildMessage_DefaultConfig_ForListOfNodes() throws Exception {
61  		// Rule: A AND (B OR C)
62  		Token and = adapter.createToken(BooleanFunctionParser.AND, "*");
63  		Token or = adapter.createToken(BooleanFunctionParser.OR, "+");
64  		Token a = adapter.createToken(BooleanFunctionParser.ALPHA, "A");
65  		Token b = adapter.createToken(BooleanFunctionParser.ALPHA, "B");
66  		Token c = adapter.createToken(BooleanFunctionParser.ALPHA, "C");
67  		
68  		// root node
69  		BooleanNode andNode = new BooleanNode(and);
70  		BooleanNode orNode = new BooleanNode(or);
71  		orNode.setParent(andNode);
72  		
73  		BooleanNode aNode = new BooleanNode(a);
74  		aNode.setParent(andNode);
75  		aNode.setNodeMessage("MATH101");
76  
77  		BooleanNode bNode = new BooleanNode(b);
78  		bNode.setParent(orNode);
79  		bNode.setNodeMessage("MATH201");
80  
81  		BooleanNode cNode = new BooleanNode(c);
82  		cNode.setParent(orNode);
83  		cNode.setNodeMessage("MATH301");
84  		
85  		orNode.addChild(bNode); // left node
86  		orNode.addChild(cNode); // right node
87  		andNode.addChild(aNode); // left node
88  		andNode.addChild(orNode); // right node
89  		
90  		// List of nodes order is important for building success message
91  		List<BooleanNode> list = new ArrayList<BooleanNode>();
92  		list.add(cNode);
93  		list.add(bNode);
94  		list.add(orNode);
95  		list.add(aNode);
96  		list.add(andNode);
97  
98  		defaultMessageBuilder.buildMessage(list);
99  
100 		Assert.assertEquals("MATH101 AND (MATH201 OR MATH301)", andNode.getNodeMessage());
101 	}
102 
103 	@Test
104 	public void testBuildMessage_ForSingleAndNode() throws Exception {
105 		// Rule: A AND B
106 		Token and = adapter.createToken(BooleanFunctionParser.AND, "*");
107 		Token a = adapter.createToken(BooleanFunctionParser.ALPHA, "A");
108 		Token b = adapter.createToken(BooleanFunctionParser.ALPHA, "B");
109 		
110 		BooleanNode andNode = new BooleanNode(and);
111 		
112 		BooleanNode aNode = new BooleanNode(a);
113 		aNode.setParent(andNode);
114 		aNode.setNodeMessage("MATH101");
115 
116 		BooleanNode bNode = new BooleanNode(b);
117 		bNode.setParent(andNode);
118 		bNode.setNodeMessage("MATH201");
119 		
120 		andNode.addChild(aNode); // left node
121 		andNode.addChild(bNode); // right node
122 		
123 		String msg = configuredMessageBuilder.buildMessage(andNode);
124 		
125 		Assert.assertEquals("    MATH101\nAND\n    MATH201", msg);
126 	}
127 
128 	@Test
129 	public void testBuildMessage_ForSingleOrNode() throws Exception {
130 		// Rule: A OR B
131 		Token and = adapter.createToken(BooleanFunctionParser.OR, "+");
132 		Token a = adapter.createToken(BooleanFunctionParser.ALPHA, "A");
133 		Token b = adapter.createToken(BooleanFunctionParser.ALPHA, "B");
134 		
135 		// root node
136 		BooleanNode andNode = new BooleanNode(and);
137 		
138 		BooleanNode aNode = new BooleanNode(a);
139 		aNode.setParent(andNode);
140 		aNode.setValue(Boolean.TRUE);
141 		aNode.setNodeMessage("MATH101");
142 
143 		BooleanNode bNode = new BooleanNode(b);
144 		bNode.setParent(andNode);
145 		bNode.setValue(Boolean.FALSE);
146 		bNode.setNodeMessage("MATH201");
147 		
148 		andNode.addChild(aNode); // left node
149 		andNode.addChild(bNode); // right node
150 		
151 		String msg = configuredMessageBuilder.buildMessage(andNode);
152 		
153 		Assert.assertEquals("    MATH101\nOR\n    MATH201", msg);
154 	}
155 
156 	@Test
157 	public void testBuildMessage_ForListOfNodes_Complex() throws Exception {
158 		// Rule: (A AND B) OR (C AND (D OR E))
159 		Token or1 = adapter.createToken(BooleanFunctionParser.OR, "+");
160 		Token or2 = adapter.createToken(BooleanFunctionParser.OR, "+");
161 		Token and1 = adapter.createToken(BooleanFunctionParser.AND, "*");
162 		Token and2 = adapter.createToken(BooleanFunctionParser.AND, "*");
163 		Token a = adapter.createToken(BooleanFunctionParser.ALPHA, "A");
164 		Token b = adapter.createToken(BooleanFunctionParser.ALPHA, "B");
165 		Token c = adapter.createToken(BooleanFunctionParser.ALPHA, "C");
166 		Token d = adapter.createToken(BooleanFunctionParser.ALPHA, "D");
167 		Token e = adapter.createToken(BooleanFunctionParser.ALPHA, "E");
168 		
169 		// root node
170 		BooleanNode orNode1 = new BooleanNode(or1);
171 
172 		BooleanNode andNode1 = new BooleanNode(and1);
173 		andNode1.setParent(orNode1);
174 
175 		BooleanNode andNode2 = new BooleanNode(and2);
176 		andNode2.setParent(orNode1);
177 		
178 		BooleanNode orNode2 = new BooleanNode(or2);
179 		orNode2.setParent(andNode2);
180 		
181 		BooleanNode aNode = new BooleanNode(a);
182 		aNode.setParent(andNode1);
183 		aNode.setNodeMessage("MATH101");
184 
185 		BooleanNode bNode = new BooleanNode(b);
186 		bNode.setParent(andNode1);
187 		bNode.setNodeMessage("MATH102");
188 
189 		BooleanNode cNode = new BooleanNode(c);
190 		cNode.setParent(andNode2);
191 		cNode.setNodeMessage("MATH201");
192 		
193 		BooleanNode dNode = new BooleanNode(d);
194 		dNode.setParent(orNode2);
195 		dNode.setNodeMessage("MATH202");
196 
197 		BooleanNode eNode = new BooleanNode(e);
198 		eNode.setParent(orNode2);
199 		eNode.setNodeMessage("MATH301");
200 		
201 		orNode1.addChild(andNode1); // left node
202 		orNode1.addChild(andNode2); // right node
203 		andNode1.addChild(aNode); // left node
204 		andNode1.addChild(bNode); // right node
205 		andNode2.addChild(cNode); // left node
206 		andNode2.addChild(orNode2); // right node
207 		orNode2.addChild(dNode); // right node
208 		orNode2.addChild(eNode); // right node
209 		
210 		// List of nodes order is important for building success message
211 		List<BooleanNode> list = new ArrayList<BooleanNode>();
212 		list.add(dNode);
213 		list.add(eNode);
214 		list.add(orNode2);
215 		list.add(aNode);
216 		list.add(bNode);
217 		list.add(cNode);
218 		list.add(andNode1);
219 		list.add(andNode2);
220 		list.add(orNode1);
221 
222 		String successMsg = configuredMessageBuilder.buildMessage(list);
223 
224 		Assert.assertEquals(successMsg, orNode1.getNodeMessage());
225 		Assert.assertEquals(
226 				"        (MATH101" +
227 				"\n    AND" +
228 				"\n        MATH102)" +
229 				"\nOR" +
230 				"\n        (MATH201" +
231 				"\n    AND" +
232 				"\n            (MATH202" +
233 				"\n        OR" +
234 				"\n            MATH301))",
235 				successMsg);
236 	}
237 
238 	@Test
239 	public void testBuildMessage_ForListOfNodes_Complex2() throws Exception {
240 		// Rule: (A OR (B AND (C OR E))
241 		Token or1 = adapter.createToken(BooleanFunctionParser.OR, "+");
242 		Token or2 = adapter.createToken(BooleanFunctionParser.OR, "+");
243 		Token and1 = adapter.createToken(BooleanFunctionParser.AND, "*");
244 		Token a = adapter.createToken(BooleanFunctionParser.ALPHA, "A");
245 		Token b = adapter.createToken(BooleanFunctionParser.ALPHA, "B");
246 		Token c = adapter.createToken(BooleanFunctionParser.ALPHA, "C");
247 		Token d = adapter.createToken(BooleanFunctionParser.ALPHA, "D");
248 		
249 		// root node
250 		BooleanNode orNode1 = new BooleanNode(or1);
251 
252 		BooleanNode andNode1 = new BooleanNode(and1);
253 		andNode1.setParent(orNode1);
254 
255 		BooleanNode orNode2 = new BooleanNode(or2);
256 		orNode2.setParent(andNode1);
257 		
258 		BooleanNode aNode = new BooleanNode(a);
259 		aNode.setParent(orNode1);
260 		aNode.setNodeMessage("MATH101");
261 
262 		BooleanNode bNode = new BooleanNode(b);
263 		bNode.setParent(andNode1);
264 		bNode.setNodeMessage("MATH201");
265 
266 		BooleanNode cNode = new BooleanNode(c);
267 		cNode.setParent(orNode2);
268 		cNode.setNodeMessage("MATH301");
269 		
270 		BooleanNode dNode = new BooleanNode(d);
271 		dNode.setParent(orNode2);
272 		dNode.setNodeMessage("MATH401");
273 
274 		orNode1.addChild(aNode); // left node
275 		orNode1.addChild(andNode1); // right node
276 		andNode1.addChild(bNode); // left node
277 		andNode1.addChild(orNode2); // right node
278 		orNode2.addChild(cNode); // left node
279 		orNode2.addChild(dNode); // right node
280 		
281 		// List of nodes order is important for building success message
282 		List<BooleanNode> list = new ArrayList<BooleanNode>();
283 		list.add(cNode);
284 		list.add(dNode);
285 		list.add(orNode2);
286 		list.add(bNode);
287 		list.add(andNode1);
288 		list.add(orNode1);
289 		list.add(aNode);
290 
291 		String successMsg = configuredMessageBuilder.buildMessage(list);
292 
293 		Assert.assertEquals(successMsg, orNode1.getNodeMessage());
294 		Assert.assertEquals(
295 				"    MATH101" +
296 				"\nOR" +
297 				"\n        (MATH201" +
298 				"\n    AND" +
299 				"\n            (MATH301" +
300 				"\n        OR" +
301 				"\n            MATH401))", 
302 				successMsg);
303 	}
304 
305 
306 	@Test
307 	public void testBuildMessage_ForListOfNodes_MultipleRootNodes() throws Exception {
308 		Token or = adapter.createToken(BooleanFunctionParser.OR, "+");
309 		Token and = adapter.createToken(BooleanFunctionParser.AND, "*");
310 		
311 		// root node1
312 		BooleanNode orNode = new BooleanNode(or);
313 		// root node1
314 		BooleanNode andNode = new BooleanNode(and);
315 		
316 		List<BooleanNode> list = new ArrayList<BooleanNode>();
317 		list.add(orNode);
318 		list.add(andNode);
319 
320 		try {
321 			configuredMessageBuilder.buildMessage(list);
322 			Assert.fail("buildSuccessMessage should have failed since list has 2 root nodes");
323 		} catch (MessageBuilderException e) {
324 			Assert.assertTrue(e.getMessage() != null);
325 			Assert.assertTrue(e.getMessage().contains("label=+"));
326 			Assert.assertTrue(e.getMessage().contains("label=*"));
327 		}
328 	}
329 }