View Javadoc
1   package de.fhdw.wtf.walker.tasks.test;
2   
3   import java.util.ArrayList;
4   import java.util.Collection;
5   import java.util.concurrent.ExecutionException;
6   
7   import junit.framework.TestCase;
8   
9   import org.junit.Test;
10  
11  import de.fhdw.wtf.common.ast.Model;
12  import de.fhdw.wtf.common.exception.parser.NoValidTokenStreamException;
13  import de.fhdw.wtf.common.exception.walker.CyclicDependencyException;
14  import de.fhdw.wtf.common.exception.walker.CyclicInheritanceException;
15  import de.fhdw.wtf.common.stream.FilteredTokenStream;
16  import de.fhdw.wtf.common.stream.SimpleScannerInput;
17  import de.fhdw.wtf.common.stream.TokenStream;
18  import de.fhdw.wtf.common.task.TaskExecutorFixed;
19  import de.fhdw.wtf.common.task.result.ExceptionalTaskResult;
20  import de.fhdw.wtf.common.task.result.OKTaskResult;
21  import de.fhdw.wtf.common.task.result.TaskResult;
22  import de.fhdw.wtf.common.task.result.visitor.TaskResultVisitor;
23  import de.fhdw.wtf.common.token.Position;
24  import de.fhdw.wtf.dsl.scanner.common.Scanner;
25  import de.fhdw.wtf.dsl.scanner.modelScanner.ModelDslScanner;
26  import de.fhdw.wtf.parser.Parser;
27  import de.fhdw.wtf.walker.tasks.CyclicInheritanceCheck;
28  import de.fhdw.wtf.walker.tasks.TypeReferencer;
29  import de.fhdw.wtf.walker.walker.SimpleWalkerTask;
30  
31  public class TestCyclicInheritanceCheck extends TestCase {
32  	
33  	@Test
34  	public void testInheritFromItself() throws InterruptedException, ExecutionException, NoValidTokenStreamException,
35  			CyclicDependencyException {
36  		final SimpleScannerInput input =
37  				new SimpleScannerInput("personGroup:group=[Person:class=Person+{name:String;} abstract; "
38  						+ "NaturalPerson:class=Person+{operation:[[(Number:Integer) -> String]] abstract;}; "
39  						+ "CorporateBody:class=Person+{};];");
40  		final TokenStream output = FilteredTokenStream.create();
41  		final Scanner scanner = ModelDslScanner.create();
42  		scanner.scan(input, output);
43  		final Parser parser = Parser.create(output);
44  		final Model model = parser.parse();
45  		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
46  		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
47  		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
48  		cyclicInheritance.addDependency(referencer);
49  		taskmanager.startAllKnownTasks();
50  		
51  		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
52  		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
53  		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
54  		for (final TaskResult current : results) {
55  			current.accept(new TaskResultVisitor() {
56  				
57  				@Override
58  				public void handleOkTaskResult(final OKTaskResult result) {
59  					okResult.add(result);
60  				}
61  				
62  				@Override
63  				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
64  					failResult.add(result);
65  				}
66  			});
67  		}
68  		
69  		assertEquals(1, okResult.size());
70  		assertEquals(1, failResult.size());
71  		
72  		final Exception exception = failResult.iterator().next().getError();
73  		if (exception instanceof CyclicInheritanceException) {
74  			final CyclicInheritanceException ex = (CyclicInheritanceException) exception;
75  			assertEquals(Position.create("", 1, 33, 32), ex.getStartPosition());
76  			assertEquals(Position.create("", 1, 39, 38), ex.getEndPos());
77  		} else {
78  			fail();
79  		}
80  	}
81  	
82  	@Test
83  	public void testSameName() throws InterruptedException, ExecutionException, NoValidTokenStreamException,
84  			CyclicDependencyException {
85  		final SimpleScannerInput input =
86  				new SimpleScannerInput("personGroup:group=[Person:class=group2>Person+{name:String;} abstract; "
87  						+ "NaturalPerson:class=Person+{operation:[[(Number:Integer) -> String]] abstract;}; "
88  						+ "CorporateBody:class=Person+{}; group2:group=[Person:class={};];];");
89  		final TokenStream output = FilteredTokenStream.create();
90  		final Scanner scanner = ModelDslScanner.create();
91  		scanner.scan(input, output);
92  		final Parser parser = Parser.create(output);
93  		final Model model = parser.parse();
94  		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
95  		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
96  		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
97  		cyclicInheritance.addDependency(referencer);
98  		taskmanager.startAllKnownTasks();
99  		
100 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
101 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
102 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
103 		for (final TaskResult current : results) {
104 			current.accept(new TaskResultVisitor() {
105 				
106 				@Override
107 				public void handleOkTaskResult(final OKTaskResult result) {
108 					okResult.add(result);
109 				}
110 				
111 				@Override
112 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
113 					failResult.add(result);
114 				}
115 			});
116 		}
117 		
118 		assertEquals(2, okResult.size());
119 		assertEquals(0, failResult.size());
120 	}
121 	
122 	@Test
123 	public void testInheritFromBasetype() throws InterruptedException, ExecutionException, NoValidTokenStreamException,
124 			CyclicDependencyException {
125 		final SimpleScannerInput input =
126 				new SimpleScannerInput("personGroup:group=[Person:class=String+{name:String;} abstract; "
127 						+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
128 		final TokenStream output = FilteredTokenStream.create();
129 		final Scanner scanner = ModelDslScanner.create();
130 		scanner.scan(input, output);
131 		final Parser parser = Parser.create(output);
132 		final Model model = parser.parse();
133 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
134 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
135 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
136 		cyclicInheritance.addDependency(referencer);
137 		taskmanager.startAllKnownTasks();
138 		
139 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
140 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
141 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
142 		for (final TaskResult current : results) {
143 			current.accept(new TaskResultVisitor() {
144 				
145 				@Override
146 				public void handleOkTaskResult(final OKTaskResult result) {
147 					okResult.add(result);
148 				}
149 				
150 				@Override
151 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
152 					failResult.add(result);
153 				}
154 			});
155 		}
156 		
157 		assertEquals(2, okResult.size());
158 		assertEquals(0, failResult.size());
159 	}
160 	
161 	@Test
162 	public void testCyclicInheritanceOverMoreClasses() throws InterruptedException, ExecutionException,
163 			NoValidTokenStreamException, CyclicDependencyException {
164 		final SimpleScannerInput input =
165 				new SimpleScannerInput("personGroup:group=[Person:class=NaturalPerson+{name:String;} abstract; "
166 						+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
167 		final TokenStream output = FilteredTokenStream.create();
168 		final Scanner scanner = ModelDslScanner.create();
169 		scanner.scan(input, output);
170 		final Parser parser = Parser.create(output);
171 		final Model model = parser.parse();
172 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
173 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
174 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
175 		cyclicInheritance.addDependency(referencer);
176 		taskmanager.startAllKnownTasks();
177 		
178 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
179 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
180 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
181 		for (final TaskResult current : results) {
182 			current.accept(new TaskResultVisitor() {
183 				
184 				@Override
185 				public void handleOkTaskResult(final OKTaskResult result) {
186 					okResult.add(result);
187 				}
188 				
189 				@Override
190 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
191 					failResult.add(result);
192 				}
193 			});
194 		}
195 		
196 		assertEquals(1, okResult.size());
197 		assertEquals(1, failResult.size());
198 		
199 		final Exception exception = failResult.iterator().next().getError();
200 		if (exception instanceof CyclicInheritanceException) {
201 			final CyclicInheritanceException ex = (CyclicInheritanceException) exception;
202 			assertEquals(Position.create("", 1, 92, 91), ex.getStartPosition());
203 			assertEquals(Position.create("", 1, 98, 97), ex.getEndPos());
204 		} else {
205 			fail();
206 		}
207 	}
208 	
209 	@Test
210 	public void testInvalidTypeReference() throws InterruptedException, ExecutionException,
211 			NoValidTokenStreamException, CyclicDependencyException {
212 		final SimpleScannerInput input =
213 				new SimpleScannerInput("personGroup:group=[Person:class=NaturalPerson2+{name:String;} abstract; "
214 						+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
215 		final TokenStream output = FilteredTokenStream.create();
216 		final Scanner scanner = ModelDslScanner.create();
217 		scanner.scan(input, output);
218 		final Parser parser = Parser.create(output);
219 		final Model model = parser.parse();
220 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
221 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
222 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
223 		cyclicInheritance.addDependency(referencer);
224 		taskmanager.startAllKnownTasks();
225 		
226 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
227 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
228 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
229 		for (final TaskResult current : results) {
230 			current.accept(new TaskResultVisitor() {
231 				
232 				@Override
233 				public void handleOkTaskResult(final OKTaskResult result) {
234 					okResult.add(result);
235 				}
236 				
237 				@Override
238 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
239 					failResult.add(result);
240 				}
241 			});
242 		}
243 		
244 		assertEquals(0, okResult.size());
245 		assertEquals(1, failResult.size());
246 		
247 		final Exception exception = failResult.iterator().next().getError();
248 		if (exception instanceof CyclicInheritanceException) {
249 			fail();
250 		}
251 	}
252 	
253 	@Test
254 	public void testWithoutTypeReferencer() throws InterruptedException, NoValidTokenStreamException {
255 		final SimpleScannerInput input =
256 				new SimpleScannerInput(
257 						"personGroup:group=[Person:class={name:String;} abstract; NaturalPerson:class=Person+{}; "
258 								+ "CorporateBody:class=Person+{};];");
259 		final TokenStream output = FilteredTokenStream.create();
260 		final Scanner scanner = ModelDslScanner.create();
261 		scanner.scan(input, output);
262 		final Parser parser = Parser.create(output);
263 		final Model model = parser.parse();
264 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
265 		CyclicInheritanceCheck.create(model, taskmanager);
266 		taskmanager.startAllKnownTasks();
267 		
268 		try {
269 			taskmanager.getResultsAndShutdown();
270 		} catch (final ExecutionException e) {
271 			// Erwartet, weil erst der TypeReferencer drĂ¼ber laufen muss
272 			return;
273 		}
274 		fail();
275 	}
276 	
277 	@Test
278 	public void testCyclicInheritanceOverMoreClassesInFirstSupertype() throws InterruptedException, ExecutionException,
279 			NoValidTokenStreamException, CyclicDependencyException {
280 		final SimpleScannerInput input =
281 				new SimpleScannerInput(
282 						"personGroup:group=[Objekt:class={}; Person:class=NaturalPerson+Objekt+{name:String;} abstract; "
283 								+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
284 		final TokenStream output = FilteredTokenStream.create();
285 		final Scanner scanner = ModelDslScanner.create();
286 		scanner.scan(input, output);
287 		final Parser parser = Parser.create(output);
288 		final Model model = parser.parse();
289 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
290 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
291 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
292 		cyclicInheritance.addDependency(referencer);
293 		taskmanager.startAllKnownTasks();
294 		
295 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
296 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
297 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
298 		for (final TaskResult current : results) {
299 			current.accept(new TaskResultVisitor() {
300 				
301 				@Override
302 				public void handleOkTaskResult(final OKTaskResult result) {
303 					okResult.add(result);
304 				}
305 				
306 				@Override
307 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
308 					failResult.add(result);
309 				}
310 			});
311 		}
312 		
313 		assertEquals(1, okResult.size());
314 		assertEquals(1, failResult.size());
315 		
316 		final Exception exception = failResult.iterator().next().getError();
317 		if (exception instanceof CyclicInheritanceException) {
318 			final CyclicInheritanceException ex = (CyclicInheritanceException) exception;
319 			assertEquals(Position.create("", 1, 116, 115), ex.getStartPosition());
320 			assertEquals(Position.create("", 1, 122, 121), ex.getEndPos());
321 		} else {
322 			fail();
323 		}
324 	}
325 	
326 	@Test
327 	public void testCyclicInheritanceOverMoreClassesInSecondSupertype() throws InterruptedException,
328 			ExecutionException, NoValidTokenStreamException, CyclicDependencyException {
329 		final SimpleScannerInput input =
330 				new SimpleScannerInput(
331 						"personGroup:group=[Objekt:class={}; Person:class=Objekt+NaturalPerson+{name:String;} abstract; "
332 								+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
333 		final TokenStream output = FilteredTokenStream.create();
334 		final Scanner scanner = ModelDslScanner.create();
335 		scanner.scan(input, output);
336 		final Parser parser = Parser.create(output);
337 		final Model model = parser.parse();
338 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
339 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
340 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
341 		cyclicInheritance.addDependency(referencer);
342 		taskmanager.startAllKnownTasks();
343 		
344 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
345 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
346 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
347 		for (final TaskResult current : results) {
348 			current.accept(new TaskResultVisitor() {
349 				
350 				@Override
351 				public void handleOkTaskResult(final OKTaskResult result) {
352 					okResult.add(result);
353 				}
354 				
355 				@Override
356 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
357 					failResult.add(result);
358 				}
359 			});
360 		}
361 		
362 		assertEquals(1, okResult.size());
363 		assertEquals(1, failResult.size());
364 		
365 		final Exception exception = failResult.iterator().next().getError();
366 		if (exception instanceof CyclicInheritanceException) {
367 			final CyclicInheritanceException ex = (CyclicInheritanceException) exception;
368 			assertEquals(Position.create("", 1, 116, 115), ex.getStartPosition());
369 			assertEquals(Position.create("", 1, 122, 121), ex.getEndPos());
370 		} else {
371 			fail();
372 		}
373 	}
374 	
375 	@Test
376 	public void testCyclicInheritanceOverMoreClassesBecauseOfTheSupertypeSupertype() throws InterruptedException,
377 			ExecutionException, NoValidTokenStreamException, CyclicDependencyException {
378 		final SimpleScannerInput input =
379 				new SimpleScannerInput(
380 						"personGroup:group=[Objekt:class=NaturalPerson+{}; Person:class=Objekt+{name:String;} abstract; "
381 								+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
382 		final TokenStream output = FilteredTokenStream.create();
383 		final Scanner scanner = ModelDslScanner.create();
384 		scanner.scan(input, output);
385 		final Parser parser = Parser.create(output);
386 		final Model model = parser.parse();
387 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
388 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
389 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
390 		cyclicInheritance.addDependency(referencer);
391 		taskmanager.startAllKnownTasks();
392 		
393 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
394 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
395 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
396 		for (final TaskResult current : results) {
397 			current.accept(new TaskResultVisitor() {
398 				
399 				@Override
400 				public void handleOkTaskResult(final OKTaskResult result) {
401 					okResult.add(result);
402 				}
403 				
404 				@Override
405 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
406 					failResult.add(result);
407 				}
408 			});
409 		}
410 		
411 		assertEquals(1, okResult.size());
412 		assertEquals(1, failResult.size());
413 		
414 		final Exception exception = failResult.iterator().next().getError();
415 		if (exception instanceof CyclicInheritanceException) {
416 			final CyclicInheritanceException ex = (CyclicInheritanceException) exception;
417 			assertEquals(Position.create("", 1, 64, 63), ex.getStartPosition());
418 			assertEquals(Position.create("", 1, 70, 69), ex.getEndPos());
419 		} else {
420 			fail();
421 		}
422 	}
423 	
424 	@Test
425 	public void testCyclicInheritanceOverMoreClassesInBothSupertypes() throws InterruptedException, ExecutionException,
426 			NoValidTokenStreamException, CyclicDependencyException {
427 		final SimpleScannerInput input =
428 				new SimpleScannerInput(
429 						"personGroup:group=[Person:class=NaturalPerson+CorporateBody+{name:String;} abstract; "
430 								+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
431 		final TokenStream output = FilteredTokenStream.create();
432 		final Scanner scanner = ModelDslScanner.create();
433 		scanner.scan(input, output);
434 		final Parser parser = Parser.create(output);
435 		final Model model = parser.parse();
436 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
437 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
438 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
439 		cyclicInheritance.addDependency(referencer);
440 		taskmanager.startAllKnownTasks();
441 		
442 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
443 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
444 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
445 		for (final TaskResult current : results) {
446 			current.accept(new TaskResultVisitor() {
447 				
448 				@Override
449 				public void handleOkTaskResult(final OKTaskResult result) {
450 					okResult.add(result);
451 				}
452 				
453 				@Override
454 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
455 					failResult.add(result);
456 				}
457 			});
458 		}
459 		
460 		assertEquals(1, okResult.size());
461 		assertEquals(1, failResult.size());
462 		
463 		final Exception exception = failResult.iterator().next().getError();
464 		if (exception instanceof CyclicInheritanceException) {
465 			final CyclicInheritanceException ex = (CyclicInheritanceException) exception;
466 			assertEquals(Position.create("", 1, 106, 105), ex.getStartPosition());
467 			assertEquals(Position.create("", 1, 112, 111), ex.getEndPos());
468 		} else {
469 			fail();
470 		}
471 	}
472 	
473 	@Test
474 	public void testInheritanceFromTheSameClassTwice() throws InterruptedException, ExecutionException,
475 			NoValidTokenStreamException, CyclicDependencyException {
476 		final SimpleScannerInput input =
477 				new SimpleScannerInput(
478 						"personGroup:group=[Objekt:class={}; Person:class=Objekt+Objekt+{name:String;} abstract; "
479 								+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
480 		final TokenStream output = FilteredTokenStream.create();
481 		final Scanner scanner = ModelDslScanner.create();
482 		scanner.scan(input, output);
483 		final Parser parser = Parser.create(output);
484 		final Model model = parser.parse();
485 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
486 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
487 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
488 		cyclicInheritance.addDependency(referencer);
489 		taskmanager.startAllKnownTasks();
490 		
491 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
492 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
493 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
494 		for (final TaskResult current : results) {
495 			current.accept(new TaskResultVisitor() {
496 				
497 				@Override
498 				public void handleOkTaskResult(final OKTaskResult result) {
499 					okResult.add(result);
500 				}
501 				
502 				@Override
503 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
504 					failResult.add(result);
505 				}
506 			});
507 		}
508 		
509 		assertEquals(2, okResult.size());
510 		assertEquals(0, failResult.size());
511 	}
512 	
513 	@Test
514 	public void testInheritanceFromTwoClassesInTheSameInheritanceStructur() throws InterruptedException,
515 			ExecutionException, NoValidTokenStreamException, CyclicDependencyException {
516 		final SimpleScannerInput input =
517 				new SimpleScannerInput(
518 						"personGroup:group=[XPerson:class=Person+NaturalPerson+{}; Person:class={name:String;} abstract; "
519 								+ "NaturalPerson:class=Person+{}; CorporateBody:class=Person+{};];");
520 		final TokenStream output = FilteredTokenStream.create();
521 		final Scanner scanner = ModelDslScanner.create();
522 		scanner.scan(input, output);
523 		final Parser parser = Parser.create(output);
524 		final Model model = parser.parse();
525 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
526 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
527 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
528 		cyclicInheritance.addDependency(referencer);
529 		taskmanager.startAllKnownTasks();
530 		
531 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
532 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
533 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
534 		for (final TaskResult current : results) {
535 			current.accept(new TaskResultVisitor() {
536 				
537 				@Override
538 				public void handleOkTaskResult(final OKTaskResult result) {
539 					okResult.add(result);
540 				}
541 				
542 				@Override
543 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
544 					failResult.add(result);
545 				}
546 			});
547 		}
548 		
549 		assertEquals(2, okResult.size());
550 		assertEquals(0, failResult.size());
551 	}
552 	
553 	@Test
554 	public void testOverGroups() throws InterruptedException, ExecutionException, NoValidTokenStreamException,
555 			CyclicDependencyException {
556 		final SimpleScannerInput input =
557 				new SimpleScannerInput("personGroup:group=[Person:class=group2>Person+{name:String;} abstract; "
558 						+ "NaturalPerson:class=Person+{operation:[[(Number:Integer) -> String]] abstract;}; "
559 						+ "CorporateBody:class=Person+{}; group2:group=[Person:class=NaturalPerson+{};];];");
560 		final TokenStream output = FilteredTokenStream.create();
561 		final Scanner scanner = ModelDslScanner.create();
562 		scanner.scan(input, output);
563 		final Parser parser = Parser.create(output);
564 		final Model model = parser.parse();
565 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
566 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
567 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
568 		cyclicInheritance.addDependency(referencer);
569 		taskmanager.startAllKnownTasks();
570 		
571 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
572 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
573 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
574 		for (final TaskResult current : results) {
575 			current.accept(new TaskResultVisitor() {
576 				
577 				@Override
578 				public void handleOkTaskResult(final OKTaskResult result) {
579 					okResult.add(result);
580 				}
581 				
582 				@Override
583 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
584 					failResult.add(result);
585 				}
586 			});
587 		}
588 		
589 		assertEquals(1, okResult.size());
590 		assertEquals(1, failResult.size());
591 		
592 		final Exception exception = failResult.iterator().next().getError();
593 		if (exception instanceof CyclicInheritanceException) {
594 			final CyclicInheritanceException ex = (CyclicInheritanceException) exception;
595 			assertEquals(Position.create("", 1, 92, 91), ex.getStartPosition());
596 			assertEquals(Position.create("", 1, 98, 97), ex.getEndPos());
597 		} else {
598 			fail();
599 		}
600 	}
601 	
602 	@Test
603 	public void testDiamondWithOutCyclus() throws InterruptedException, ExecutionException,
604 			NoValidTokenStreamException, CyclicDependencyException {
605 		final SimpleScannerInput input =
606 				new SimpleScannerInput("Gruppe:group=[D:class=B+C+{}; B:class=A+{}; C:class=A+{} ;A:class={};];");
607 		final TokenStream output = FilteredTokenStream.create();
608 		final Scanner scanner = ModelDslScanner.create();
609 		scanner.scan(input, output);
610 		final Parser parser = Parser.create(output);
611 		final Model model = parser.parse();
612 		final TaskExecutorFixed taskmanager = TaskExecutorFixed.create();
613 		final SimpleWalkerTask referencer = TypeReferencer.create(model, taskmanager);
614 		final SimpleWalkerTask cyclicInheritance = CyclicInheritanceCheck.create(model, taskmanager);
615 		cyclicInheritance.addDependency(referencer);
616 		taskmanager.startAllKnownTasks();
617 		
618 		final Collection<OKTaskResult> okResult = new ArrayList<OKTaskResult>();
619 		final Collection<ExceptionalTaskResult> failResult = new ArrayList<ExceptionalTaskResult>();
620 		final Collection<TaskResult> results = taskmanager.getResultsAndShutdown();
621 		for (final TaskResult current : results) {
622 			current.accept(new TaskResultVisitor() {
623 				
624 				@Override
625 				public void handleOkTaskResult(final OKTaskResult result) {
626 					okResult.add(result);
627 				}
628 				
629 				@Override
630 				public void handleExceptionalTaskResult(final ExceptionalTaskResult result) {
631 					failResult.add(result);
632 				}
633 			});
634 		}
635 		
636 		assertEquals(2, okResult.size());
637 		assertEquals(0, failResult.size());
638 	}
639 }