View Javadoc
1   package de.fhdw.wtf.parser.test;
2   
3   import static org.junit.Assert.assertEquals;
4   import static org.junit.Assert.assertFalse;
5   import static org.junit.Assert.assertTrue;
6   import static org.junit.Assert.fail;
7   
8   import java.util.ArrayList;
9   import java.util.Collection;
10  import java.util.List;
11  import java.util.Vector;
12  
13  import org.junit.Before;
14  import org.junit.Test;
15  
16  import de.fhdw.wtf.common.ast.Attribute;
17  import de.fhdw.wtf.common.ast.AttributeModifier;
18  import de.fhdw.wtf.common.ast.AttributeModifierFindable;
19  import de.fhdw.wtf.common.ast.AttributeModifierMutable;
20  import de.fhdw.wtf.common.ast.AttributeModifierPrior;
21  import de.fhdw.wtf.common.ast.AttributeModifierSymmetric;
22  import de.fhdw.wtf.common.ast.AttributeModifierTransient;
23  import de.fhdw.wtf.common.ast.Constructor;
24  import de.fhdw.wtf.common.ast.Group;
25  import de.fhdw.wtf.common.ast.GroupElement;
26  import de.fhdw.wtf.common.ast.Model;
27  import de.fhdw.wtf.common.ast.Name;
28  import de.fhdw.wtf.common.ast.Operation;
29  import de.fhdw.wtf.common.ast.UnqualifiedName;
30  import de.fhdw.wtf.common.ast.type.BaseType;
31  import de.fhdw.wtf.common.ast.type.ByNameState;
32  import de.fhdw.wtf.common.ast.type.ClassModifier;
33  import de.fhdw.wtf.common.ast.type.ClassType;
34  import de.fhdw.wtf.common.ast.type.ListType;
35  import de.fhdw.wtf.common.ast.type.MapType;
36  import de.fhdw.wtf.common.ast.type.ProductElementType;
37  import de.fhdw.wtf.common.ast.type.ProductType;
38  import de.fhdw.wtf.common.ast.type.RegularClassType;
39  import de.fhdw.wtf.common.ast.type.SumType;
40  import de.fhdw.wtf.common.ast.type.Type;
41  import de.fhdw.wtf.common.ast.type.TypeProxy;
42  import de.fhdw.wtf.common.exception.parser.NoValidTokenStreamException;
43  import de.fhdw.wtf.common.stream.SimpleTokenStream;
44  import de.fhdw.wtf.common.stream.TokenStream;
45  import de.fhdw.wtf.common.token.EndToken;
46  import de.fhdw.wtf.common.token.IdentifierToken;
47  import de.fhdw.wtf.common.token.Position;
48  import de.fhdw.wtf.common.token.keywords.ClassToken;
49  import de.fhdw.wtf.common.token.keywords.FindableToken;
50  import de.fhdw.wtf.common.token.keywords.GroupToken;
51  import de.fhdw.wtf.common.token.keywords.MutableToken;
52  import de.fhdw.wtf.common.token.keywords.PriorToken;
53  import de.fhdw.wtf.common.token.keywords.SymmetricToken;
54  import de.fhdw.wtf.common.token.keywords.TransientToken;
55  import de.fhdw.wtf.common.token.symbols.ArrowToken;
56  import de.fhdw.wtf.common.token.symbols.AsteriskToken;
57  import de.fhdw.wtf.common.token.symbols.BracketCloseToken;
58  import de.fhdw.wtf.common.token.symbols.BracketOpenToken;
59  import de.fhdw.wtf.common.token.symbols.ColonToken;
60  import de.fhdw.wtf.common.token.symbols.CommaToken;
61  import de.fhdw.wtf.common.token.symbols.CurlyBracketCloseToken;
62  import de.fhdw.wtf.common.token.symbols.CurlyBracketOpenToken;
63  import de.fhdw.wtf.common.token.symbols.EqualToken;
64  import de.fhdw.wtf.common.token.symbols.GreaterSymbolToken;
65  import de.fhdw.wtf.common.token.symbols.PlusSymbolToken;
66  import de.fhdw.wtf.common.token.symbols.SemicolonToken;
67  import de.fhdw.wtf.common.token.symbols.SquareBracketCloseToken;
68  import de.fhdw.wtf.common.token.symbols.SquareBracketOpenToken;
69  import de.fhdw.wtf.parser.Parser;
70  
71  public class TestAttributes {
72  	
73  	private TokenStream stream;
74  	private ColonToken colonToken;
75  	private GroupToken groupToken;
76  	private EqualToken equalToken;
77  	private SquareBracketOpenToken squareBracketOpenToken;
78  	private SquareBracketCloseToken squareBracketCloseToken;
79  	private SemicolonToken semicolonToken;
80  	private Parser parser;
81  	private ClassToken classToken;
82  	private CurlyBracketOpenToken curlyBracketOpenToken;
83  	private CurlyBracketCloseToken curlyBracketCloseToken;
84  	private EndToken endToken;
85  	private PlusSymbolToken plusSymbolToken;
86  	private GreaterSymbolToken greaterSymbol;
87  	private AsteriskToken asteriskToken;
88  	private IdentifierToken stringIdentifier;
89  	private IdentifierToken integerIdentifier;
90  	private BracketOpenToken bracketOpenToken;
91  	private BracketCloseToken bracketCloseToken;
92  	private CommaToken commaToken;
93  	private ArrowToken arrowToken;
94  	
95  	/**
96  	 * Creates the most important Tokens.
97  	 */
98  	@Before
99  	public void setUp() {
100 		this.stream = SimpleTokenStream.create();
101 		this.stringIdentifier = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
102 		this.integerIdentifier = IdentifierToken.create("Integer", Position.create("", 0 + 1, 0 + 1, 0));
103 		this.colonToken = ColonToken.create(Position.create("", 0 + 1, 0 + 1, 0));
104 		this.groupToken = GroupToken.create(Position.create("", 0 + 1, 0 + 1, 0));
105 		this.equalToken = EqualToken.create(Position.create("", 0 + 1, 0 + 1, 0));
106 		this.squareBracketOpenToken = SquareBracketOpenToken.create(Position.create("", 0, 0, 0));
107 		this.squareBracketCloseToken = SquareBracketCloseToken.create(Position.create("", 0, 0, 0));
108 		this.semicolonToken = SemicolonToken.create(Position.create("", 0 + 1, 0 + 1, 0));
109 		this.parser = Parser.create(this.stream);
110 		this.classToken = ClassToken.create(Position.create("", 0 + 1, 0 + 1, 0));
111 		this.curlyBracketOpenToken = CurlyBracketOpenToken.create(Position.create("", 0, 0, 0));
112 		this.curlyBracketCloseToken = CurlyBracketCloseToken.create(Position.create("", 0, 0, 0));
113 		this.endToken = EndToken.create(Position.create("", 0 + 1, 0 + 1, 0));
114 		this.plusSymbolToken = PlusSymbolToken.create(Position.create("", 0 + 1, 0 + 1, 0));
115 		this.greaterSymbol = GreaterSymbolToken.create(Position.create("", 0, 0, 0));
116 		this.asteriskToken = AsteriskToken.create(Position.create("", 0 + 1, 0 + 1, 0));
117 		this.bracketOpenToken = BracketOpenToken.create(Position.create("", 1, 1, 0));
118 		this.bracketCloseToken = BracketCloseToken.create(Position.create("", 1, 1, 0));
119 		this.commaToken = CommaToken.create(Position.create("", 1, 1, 0));
120 		this.arrowToken = ArrowToken.create(Position.create("", 1, 1, 0));
121 	}
122 	
123 	/**
124 	 * Group:group=[Class:class={Attribute:String;};];.
125 	 * 
126 	 * @throws Exception
127 	 *             : {@link NoValidTokenStreamException}
128 	 */
129 	@Test
130 	public void testOneAttribute() throws Exception {
131 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
132 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
133 		final IdentifierToken attributeIdentifier =
134 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
135 		this.stream.add(groupIdentifier);
136 		this.stream.add(this.colonToken);
137 		this.stream.add(this.groupToken);
138 		this.stream.add(this.equalToken);
139 		this.stream.add(this.squareBracketOpenToken);
140 		this.stream.add(classIdentifier);
141 		this.stream.add(this.colonToken);
142 		this.stream.add(this.classToken);
143 		this.stream.add(this.equalToken);
144 		this.stream.add(this.curlyBracketOpenToken);
145 		this.stream.add(attributeIdentifier);
146 		this.stream.add(this.colonToken);
147 		this.stream.add(this.stringIdentifier);
148 		this.stream.add(this.semicolonToken);
149 		this.stream.add(this.curlyBracketCloseToken);
150 		this.stream.add(this.semicolonToken);
151 		this.stream.add(this.squareBracketCloseToken);
152 		this.stream.add(this.semicolonToken);
153 		this.stream.add(this.endToken);
154 		
155 		final Vector<GroupElement> groupVector = new Vector<>();
156 		final Vector<Attribute> attributes = new Vector<>();
157 		
158 		final Name groupName = UnqualifiedName.create(groupIdentifier);
159 		final Group group1 = Group.create(groupName, groupVector, groupIdentifier);
160 		
161 		final Name className = groupName.addName(classIdentifier);
162 		final ClassType class1 =
163 				RegularClassType.create(
164 						className,
165 						new Vector<ClassModifier>(),
166 						attributes,
167 						new Vector<Type>(),
168 						new Vector<Operation>(),
169 						new Vector<Constructor>(),
170 						classIdentifier,
171 						new Vector<ClassType>());
172 		
173 		final ByNameState attributeTypeReferenceState =
174 				ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
175 		final TypeProxy attributeType = TypeProxy.create(this.stringIdentifier, attributeTypeReferenceState);
176 		final Attribute class1Attribute =
177 				Attribute.create("Attribute", attributeType, new Vector<AttributeModifier>(), attributeIdentifier);
178 		attributes.add(class1Attribute);
179 		groupVector.add(class1);
180 		final Model expected = Model.create(groupIdentifier);
181 		expected.addGroup(group1);
182 		
183 		final Model actual = this.parser.parse();
184 		assertEquals(expected, actual);
185 		assertEquals(0, this.parser.getExceptions().size());
186 	}
187 	
188 	/**
189 	 * Group:group=[Class:class= Superclass + {Attribute:String;};];.
190 	 * 
191 	 * @throws Exception
192 	 *             : {@link NoValidTokenStreamException}
193 	 */
194 	@Test
195 	public void testClassWithSuperclassAndAttribute() throws Exception {
196 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
197 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
198 		final IdentifierToken superclassIdentifier =
199 				IdentifierToken.create("Superclass", Position.create("", 0 + 1, 0 + 1, 0));
200 		final IdentifierToken attributeIdentifier =
201 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
202 		this.stream.add(groupIdentifier);
203 		this.stream.add(this.colonToken);
204 		this.stream.add(this.groupToken);
205 		this.stream.add(this.equalToken);
206 		this.stream.add(this.squareBracketOpenToken);
207 		this.stream.add(classIdentifier);
208 		this.stream.add(this.colonToken);
209 		this.stream.add(this.classToken);
210 		this.stream.add(this.equalToken);
211 		this.stream.add(superclassIdentifier);
212 		this.stream.add(this.plusSymbolToken);
213 		this.stream.add(this.curlyBracketOpenToken);
214 		this.stream.add(attributeIdentifier);
215 		this.stream.add(this.colonToken);
216 		this.stream.add(this.stringIdentifier);
217 		this.stream.add(this.semicolonToken);
218 		this.stream.add(this.curlyBracketCloseToken);
219 		this.stream.add(this.semicolonToken);
220 		this.stream.add(this.squareBracketCloseToken);
221 		this.stream.add(this.semicolonToken);
222 		this.stream.add(EndToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
223 		
224 		final Collection<GroupElement> groupVector = new Vector<>();
225 		final Collection<Attribute> classAttributes = new Vector<>();
226 		final List<Type> class1SuperTypes = new Vector<>();
227 		final Collection<AttributeModifier> attrModifiers = new Vector<>();
228 		
229 		final Name name = UnqualifiedName.create(groupIdentifier);
230 		final Group group = Group.create(name, groupVector, groupIdentifier);
231 		final Name class1Name = name.addName(classIdentifier);
232 		
233 		final ClassType classModel =
234 				RegularClassType.create(
235 						class1Name,
236 						new Vector<ClassModifier>(),
237 						classAttributes,
238 						class1SuperTypes,
239 						new Vector<Operation>(),
240 						new Vector<Constructor>(),
241 						classIdentifier,
242 						
243 						new Vector<ClassType>());
244 		
245 		final Name class2name = UnqualifiedName.create(superclassIdentifier);
246 		final ByNameState class2ReferenceState = ByNameState.create(class2name);
247 		final TypeProxy class2Reference = TypeProxy.create(superclassIdentifier, class2ReferenceState);
248 		class1SuperTypes.add(class2Reference);
249 		
250 		final Name attrTypeClass1Name = UnqualifiedName.create(this.stringIdentifier);
251 		final ByNameState attrClass1TypeReferenceState = ByNameState.create(attrTypeClass1Name);
252 		final TypeProxy attrClass1Type = TypeProxy.create(this.stringIdentifier, attrClass1TypeReferenceState);
253 		final Attribute class1Attribute =
254 				Attribute.create("Attribute", attrClass1Type, attrModifiers, attributeIdentifier);
255 		classAttributes.add(class1Attribute);
256 		groupVector.add(classModel);
257 		
258 		final Model expected = Model.create(groupIdentifier);
259 		expected.addGroup(group);
260 		
261 		final Model actual = this.parser.parse();
262 		assertEquals(0, this.parser.getExceptions().size());
263 		assertEquals(expected, actual);
264 	}
265 	
266 	/**
267 	 * Group:group=[Class:class={Attribute1:String;Attribute2:Integer;Attribute3 :String;};];.
268 	 * 
269 	 * @throws Exception
270 	 *             : {@link NoValidTokenStreamException}
271 	 */
272 	@Test
273 	public void testSomeAttributes() throws Exception {
274 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
275 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
276 		final IdentifierToken attributeIdentifier1 =
277 				IdentifierToken.create("Attribute1", Position.create("", 0 + 1, 0 + 1, 0));
278 		final IdentifierToken attributeIdentifier2 =
279 				IdentifierToken.create("Attribute2", Position.create("", 0 + 1, 0 + 1, 0));
280 		final IdentifierToken attributeIdentifier3 =
281 				IdentifierToken.create("Attribute3", Position.create("", 0 + 1, 0 + 1, 0));
282 		this.stream.add(groupIdentifier);
283 		this.stream.add(this.colonToken);
284 		this.stream.add(this.groupToken);
285 		this.stream.add(this.equalToken);
286 		this.stream.add(this.squareBracketOpenToken);
287 		this.stream.add(classIdentifier);
288 		this.stream.add(this.colonToken);
289 		this.stream.add(this.classToken);
290 		this.stream.add(this.equalToken);
291 		this.stream.add(this.curlyBracketOpenToken);
292 		this.stream.add(attributeIdentifier1);
293 		this.stream.add(this.colonToken);
294 		this.stream.add(this.stringIdentifier);
295 		this.stream.add(this.semicolonToken);
296 		this.stream.add(attributeIdentifier2);
297 		this.stream.add(this.colonToken);
298 		this.stream.add(this.integerIdentifier);
299 		this.stream.add(this.semicolonToken);
300 		this.stream.add(attributeIdentifier3);
301 		this.stream.add(this.colonToken);
302 		this.stream.add(this.stringIdentifier);
303 		this.stream.add(this.semicolonToken);
304 		this.stream.add(this.curlyBracketCloseToken);
305 		this.stream.add(this.semicolonToken);
306 		this.stream.add(this.squareBracketCloseToken);
307 		this.stream.add(this.semicolonToken);
308 		this.stream.add(this.endToken);
309 		
310 		final Vector<GroupElement> groupVector = new Vector<>();
311 		final Vector<Attribute> attributes = new Vector<>();
312 		
313 		final Name groupName = UnqualifiedName.create(groupIdentifier);
314 		final Group group1 = Group.create(groupName, groupVector, groupIdentifier);
315 		
316 		final Name className = groupName.addName(classIdentifier);
317 		final ClassType class1 =
318 				RegularClassType.create(
319 						className,
320 						new Vector<ClassModifier>(),
321 						attributes,
322 						new Vector<Type>(),
323 						new Vector<Operation>(),
324 						new Vector<Constructor>(),
325 						classIdentifier,
326 						
327 						new Vector<ClassType>());
328 		
329 		final ByNameState attributeStringReferenceState =
330 				ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
331 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, attributeStringReferenceState);
332 		
333 		final ByNameState attributeIntegerReferenceState =
334 				ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
335 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, attributeIntegerReferenceState);
336 		
337 		final Attribute attribute1 =
338 				Attribute.create("Attribute1", stringType, new Vector<AttributeModifier>(), attributeIdentifier1);
339 		final Attribute attribute2 =
340 				Attribute.create("Attribute2", integerType, new Vector<AttributeModifier>(), attributeIdentifier2);
341 		final Attribute attribute3 =
342 				Attribute.create("Attribute3", stringType, new Vector<AttributeModifier>(), attributeIdentifier3);
343 		attributes.add(attribute1);
344 		attributes.add(attribute2);
345 		attributes.add(attribute3);
346 		groupVector.add(class1);
347 		final Model expected = Model.create(groupIdentifier);
348 		expected.addGroup(group1);
349 		
350 		final Model actual = this.parser.parse();
351 		assertEquals(expected, actual);
352 		assertEquals(0, this.parser.getExceptions().size());
353 	}
354 	
355 	/**
356 	 * Group1:group=[Class1:class={};];Group2:group=[Class2:class={Attribute: Class1;};];.
357 	 * 
358 	 * @throws Exception
359 	 *             : {@link NoValidTokenStreamException}
360 	 */
361 	@Test
362 	public void testAttributeWithOwnClassType() throws Exception {
363 		final IdentifierToken group1Identifier = IdentifierToken.create("Group1", Position.create("", 0 + 1, 0 + 1, 0));
364 		final IdentifierToken group2Identifier = IdentifierToken.create("Group2", Position.create("", 0 + 1, 0 + 1, 0));
365 		final IdentifierToken class1Identifier = IdentifierToken.create("Class1", Position.create("", 0 + 1, 0 + 1, 0));
366 		final IdentifierToken class2Identifier = IdentifierToken.create("Class2", Position.create("", 0 + 1, 0 + 1, 0));
367 		final IdentifierToken attributeIdentifier =
368 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
369 		this.stream.add(group1Identifier);
370 		this.stream.add(this.colonToken);
371 		this.stream.add(this.groupToken);
372 		this.stream.add(this.equalToken);
373 		this.stream.add(this.squareBracketOpenToken);
374 		this.stream.add(class1Identifier);
375 		this.stream.add(this.colonToken);
376 		this.stream.add(this.classToken);
377 		this.stream.add(this.equalToken);
378 		this.stream.add(this.curlyBracketOpenToken);
379 		this.stream.add(this.curlyBracketCloseToken);
380 		this.stream.add(this.semicolonToken);
381 		this.stream.add(this.squareBracketCloseToken);
382 		this.stream.add(this.semicolonToken);
383 		this.stream.add(group2Identifier);
384 		this.stream.add(this.colonToken);
385 		this.stream.add(this.groupToken);
386 		this.stream.add(this.equalToken);
387 		this.stream.add(this.squareBracketOpenToken);
388 		this.stream.add(class2Identifier);
389 		this.stream.add(this.colonToken);
390 		this.stream.add(this.classToken);
391 		this.stream.add(this.equalToken);
392 		this.stream.add(this.curlyBracketOpenToken);
393 		this.stream.add(attributeIdentifier);
394 		this.stream.add(this.colonToken);
395 		this.stream.add(class1Identifier);
396 		this.stream.add(this.semicolonToken);
397 		this.stream.add(this.curlyBracketCloseToken);
398 		this.stream.add(this.semicolonToken);
399 		this.stream.add(this.squareBracketCloseToken);
400 		this.stream.add(this.semicolonToken);
401 		this.stream.add(this.endToken);
402 		
403 		final Vector<GroupElement> group1Vector = new Vector<>();
404 		final Vector<GroupElement> group2Vector = new Vector<>();
405 		final Vector<Attribute> attributes = new Vector<>();
406 		
407 		final Name group1Name = UnqualifiedName.create(group1Identifier);
408 		final Group group1 = Group.create(group1Name, group1Vector, group1Identifier);
409 		
410 		final Name class1Name = group1Name.addName(class1Identifier);
411 		final ClassType class1 =
412 				RegularClassType.create(
413 						class1Name,
414 						new Vector<ClassModifier>(),
415 						new Vector<Attribute>(),
416 						new Vector<Type>(),
417 						new Vector<Operation>(),
418 						new Vector<Constructor>(),
419 						class1Identifier,
420 						
421 						new Vector<ClassType>());
422 		
423 		final Name group2Name = UnqualifiedName.create(group2Identifier);
424 		final Group group2 = Group.create(group2Name, group2Vector, group2Identifier);
425 		
426 		final Name class2Name = group2Name.addName(class2Identifier);
427 		final ClassType class2 =
428 				RegularClassType.create(
429 						class2Name,
430 						new Vector<ClassModifier>(),
431 						attributes,
432 						new Vector<Type>(),
433 						new Vector<Operation>(),
434 						new Vector<Constructor>(),
435 						class1Identifier,
436 						
437 						new Vector<ClassType>());
438 		
439 		final ByNameState attributeReferenceState = ByNameState.create(UnqualifiedName.create(class1Identifier));
440 		final TypeProxy classType = TypeProxy.create(class1Identifier, attributeReferenceState);
441 		
442 		final Attribute attribute1 =
443 				Attribute.create("Attribute", classType, new Vector<AttributeModifier>(), attributeIdentifier);
444 		attributes.add(attribute1);
445 		group1Vector.add(class1);
446 		group2Vector.add(class2);
447 		final Model expected = Model.create(group1Identifier);
448 		expected.addGroup(group1);
449 		expected.addGroup(group2);
450 		
451 		final Model actual = this.parser.parse();
452 		assertEquals(expected, actual);
453 		assertEquals(0, this.parser.getExceptions().size());
454 	}
455 	
456 	/**
457 	 * Group:group=[Class:class={Attribute:String*;};];.
458 	 * 
459 	 * @throws Exception
460 	 *             : {@link NoValidTokenStreamException}
461 	 */
462 	@Test
463 	public void testAttributeWithList() throws Exception {
464 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
465 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
466 		final IdentifierToken attributeIdentifier =
467 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
468 		this.stream.add(groupIdentifier);
469 		this.stream.add(this.colonToken);
470 		this.stream.add(this.groupToken);
471 		this.stream.add(this.equalToken);
472 		this.stream.add(this.squareBracketOpenToken);
473 		this.stream.add(classIdentifier);
474 		this.stream.add(this.colonToken);
475 		this.stream.add(this.classToken);
476 		this.stream.add(this.equalToken);
477 		this.stream.add(this.curlyBracketOpenToken);
478 		this.stream.add(attributeIdentifier);
479 		this.stream.add(this.colonToken);
480 		this.stream.add(this.stringIdentifier);
481 		this.stream.add(this.asteriskToken);
482 		this.stream.add(this.semicolonToken);
483 		this.stream.add(this.curlyBracketCloseToken);
484 		this.stream.add(this.semicolonToken);
485 		this.stream.add(this.squareBracketCloseToken);
486 		this.stream.add(this.semicolonToken);
487 		this.stream.add(this.endToken);
488 		
489 		final Vector<GroupElement> groupVector = new Vector<>();
490 		final Vector<Attribute> attributes = new Vector<>();
491 		
492 		final Name groupName = UnqualifiedName.create(groupIdentifier);
493 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
494 		
495 		final Name className = groupName.addName(classIdentifier);
496 		final ClassType classModel =
497 				RegularClassType.create(
498 						className,
499 						new Vector<ClassModifier>(),
500 						attributes,
501 						new Vector<Type>(),
502 						new Vector<Operation>(),
503 						new Vector<Constructor>(),
504 						classIdentifier,
505 						
506 						new Vector<ClassType>());
507 		
508 		final ByNameState attributeReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
509 		final TypeProxy attributeType = TypeProxy.create(this.stringIdentifier, attributeReferenceState);
510 		final ListType listType = ListType.create(this.stringIdentifier, attributeType);
511 		
512 		final Attribute attribute =
513 				Attribute.create("Attribute", listType, new Vector<AttributeModifier>(), attributeIdentifier);
514 		attributes.add(attribute);
515 		groupVector.add(classModel);
516 		final Model expected = Model.create(groupIdentifier);
517 		expected.addGroup(group);
518 		
519 		final Model actual = this.parser.parse();
520 		assertEquals(expected, actual);
521 		assertEquals(0, this.parser.getExceptions().size());
522 	}
523 	
524 	/**
525 	 * Group:group=[Class:class={Attribute:String***;};];.
526 	 * 
527 	 * @throws Exception
528 	 *             : {@link NoValidTokenStreamException}
529 	 */
530 	@Test
531 	public void testAttributeWithListInList() throws Exception {
532 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
533 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
534 		final IdentifierToken attributeIdentifier =
535 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
536 		this.stream.add(groupIdentifier);
537 		this.stream.add(this.colonToken);
538 		this.stream.add(this.groupToken);
539 		this.stream.add(this.equalToken);
540 		this.stream.add(this.squareBracketOpenToken);
541 		this.stream.add(classIdentifier);
542 		this.stream.add(this.colonToken);
543 		this.stream.add(this.classToken);
544 		this.stream.add(this.equalToken);
545 		this.stream.add(this.curlyBracketOpenToken);
546 		this.stream.add(attributeIdentifier);
547 		this.stream.add(this.colonToken);
548 		this.stream.add(this.stringIdentifier);
549 		this.stream.add(this.asteriskToken);
550 		this.stream.add(this.asteriskToken);
551 		this.stream.add(this.asteriskToken);
552 		this.stream.add(this.semicolonToken);
553 		this.stream.add(this.curlyBracketCloseToken);
554 		this.stream.add(this.semicolonToken);
555 		this.stream.add(this.squareBracketCloseToken);
556 		this.stream.add(this.semicolonToken);
557 		this.stream.add(this.endToken);
558 		
559 		final Vector<GroupElement> groupVector = new Vector<>();
560 		final Vector<Attribute> attributes = new Vector<>();
561 		
562 		final Name groupName = UnqualifiedName.create(groupIdentifier);
563 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
564 		
565 		final Name className = groupName.addName(classIdentifier);
566 		final ClassType classModel =
567 				RegularClassType.create(
568 						className,
569 						new Vector<ClassModifier>(),
570 						attributes,
571 						new Vector<Type>(),
572 						new Vector<Operation>(),
573 						new Vector<Constructor>(),
574 						classIdentifier,
575 						
576 						new Vector<ClassType>());
577 		
578 		final ByNameState attributeReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
579 		final TypeProxy attributeType = TypeProxy.create(this.stringIdentifier, attributeReferenceState);
580 		final ListType list1 = ListType.create(this.stringIdentifier, attributeType);
581 		final ListType list2 = ListType.create(this.stringIdentifier, list1);
582 		final ListType list3 = ListType.create(this.stringIdentifier, list2);
583 		
584 		final Attribute attribute =
585 				Attribute.create("Attribute", list3, new Vector<AttributeModifier>(), attributeIdentifier);
586 		attributes.add(attribute);
587 		groupVector.add(classModel);
588 		final Model expected = Model.create(groupIdentifier);
589 		expected.addGroup(group);
590 		
591 		final Model actual = this.parser.parse();
592 		assertEquals(expected, actual);
593 		assertEquals(0, this.parser.getExceptions().size());
594 	}
595 	
596 	/**
597 	 * Group:group=[Class:class={Attribute:();};];.
598 	 * 
599 	 * @throws Exception
600 	 *             : {@link NoValidTokenStreamException}
601 	 */
602 	@Test
603 	public void testAttributeWithEmptyProduct() throws Exception {
604 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
605 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
606 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
607 		this.stream.add(groupIdentifier);
608 		this.stream.add(this.colonToken);
609 		this.stream.add(this.groupToken);
610 		this.stream.add(this.equalToken);
611 		this.stream.add(this.squareBracketOpenToken);
612 		this.stream.add(classIdentifier);
613 		this.stream.add(this.colonToken);
614 		this.stream.add(this.classToken);
615 		this.stream.add(this.equalToken);
616 		this.stream.add(this.curlyBracketOpenToken);
617 		this.stream.add(attributeIdentifier);
618 		this.stream.add(this.colonToken);
619 		this.stream.add(this.bracketOpenToken);
620 		this.stream.add(this.bracketCloseToken);
621 		this.stream.add(this.semicolonToken);
622 		this.stream.add(this.curlyBracketCloseToken);
623 		this.stream.add(this.semicolonToken);
624 		this.stream.add(this.squareBracketCloseToken);
625 		this.stream.add(this.semicolonToken);
626 		this.stream.add(this.endToken);
627 		
628 		final Vector<GroupElement> groupVector = new Vector<>();
629 		final Vector<Attribute> attributes = new Vector<>();
630 		
631 		final Name groupName = UnqualifiedName.create(groupIdentifier);
632 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
633 		
634 		final Name className = groupName.addName(classIdentifier);
635 		final ClassType classModel =
636 				RegularClassType.create(
637 						className,
638 						new Vector<ClassModifier>(),
639 						attributes,
640 						new Vector<Type>(),
641 						new Vector<Operation>(),
642 						new Vector<Constructor>(),
643 						classIdentifier,
644 						
645 						new Vector<ClassType>());
646 		
647 		final ProductType product = ProductType.create(this.bracketOpenToken);
648 		
649 		final Attribute attribute =
650 				Attribute.create("Attribute", product, new Vector<AttributeModifier>(), attributeIdentifier);
651 		attributes.add(attribute);
652 		groupVector.add(classModel);
653 		final Model expected = Model.create(groupIdentifier);
654 		expected.addGroup(group);
655 		
656 		final Model actual = this.parser.parse();
657 		assertEquals(expected, actual);
658 		assertEquals(0, this.parser.getExceptions().size());
659 	}
660 	
661 	/**
662 	 * Group:group=[Class:class={Attribute:(name:String,count:Integer)*;};];.
663 	 * 
664 	 * @throws Exception
665 	 *             : {@link NoValidTokenStreamException}
666 	 */
667 	@Test
668 	public void testAttributeWithListOnProduct() throws Exception {
669 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
670 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
671 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
672 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
673 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
674 		this.stream.add(groupIdentifier);
675 		this.stream.add(this.colonToken);
676 		this.stream.add(this.groupToken);
677 		this.stream.add(this.equalToken);
678 		this.stream.add(this.squareBracketOpenToken);
679 		this.stream.add(classIdentifier);
680 		this.stream.add(this.colonToken);
681 		this.stream.add(this.classToken);
682 		this.stream.add(this.equalToken);
683 		this.stream.add(this.curlyBracketOpenToken);
684 		this.stream.add(attributeIdentifier);
685 		this.stream.add(this.colonToken);
686 		this.stream.add(this.bracketOpenToken);
687 		this.stream.add(nameIdentifier);
688 		this.stream.add(this.colonToken);
689 		this.stream.add(this.stringIdentifier);
690 		this.stream.add(this.commaToken);
691 		this.stream.add(countIdentifier);
692 		this.stream.add(this.colonToken);
693 		this.stream.add(this.integerIdentifier);
694 		this.stream.add(this.bracketCloseToken);
695 		this.stream.add(this.asteriskToken);
696 		this.stream.add(this.semicolonToken);
697 		this.stream.add(this.curlyBracketCloseToken);
698 		this.stream.add(this.semicolonToken);
699 		this.stream.add(this.squareBracketCloseToken);
700 		this.stream.add(this.semicolonToken);
701 		this.stream.add(this.endToken);
702 		
703 		final Vector<GroupElement> groupVector = new Vector<>();
704 		final Vector<Attribute> attributes = new Vector<>();
705 		
706 		final Name groupName = UnqualifiedName.create(groupIdentifier);
707 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
708 		
709 		final Name className = groupName.addName(classIdentifier);
710 		final ClassType classModel =
711 				RegularClassType.create(
712 						className,
713 						new Vector<ClassModifier>(),
714 						attributes,
715 						new Vector<Type>(),
716 						new Vector<Operation>(),
717 						new Vector<Constructor>(),
718 						classIdentifier,
719 						
720 						new Vector<ClassType>());
721 		
722 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
723 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
724 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
725 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
726 		
727 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
728 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
729 		final ProductType product = ProductType.create(this.bracketOpenToken);
730 		product.addElement(nameElement);
731 		product.addElement(countElement);
732 		
733 		final ListType list = ListType.create(this.bracketOpenToken, product);
734 		
735 		final Attribute attribute =
736 				Attribute.create("Attribute", list, new Vector<AttributeModifier>(), attributeIdentifier);
737 		attributes.add(attribute);
738 		groupVector.add(classModel);
739 		final Model expected = Model.create(groupIdentifier);
740 		expected.addGroup(group);
741 		
742 		final Model actual = this.parser.parse();
743 		assertEquals(expected, actual);
744 		assertEquals(0, this.parser.getExceptions().size());
745 	}
746 	
747 	/**
748 	 * Group:group=[Class:class={Attribute:(name:String,count:Integer)**;};];.
749 	 * 
750 	 * @throws Exception
751 	 *             : {@link NoValidTokenStreamException}
752 	 */
753 	@Test
754 	public void testAttributeWithMoreListsOnProduct() throws Exception {
755 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
756 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
757 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
758 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
759 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
760 		
761 		this.stream.add(groupIdentifier);
762 		this.stream.add(this.colonToken);
763 		this.stream.add(this.groupToken);
764 		this.stream.add(this.equalToken);
765 		this.stream.add(this.squareBracketOpenToken);
766 		this.stream.add(classIdentifier);
767 		this.stream.add(this.colonToken);
768 		this.stream.add(this.classToken);
769 		this.stream.add(this.equalToken);
770 		this.stream.add(this.curlyBracketOpenToken);
771 		this.stream.add(attributeIdentifier);
772 		this.stream.add(this.colonToken);
773 		this.stream.add(this.bracketOpenToken);
774 		this.stream.add(IdentifierToken.create("name", Position.create("", 1, 1, 0)));
775 		this.stream.add(this.colonToken);
776 		this.stream.add(this.stringIdentifier);
777 		this.stream.add(this.commaToken);
778 		this.stream.add(IdentifierToken.create("count", Position.create("", 1, 1, 0)));
779 		this.stream.add(this.colonToken);
780 		this.stream.add(this.integerIdentifier);
781 		this.stream.add(this.bracketCloseToken);
782 		this.stream.add(this.asteriskToken);
783 		this.stream.add(this.asteriskToken);
784 		this.stream.add(this.semicolonToken);
785 		this.stream.add(this.curlyBracketCloseToken);
786 		this.stream.add(this.semicolonToken);
787 		this.stream.add(this.squareBracketCloseToken);
788 		this.stream.add(this.semicolonToken);
789 		this.stream.add(this.endToken);
790 		
791 		final Vector<GroupElement> groupVector = new Vector<>();
792 		final Vector<Attribute> attributes = new Vector<>();
793 		
794 		final Name groupName = UnqualifiedName.create(groupIdentifier);
795 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
796 		
797 		final Name className = groupName.addName(classIdentifier);
798 		final ClassType classModel =
799 				RegularClassType.create(
800 						className,
801 						new Vector<ClassModifier>(),
802 						attributes,
803 						new Vector<Type>(),
804 						new Vector<Operation>(),
805 						new Vector<Constructor>(),
806 						classIdentifier,
807 						
808 						new Vector<ClassType>());
809 		
810 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
811 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
812 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
813 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
814 		
815 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
816 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
817 		final ProductType product = ProductType.create(this.bracketOpenToken);
818 		product.addElement(nameElement);
819 		product.addElement(countElement);
820 		
821 		final ListType list = ListType.create(this.bracketOpenToken, product);
822 		final ListType list2 = ListType.create(this.bracketOpenToken, list);
823 		
824 		final Attribute attribute =
825 				Attribute.create("Attribute", list2, new Vector<AttributeModifier>(), attributeIdentifier);
826 		attributes.add(attribute);
827 		groupVector.add(classModel);
828 		final Model expected = Model.create(groupIdentifier);
829 		expected.addGroup(group);
830 		
831 		final Model actual = this.parser.parse();
832 		assertEquals(expected, actual);
833 		assertEquals(0, this.parser.getExceptions().size());
834 	}
835 	
836 	/**
837 	 * Group:group=[Class:class={Attribute:{True, False}**;};];.
838 	 * 
839 	 * @throws Exception
840 	 *             : {@link NoValidTokenStreamException}
841 	 */
842 	@Test
843 	public void testAttributeWithMoreListsOnSum() throws Exception {
844 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
845 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
846 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
847 		final IdentifierToken trueIdentifier = IdentifierToken.create("true", Position.create("", 1, 1, 0));
848 		final IdentifierToken falseIdentifier = IdentifierToken.create("false", Position.create("", 1, 1, 0));
849 		
850 		this.stream.add(groupIdentifier);
851 		this.stream.add(this.colonToken);
852 		this.stream.add(this.groupToken);
853 		this.stream.add(this.equalToken);
854 		this.stream.add(this.squareBracketOpenToken);
855 		this.stream.add(classIdentifier);
856 		this.stream.add(this.colonToken);
857 		this.stream.add(this.classToken);
858 		this.stream.add(this.equalToken);
859 		this.stream.add(this.curlyBracketOpenToken);
860 		this.stream.add(attributeIdentifier);
861 		this.stream.add(this.colonToken);
862 		this.stream.add(this.curlyBracketOpenToken);
863 		this.stream.add(trueIdentifier);
864 		this.stream.add(this.commaToken);
865 		this.stream.add(falseIdentifier);
866 		this.stream.add(this.curlyBracketCloseToken);
867 		this.stream.add(this.asteriskToken);
868 		this.stream.add(this.asteriskToken);
869 		this.stream.add(this.semicolonToken);
870 		this.stream.add(this.curlyBracketCloseToken);
871 		this.stream.add(this.semicolonToken);
872 		this.stream.add(this.squareBracketCloseToken);
873 		this.stream.add(this.semicolonToken);
874 		this.stream.add(this.endToken);
875 		
876 		final Vector<GroupElement> groupVector = new Vector<>();
877 		final Vector<Attribute> attributes = new Vector<>();
878 		
879 		final Name groupName = UnqualifiedName.create(groupIdentifier);
880 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
881 		
882 		final Name className = groupName.addName(classIdentifier);
883 		final ClassType classModel =
884 				RegularClassType.create(
885 						className,
886 						new Vector<ClassModifier>(),
887 						attributes,
888 						new Vector<Type>(),
889 						new Vector<Operation>(),
890 						new Vector<Constructor>(),
891 						classIdentifier,
892 						
893 						new Vector<ClassType>());
894 		
895 		final ByNameState trueReferenceState = ByNameState.create(UnqualifiedName.create(trueIdentifier));
896 		final TypeProxy trueType = TypeProxy.create(trueIdentifier, trueReferenceState);
897 		final ByNameState falseReferenceState = ByNameState.create(UnqualifiedName.create(falseIdentifier));
898 		final TypeProxy falseType = TypeProxy.create(falseIdentifier, falseReferenceState);
899 		
900 		final SumType sum = SumType.create(this.curlyBracketOpenToken);
901 		sum.getElements().add(trueType);
902 		sum.getElements().add(falseType);
903 		
904 		final ListType list = ListType.create(this.bracketOpenToken, sum);
905 		final ListType list2 = ListType.create(this.bracketOpenToken, list);
906 		
907 		final Attribute attribute =
908 				Attribute.create("Attribute", list2, new Vector<AttributeModifier>(), attributeIdentifier);
909 		attributes.add(attribute);
910 		groupVector.add(classModel);
911 		final Model expected = Model.create(groupIdentifier);
912 		expected.addGroup(group);
913 		
914 		final Model actual = this.parser.parse();
915 		assertEquals(expected, actual);
916 		assertEquals(0, this.parser.getExceptions().size());
917 	}
918 	
919 	/**
920 	 * Group:group=[Class:class={Attribute:[Integer->String];};];.
921 	 * 
922 	 * @throws Exception
923 	 *             : {@link NoValidTokenStreamException}
924 	 */
925 	@Test
926 	public void testAttributeMap() throws Exception {
927 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
928 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
929 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
930 		
931 		this.stream.add(groupIdentifier);
932 		this.stream.add(this.colonToken);
933 		this.stream.add(this.groupToken);
934 		this.stream.add(this.equalToken);
935 		this.stream.add(this.squareBracketOpenToken);
936 		this.stream.add(classIdentifier);
937 		this.stream.add(this.colonToken);
938 		this.stream.add(this.classToken);
939 		this.stream.add(this.equalToken);
940 		this.stream.add(this.curlyBracketOpenToken);
941 		this.stream.add(attributeIdentifier);
942 		this.stream.add(this.colonToken);
943 		this.stream.add(this.squareBracketOpenToken);
944 		this.stream.add(this.integerIdentifier);
945 		this.stream.add(this.arrowToken);
946 		this.stream.add(this.stringIdentifier);
947 		this.stream.add(this.squareBracketCloseToken);
948 		this.stream.add(this.semicolonToken);
949 		this.stream.add(this.curlyBracketCloseToken);
950 		this.stream.add(this.semicolonToken);
951 		this.stream.add(this.squareBracketCloseToken);
952 		this.stream.add(this.semicolonToken);
953 		this.stream.add(this.endToken);
954 		
955 		final Vector<GroupElement> groupVector = new Vector<>();
956 		final Vector<Attribute> attributes = new Vector<>();
957 		
958 		final Name groupName = UnqualifiedName.create(groupIdentifier);
959 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
960 		
961 		final Name className = groupName.addName(classIdentifier);
962 		final ClassType classModel =
963 				RegularClassType.create(
964 						className,
965 						new Vector<ClassModifier>(),
966 						attributes,
967 						new Vector<Type>(),
968 						new Vector<Operation>(),
969 						new Vector<Constructor>(),
970 						classIdentifier,
971 						
972 						new Vector<ClassType>());
973 		
974 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
975 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
976 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
977 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
978 		
979 		final MapType map = MapType.create(this.integerIdentifier, integerType, stringType);
980 		
981 		final Attribute attribute =
982 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
983 		attributes.add(attribute);
984 		groupVector.add(classModel);
985 		final Model expected = Model.create(groupIdentifier);
986 		expected.addGroup(group);
987 		
988 		final Model actual = this.parser.parse();
989 		assertEquals(expected, actual);
990 		assertEquals(0, this.parser.getExceptions().size());
991 	}
992 	
993 	/**
994 	 * Group:group=[Class:class={Attribute:[Integer*->String];};];.
995 	 * 
996 	 * @throws Exception
997 	 *             : {@link NoValidTokenStreamException}
998 	 */
999 	@Test
1000 	public void testAttributeWithMapAndListAsKey() throws Exception {
1001 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1002 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1003 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1004 		
1005 		this.stream.add(groupIdentifier);
1006 		this.stream.add(this.colonToken);
1007 		this.stream.add(this.groupToken);
1008 		this.stream.add(this.equalToken);
1009 		this.stream.add(this.squareBracketOpenToken);
1010 		this.stream.add(classIdentifier);
1011 		this.stream.add(this.colonToken);
1012 		this.stream.add(this.classToken);
1013 		this.stream.add(this.equalToken);
1014 		this.stream.add(this.curlyBracketOpenToken);
1015 		this.stream.add(attributeIdentifier);
1016 		this.stream.add(this.colonToken);
1017 		this.stream.add(this.squareBracketOpenToken);
1018 		this.stream.add(this.integerIdentifier);
1019 		this.stream.add(this.asteriskToken);
1020 		this.stream.add(this.arrowToken);
1021 		this.stream.add(this.stringIdentifier);
1022 		this.stream.add(this.squareBracketCloseToken);
1023 		this.stream.add(this.semicolonToken);
1024 		this.stream.add(this.curlyBracketCloseToken);
1025 		this.stream.add(this.semicolonToken);
1026 		this.stream.add(this.squareBracketCloseToken);
1027 		this.stream.add(this.semicolonToken);
1028 		this.stream.add(this.endToken);
1029 		
1030 		final Vector<GroupElement> groupVector = new Vector<>();
1031 		final Vector<Attribute> attributes = new Vector<>();
1032 		
1033 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1034 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1035 		
1036 		final Name className = groupName.addName(classIdentifier);
1037 		final ClassType classModel =
1038 				RegularClassType.create(
1039 						className,
1040 						new Vector<ClassModifier>(),
1041 						attributes,
1042 						new Vector<Type>(),
1043 						new Vector<Operation>(),
1044 						new Vector<Constructor>(),
1045 						classIdentifier,
1046 						
1047 						new Vector<ClassType>());
1048 		
1049 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1050 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1051 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1052 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1053 		
1054 		final ListType list = ListType.create(this.integerIdentifier, integerType);
1055 		
1056 		final MapType map = MapType.create(this.integerIdentifier, list, stringType);
1057 		
1058 		final Attribute attribute =
1059 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
1060 		attributes.add(attribute);
1061 		groupVector.add(classModel);
1062 		final Model expected = Model.create(groupIdentifier);
1063 		expected.addGroup(group);
1064 		
1065 		final Model actual = this.parser.parse();
1066 		assertEquals(expected, actual);
1067 		assertEquals(0, this.parser.getExceptions().size());
1068 	}
1069 	
1070 	/**
1071 	 * Group:group=[Class:class={Attribute:[Integer->String]*;};];.
1072 	 * 
1073 	 * @throws Exception
1074 	 *             : {@link NoValidTokenStreamException}
1075 	 */
1076 	@Test
1077 	public void testAttributeWithListOfMap() throws Exception {
1078 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1079 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1080 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1081 		
1082 		this.stream.add(groupIdentifier);
1083 		this.stream.add(this.colonToken);
1084 		this.stream.add(this.groupToken);
1085 		this.stream.add(this.equalToken);
1086 		this.stream.add(this.squareBracketOpenToken);
1087 		this.stream.add(classIdentifier);
1088 		this.stream.add(this.colonToken);
1089 		this.stream.add(this.classToken);
1090 		this.stream.add(this.equalToken);
1091 		this.stream.add(this.curlyBracketOpenToken);
1092 		this.stream.add(attributeIdentifier);
1093 		this.stream.add(this.colonToken);
1094 		this.stream.add(this.squareBracketOpenToken);
1095 		this.stream.add(this.integerIdentifier);
1096 		this.stream.add(this.arrowToken);
1097 		this.stream.add(this.stringIdentifier);
1098 		this.stream.add(this.squareBracketCloseToken);
1099 		this.stream.add(this.asteriskToken);
1100 		this.stream.add(this.semicolonToken);
1101 		this.stream.add(this.curlyBracketCloseToken);
1102 		this.stream.add(this.semicolonToken);
1103 		this.stream.add(this.squareBracketCloseToken);
1104 		this.stream.add(this.semicolonToken);
1105 		this.stream.add(this.endToken);
1106 		
1107 		final Vector<GroupElement> groupVector = new Vector<>();
1108 		final Vector<Attribute> attributes = new Vector<>();
1109 		
1110 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1111 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1112 		
1113 		final Name className = groupName.addName(classIdentifier);
1114 		final ClassType classModel =
1115 				RegularClassType.create(
1116 						className,
1117 						new Vector<ClassModifier>(),
1118 						attributes,
1119 						new Vector<Type>(),
1120 						new Vector<Operation>(),
1121 						new Vector<Constructor>(),
1122 						classIdentifier,
1123 						
1124 						new Vector<ClassType>());
1125 		
1126 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1127 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1128 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1129 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1130 		
1131 		final MapType map = MapType.create(this.integerIdentifier, integerType, stringType);
1132 		
1133 		final ListType list = ListType.create(this.bracketOpenToken, map);
1134 		
1135 		final Attribute attribute =
1136 				Attribute.create("Attribute", list, new Vector<AttributeModifier>(), attributeIdentifier);
1137 		attributes.add(attribute);
1138 		groupVector.add(classModel);
1139 		final Model expected = Model.create(groupIdentifier);
1140 		expected.addGroup(group);
1141 		
1142 		final Model actual = this.parser.parse();
1143 		assertEquals(expected, actual);
1144 		assertEquals(0, this.parser.getExceptions().size());
1145 	}
1146 	
1147 	/**
1148 	 * Group:group=[Class:class={Attribute:[Integer->String]*;;];.
1149 	 * 
1150 	 * @throws Exception
1151 	 *             : {@link NoValidTokenStreamException}
1152 	 */
1153 	@Test
1154 	public void testAttributeWithListOfMapButMissingBracketClose() throws Exception {
1155 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1156 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1157 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1158 		
1159 		this.stream.add(groupIdentifier);
1160 		this.stream.add(this.colonToken);
1161 		this.stream.add(this.groupToken);
1162 		this.stream.add(this.equalToken);
1163 		this.stream.add(this.squareBracketOpenToken);
1164 		this.stream.add(classIdentifier);
1165 		this.stream.add(this.colonToken);
1166 		this.stream.add(this.classToken);
1167 		this.stream.add(this.equalToken);
1168 		this.stream.add(this.curlyBracketOpenToken);
1169 		this.stream.add(attributeIdentifier);
1170 		this.stream.add(this.colonToken);
1171 		this.stream.add(this.squareBracketOpenToken);
1172 		this.stream.add(this.integerIdentifier);
1173 		this.stream.add(this.arrowToken);
1174 		this.stream.add(this.stringIdentifier);
1175 		this.stream.add(this.squareBracketCloseToken);
1176 		this.stream.add(this.asteriskToken);
1177 		this.stream.add(this.semicolonToken);
1178 		this.stream.add(this.semicolonToken);
1179 		this.stream.add(this.squareBracketCloseToken);
1180 		this.stream.add(this.semicolonToken);
1181 		this.stream.add(this.endToken);
1182 		
1183 		try {
1184 			this.parser.parse();
1185 		} catch (final NoValidTokenStreamException e) {
1186 			// Erwartet
1187 			return;
1188 		}
1189 		fail();
1190 	}
1191 	
1192 	/**
1193 	 * Group:group=[Class:class={Attribute:[String->(name:String,count:Integer)] ;};];.
1194 	 * 
1195 	 * @throws Exception
1196 	 *             : {@link NoValidTokenStreamException}
1197 	 */
1198 	@Test
1199 	public void testAttributeWithMapOnProduct() throws Exception {
1200 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1201 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1202 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1203 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
1204 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
1205 		this.stream.add(groupIdentifier);
1206 		this.stream.add(this.colonToken);
1207 		this.stream.add(this.groupToken);
1208 		this.stream.add(this.equalToken);
1209 		this.stream.add(this.squareBracketOpenToken);
1210 		this.stream.add(classIdentifier);
1211 		this.stream.add(this.colonToken);
1212 		this.stream.add(this.classToken);
1213 		this.stream.add(this.equalToken);
1214 		this.stream.add(this.curlyBracketOpenToken);
1215 		this.stream.add(attributeIdentifier);
1216 		this.stream.add(this.colonToken);
1217 		this.stream.add(this.squareBracketOpenToken);
1218 		this.stream.add(this.stringIdentifier);
1219 		this.stream.add(this.arrowToken);
1220 		this.stream.add(this.bracketOpenToken);
1221 		this.stream.add(nameIdentifier);
1222 		this.stream.add(this.colonToken);
1223 		this.stream.add(this.stringIdentifier);
1224 		this.stream.add(this.commaToken);
1225 		this.stream.add(countIdentifier);
1226 		this.stream.add(this.colonToken);
1227 		this.stream.add(this.integerIdentifier);
1228 		this.stream.add(this.bracketCloseToken);
1229 		this.stream.add(this.squareBracketCloseToken);
1230 		this.stream.add(this.semicolonToken);
1231 		this.stream.add(this.curlyBracketCloseToken);
1232 		this.stream.add(this.semicolonToken);
1233 		this.stream.add(this.squareBracketCloseToken);
1234 		this.stream.add(this.semicolonToken);
1235 		this.stream.add(this.endToken);
1236 		
1237 		final Vector<GroupElement> groupVector = new Vector<>();
1238 		final Vector<Attribute> attributes = new Vector<>();
1239 		
1240 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1241 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1242 		
1243 		final Name className = groupName.addName(classIdentifier);
1244 		final ClassType classModel =
1245 				RegularClassType.create(
1246 						className,
1247 						new Vector<ClassModifier>(),
1248 						attributes,
1249 						new Vector<Type>(),
1250 						new Vector<Operation>(),
1251 						new Vector<Constructor>(),
1252 						classIdentifier,
1253 						
1254 						new Vector<ClassType>());
1255 		
1256 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1257 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1258 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1259 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1260 		
1261 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
1262 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
1263 		final ProductType product = ProductType.create(this.bracketOpenToken);
1264 		product.addElement(nameElement);
1265 		product.addElement(countElement);
1266 		
1267 		final MapType map = MapType.create(this.stringIdentifier, stringType, product);
1268 		
1269 		final Attribute attribute =
1270 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
1271 		attributes.add(attribute);
1272 		groupVector.add(classModel);
1273 		final Model expected = Model.create(groupIdentifier);
1274 		expected.addGroup(group);
1275 		
1276 		final Model actual = this.parser.parse();
1277 		assertEquals(expected, actual);
1278 		assertEquals(0, this.parser.getExceptions().size());
1279 	}
1280 	
1281 	/**
1282 	 * Group:group=[Class:class={Attribute:[(name:String,count:Integer)->Integer* ];};];.
1283 	 * 
1284 	 * @throws Exception
1285 	 *             : {@link NoValidTokenStreamException}
1286 	 */
1287 	@Test
1288 	public void testAttributeWithMapOnProductAsKey() throws Exception {
1289 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1290 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1291 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1292 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
1293 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
1294 		this.stream.add(groupIdentifier);
1295 		this.stream.add(this.colonToken);
1296 		this.stream.add(this.groupToken);
1297 		this.stream.add(this.equalToken);
1298 		this.stream.add(this.squareBracketOpenToken);
1299 		this.stream.add(classIdentifier);
1300 		this.stream.add(this.colonToken);
1301 		this.stream.add(this.classToken);
1302 		this.stream.add(this.equalToken);
1303 		this.stream.add(this.curlyBracketOpenToken);
1304 		this.stream.add(attributeIdentifier);
1305 		this.stream.add(this.colonToken);
1306 		this.stream.add(this.squareBracketOpenToken);
1307 		this.stream.add(this.bracketOpenToken);
1308 		this.stream.add(nameIdentifier);
1309 		this.stream.add(this.colonToken);
1310 		this.stream.add(this.stringIdentifier);
1311 		this.stream.add(this.commaToken);
1312 		this.stream.add(countIdentifier);
1313 		this.stream.add(this.colonToken);
1314 		this.stream.add(this.integerIdentifier);
1315 		this.stream.add(this.bracketCloseToken);
1316 		this.stream.add(this.arrowToken);
1317 		this.stream.add(this.integerIdentifier);
1318 		this.stream.add(this.squareBracketCloseToken);
1319 		this.stream.add(this.semicolonToken);
1320 		this.stream.add(this.curlyBracketCloseToken);
1321 		this.stream.add(this.semicolonToken);
1322 		this.stream.add(this.squareBracketCloseToken);
1323 		this.stream.add(this.semicolonToken);
1324 		this.stream.add(this.endToken);
1325 		
1326 		final Vector<GroupElement> groupVector = new Vector<>();
1327 		final Vector<Attribute> attributes = new Vector<>();
1328 		
1329 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1330 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1331 		
1332 		final Name className = groupName.addName(classIdentifier);
1333 		final ClassType classModel =
1334 				RegularClassType.create(
1335 						className,
1336 						new Vector<ClassModifier>(),
1337 						attributes,
1338 						new Vector<Type>(),
1339 						new Vector<Operation>(),
1340 						new Vector<Constructor>(),
1341 						classIdentifier,
1342 						
1343 						new Vector<ClassType>());
1344 		
1345 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1346 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1347 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1348 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1349 		
1350 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
1351 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
1352 		final ProductType product = ProductType.create(this.bracketOpenToken);
1353 		product.addElement(nameElement);
1354 		product.addElement(countElement);
1355 		
1356 		final MapType map = MapType.create(this.bracketOpenToken, product, integerType);
1357 		
1358 		final Attribute attribute =
1359 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
1360 		attributes.add(attribute);
1361 		groupVector.add(classModel);
1362 		final Model expected = Model.create(groupIdentifier);
1363 		expected.addGroup(group);
1364 		
1365 		final Model actual = this.parser.parse();
1366 		assertEquals(expected, actual);
1367 		assertEquals(0, this.parser.getExceptions().size());
1368 	}
1369 	
1370 	/**
1371 	 * Group:group=[Class:class={Attribute:(name:.
1372 	 * 
1373 	 * @throws Exception
1374 	 *             : {@link NoValidTokenStreamException}
1375 	 */
1376 	@Test
1377 	public void testAttributeWithMapOnBeginningOfProduct() throws Exception {
1378 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1379 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1380 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1381 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
1382 		this.stream.add(groupIdentifier);
1383 		this.stream.add(this.colonToken);
1384 		this.stream.add(this.groupToken);
1385 		this.stream.add(this.equalToken);
1386 		this.stream.add(this.squareBracketOpenToken);
1387 		this.stream.add(classIdentifier);
1388 		this.stream.add(this.colonToken);
1389 		this.stream.add(this.classToken);
1390 		this.stream.add(this.equalToken);
1391 		this.stream.add(this.curlyBracketOpenToken);
1392 		this.stream.add(attributeIdentifier);
1393 		this.stream.add(this.colonToken);
1394 		this.stream.add(this.bracketOpenToken);
1395 		this.stream.add(nameIdentifier);
1396 		this.stream.add(this.colonToken);
1397 		this.stream.add(this.endToken);
1398 		
1399 		try {
1400 			this.parser.parse();
1401 			fail();
1402 		} catch (final NoValidTokenStreamException e) {
1403 			assertEquals(3, this.parser.getExceptions().size());
1404 		}
1405 	}
1406 	
1407 	/**
1408 	 * Group:group=[Class:class={Attribute:[()->Integer];};];.
1409 	 * 
1410 	 * @throws Exception
1411 	 *             : {@link NoValidTokenStreamException}
1412 	 */
1413 	@Test
1414 	public void testAttributeWithMapOnEmptyProductAsKey() throws Exception {
1415 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1416 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1417 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1418 		
1419 		this.stream.add(groupIdentifier);
1420 		this.stream.add(this.colonToken);
1421 		this.stream.add(this.groupToken);
1422 		this.stream.add(this.equalToken);
1423 		this.stream.add(this.squareBracketOpenToken);
1424 		this.stream.add(classIdentifier);
1425 		this.stream.add(this.colonToken);
1426 		this.stream.add(this.classToken);
1427 		this.stream.add(this.equalToken);
1428 		this.stream.add(this.curlyBracketOpenToken);
1429 		this.stream.add(attributeIdentifier);
1430 		this.stream.add(this.colonToken);
1431 		this.stream.add(this.squareBracketOpenToken);
1432 		this.stream.add(this.bracketOpenToken);
1433 		this.stream.add(this.bracketCloseToken);
1434 		this.stream.add(this.arrowToken);
1435 		this.stream.add(this.integerIdentifier);
1436 		this.stream.add(this.squareBracketCloseToken);
1437 		this.stream.add(this.semicolonToken);
1438 		this.stream.add(this.curlyBracketCloseToken);
1439 		this.stream.add(this.semicolonToken);
1440 		this.stream.add(this.squareBracketCloseToken);
1441 		this.stream.add(this.semicolonToken);
1442 		this.stream.add(this.endToken);
1443 		
1444 		final Vector<GroupElement> groupVector = new Vector<>();
1445 		final Vector<Attribute> attributes = new Vector<>();
1446 		
1447 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1448 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1449 		
1450 		final Name className = groupName.addName(classIdentifier);
1451 		final ClassType classModel =
1452 				RegularClassType.create(
1453 						className,
1454 						new Vector<ClassModifier>(),
1455 						attributes,
1456 						new Vector<Type>(),
1457 						new Vector<Operation>(),
1458 						new Vector<Constructor>(),
1459 						classIdentifier,
1460 						
1461 						new Vector<ClassType>());
1462 		
1463 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1464 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1465 		
1466 		final ProductType product = ProductType.create(this.bracketOpenToken);
1467 		
1468 		final MapType map = MapType.create(this.bracketOpenToken, product, integerType);
1469 		
1470 		final Attribute attribute =
1471 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
1472 		attributes.add(attribute);
1473 		groupVector.add(classModel);
1474 		final Model expected = Model.create(groupIdentifier);
1475 		expected.addGroup(group);
1476 		
1477 		final Model actual = this.parser.parse();
1478 		assertEquals(expected, actual);
1479 		assertEquals(0, this.parser.getExceptions().size());
1480 	}
1481 	
1482 	/**
1483 	 * Group:group=[Class:class={Attribute:[(name:String,count:Integer)->Integer ]*;};];.
1484 	 * 
1485 	 * @throws Exception
1486 	 *             : {@link NoValidTokenStreamException}
1487 	 */
1488 	@Test
1489 	public void testAttributeWithListOfMapAndProductAsKey() throws Exception {
1490 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1491 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1492 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1493 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
1494 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
1495 		this.stream.add(groupIdentifier);
1496 		this.stream.add(this.colonToken);
1497 		this.stream.add(this.groupToken);
1498 		this.stream.add(this.equalToken);
1499 		this.stream.add(this.squareBracketOpenToken);
1500 		this.stream.add(classIdentifier);
1501 		this.stream.add(this.colonToken);
1502 		this.stream.add(this.classToken);
1503 		this.stream.add(this.equalToken);
1504 		this.stream.add(this.curlyBracketOpenToken);
1505 		this.stream.add(attributeIdentifier);
1506 		this.stream.add(this.colonToken);
1507 		this.stream.add(this.squareBracketOpenToken);
1508 		this.stream.add(this.bracketOpenToken);
1509 		this.stream.add(nameIdentifier);
1510 		this.stream.add(this.colonToken);
1511 		this.stream.add(this.stringIdentifier);
1512 		this.stream.add(this.commaToken);
1513 		this.stream.add(countIdentifier);
1514 		this.stream.add(this.colonToken);
1515 		this.stream.add(this.integerIdentifier);
1516 		this.stream.add(this.bracketCloseToken);
1517 		this.stream.add(this.arrowToken);
1518 		this.stream.add(this.integerIdentifier);
1519 		this.stream.add(this.squareBracketCloseToken);
1520 		this.stream.add(this.asteriskToken);
1521 		this.stream.add(this.semicolonToken);
1522 		this.stream.add(this.curlyBracketCloseToken);
1523 		this.stream.add(this.semicolonToken);
1524 		this.stream.add(this.squareBracketCloseToken);
1525 		this.stream.add(this.semicolonToken);
1526 		this.stream.add(this.endToken);
1527 		
1528 		final Vector<GroupElement> groupVector = new Vector<>();
1529 		final Vector<Attribute> attributes = new Vector<>();
1530 		
1531 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1532 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1533 		
1534 		final Name className = groupName.addName(classIdentifier);
1535 		final ClassType classModel =
1536 				RegularClassType.create(
1537 						className,
1538 						new Vector<ClassModifier>(),
1539 						attributes,
1540 						new Vector<Type>(),
1541 						new Vector<Operation>(),
1542 						new Vector<Constructor>(),
1543 						classIdentifier,
1544 						
1545 						new Vector<ClassType>());
1546 		
1547 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1548 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1549 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1550 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1551 		
1552 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
1553 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
1554 		final ProductType product = ProductType.create(this.bracketOpenToken);
1555 		product.addElement(nameElement);
1556 		product.addElement(countElement);
1557 		
1558 		final MapType map = MapType.create(this.bracketOpenToken, product, integerType);
1559 		final ListType list = ListType.create(this.bracketOpenToken, map);
1560 		
1561 		final Attribute attribute =
1562 				Attribute.create("Attribute", list, new Vector<AttributeModifier>(), attributeIdentifier);
1563 		attributes.add(attribute);
1564 		groupVector.add(classModel);
1565 		final Model expected = Model.create(groupIdentifier);
1566 		expected.addGroup(group);
1567 		
1568 		final Model actual = this.parser.parse();
1569 		assertEquals(expected, actual);
1570 		assertEquals(0, this.parser.getExceptions().size());
1571 	}
1572 	
1573 	/**
1574 	 * Group:group=[Class:class={Attribute:[(name:String,count:Integer)->Integer ]**;};];.
1575 	 * 
1576 	 * @throws Exception
1577 	 *             : {@link NoValidTokenStreamException}
1578 	 */
1579 	@Test
1580 	public void testAttributeWithListOfListOfMapAndProductAsKey() throws Exception {
1581 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1582 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1583 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1584 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
1585 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
1586 		this.stream.add(groupIdentifier);
1587 		this.stream.add(this.colonToken);
1588 		this.stream.add(this.groupToken);
1589 		this.stream.add(this.equalToken);
1590 		this.stream.add(this.squareBracketOpenToken);
1591 		this.stream.add(classIdentifier);
1592 		this.stream.add(this.colonToken);
1593 		this.stream.add(this.classToken);
1594 		this.stream.add(this.equalToken);
1595 		this.stream.add(this.curlyBracketOpenToken);
1596 		this.stream.add(attributeIdentifier);
1597 		this.stream.add(this.colonToken);
1598 		this.stream.add(this.squareBracketOpenToken);
1599 		this.stream.add(this.bracketOpenToken);
1600 		this.stream.add(nameIdentifier);
1601 		this.stream.add(this.colonToken);
1602 		this.stream.add(this.stringIdentifier);
1603 		this.stream.add(this.commaToken);
1604 		this.stream.add(countIdentifier);
1605 		this.stream.add(this.colonToken);
1606 		this.stream.add(this.integerIdentifier);
1607 		this.stream.add(this.bracketCloseToken);
1608 		this.stream.add(this.arrowToken);
1609 		this.stream.add(this.integerIdentifier);
1610 		this.stream.add(this.squareBracketCloseToken);
1611 		this.stream.add(this.asteriskToken);
1612 		this.stream.add(this.asteriskToken);
1613 		this.stream.add(this.semicolonToken);
1614 		this.stream.add(this.curlyBracketCloseToken);
1615 		this.stream.add(this.semicolonToken);
1616 		this.stream.add(this.squareBracketCloseToken);
1617 		this.stream.add(this.semicolonToken);
1618 		this.stream.add(this.endToken);
1619 		
1620 		final Vector<GroupElement> groupVector = new Vector<>();
1621 		final Vector<Attribute> attributes = new Vector<>();
1622 		
1623 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1624 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1625 		
1626 		final Name className = groupName.addName(classIdentifier);
1627 		final ClassType classModel =
1628 				RegularClassType.create(
1629 						className,
1630 						new Vector<ClassModifier>(),
1631 						attributes,
1632 						new Vector<Type>(),
1633 						new Vector<Operation>(),
1634 						new Vector<Constructor>(),
1635 						classIdentifier,
1636 						
1637 						new Vector<ClassType>());
1638 		
1639 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1640 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1641 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1642 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1643 		
1644 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
1645 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
1646 		final ProductType product = ProductType.create(this.bracketOpenToken);
1647 		product.addElement(nameElement);
1648 		product.addElement(countElement);
1649 		
1650 		final MapType map = MapType.create(this.bracketOpenToken, product, integerType);
1651 		final ListType list = ListType.create(this.bracketOpenToken, map);
1652 		final ListType outerList = ListType.create(this.bracketOpenToken, list);
1653 		
1654 		final Attribute attribute =
1655 				Attribute.create("Attribute", outerList, new Vector<AttributeModifier>(), attributeIdentifier);
1656 		attributes.add(attribute);
1657 		groupVector.add(classModel);
1658 		final Model expected = Model.create(groupIdentifier);
1659 		expected.addGroup(group);
1660 		
1661 		final Model actual = this.parser.parse();
1662 		assertEquals(expected, actual);
1663 		assertEquals(0, this.parser.getExceptions().size());
1664 	}
1665 	
1666 	/**
1667 	 * Group:group=[Class:class={Attribute:[ [(name:String,count:Integer)->Integer]->String];};];.
1668 	 * 
1669 	 * @throws Exception
1670 	 *             : {@link NoValidTokenStreamException}
1671 	 */
1672 	@Test
1673 	public void testAttributeWithMapAndMapAsKey() throws Exception {
1674 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1675 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1676 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1677 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
1678 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
1679 		this.stream.add(groupIdentifier);
1680 		this.stream.add(this.colonToken);
1681 		this.stream.add(this.groupToken);
1682 		this.stream.add(this.equalToken);
1683 		this.stream.add(this.squareBracketOpenToken);
1684 		this.stream.add(classIdentifier);
1685 		this.stream.add(this.colonToken);
1686 		this.stream.add(this.classToken);
1687 		this.stream.add(this.equalToken);
1688 		this.stream.add(this.curlyBracketOpenToken);
1689 		this.stream.add(attributeIdentifier);
1690 		this.stream.add(this.colonToken);
1691 		this.stream.add(this.squareBracketOpenToken);
1692 		this.stream.add(this.squareBracketOpenToken);
1693 		this.stream.add(this.bracketOpenToken);
1694 		this.stream.add(nameIdentifier);
1695 		this.stream.add(this.colonToken);
1696 		this.stream.add(this.stringIdentifier);
1697 		this.stream.add(this.commaToken);
1698 		this.stream.add(countIdentifier);
1699 		this.stream.add(this.colonToken);
1700 		this.stream.add(this.integerIdentifier);
1701 		this.stream.add(this.bracketCloseToken);
1702 		this.stream.add(this.arrowToken);
1703 		this.stream.add(this.integerIdentifier);
1704 		this.stream.add(this.squareBracketCloseToken);
1705 		this.stream.add(this.arrowToken);
1706 		this.stream.add(this.stringIdentifier);
1707 		this.stream.add(this.squareBracketCloseToken);
1708 		this.stream.add(this.semicolonToken);
1709 		this.stream.add(this.curlyBracketCloseToken);
1710 		this.stream.add(this.semicolonToken);
1711 		this.stream.add(this.squareBracketCloseToken);
1712 		this.stream.add(this.semicolonToken);
1713 		this.stream.add(this.endToken);
1714 		
1715 		final Vector<GroupElement> groupVector = new Vector<>();
1716 		final Vector<Attribute> attributes = new Vector<>();
1717 		
1718 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1719 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1720 		
1721 		final Name className = groupName.addName(classIdentifier);
1722 		final ClassType classModel =
1723 				RegularClassType.create(
1724 						className,
1725 						new Vector<ClassModifier>(),
1726 						attributes,
1727 						new Vector<Type>(),
1728 						new Vector<Operation>(),
1729 						new Vector<Constructor>(),
1730 						classIdentifier,
1731 						
1732 						new Vector<ClassType>());
1733 		
1734 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1735 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1736 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1737 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1738 		
1739 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
1740 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
1741 		final ProductType product = ProductType.create(this.bracketOpenToken);
1742 		product.addElement(nameElement);
1743 		product.addElement(countElement);
1744 		
1745 		final MapType mapKey = MapType.create(this.bracketOpenToken, product, integerType);
1746 		final MapType map = MapType.create(this.bracketOpenToken, mapKey, stringType);
1747 		
1748 		final Attribute attribute =
1749 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
1750 		attributes.add(attribute);
1751 		groupVector.add(classModel);
1752 		final Model expected = Model.create(groupIdentifier);
1753 		expected.addGroup(group);
1754 		
1755 		final Model actual = this.parser.parse();
1756 		assertEquals(expected, actual);
1757 		assertEquals(0, this.parser.getExceptions().size());
1758 	}
1759 	
1760 	/**
1761 	 * Group:group=[Class:class={Attribute:[(name:String,count:Integer)* -> String];};];.
1762 	 * 
1763 	 * @throws Exception
1764 	 *             : {@link NoValidTokenStreamException}
1765 	 */
1766 	@Test
1767 	public void testAttributeWithMapAndListOfProductAsKey() throws Exception {
1768 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
1769 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
1770 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
1771 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
1772 		final IdentifierToken countIdentifier = IdentifierToken.create("count", Position.create("", 1, 1, 0));
1773 		this.stream.add(groupIdentifier);
1774 		this.stream.add(this.colonToken);
1775 		this.stream.add(this.groupToken);
1776 		this.stream.add(this.equalToken);
1777 		this.stream.add(this.squareBracketOpenToken);
1778 		this.stream.add(classIdentifier);
1779 		this.stream.add(this.colonToken);
1780 		this.stream.add(this.classToken);
1781 		this.stream.add(this.equalToken);
1782 		this.stream.add(this.curlyBracketOpenToken);
1783 		this.stream.add(attributeIdentifier);
1784 		this.stream.add(this.colonToken);
1785 		this.stream.add(this.squareBracketOpenToken);
1786 		this.stream.add(this.bracketOpenToken);
1787 		this.stream.add(nameIdentifier);
1788 		this.stream.add(this.colonToken);
1789 		this.stream.add(this.stringIdentifier);
1790 		this.stream.add(this.commaToken);
1791 		this.stream.add(countIdentifier);
1792 		this.stream.add(this.colonToken);
1793 		this.stream.add(this.integerIdentifier);
1794 		this.stream.add(this.bracketCloseToken);
1795 		this.stream.add(this.asteriskToken);
1796 		this.stream.add(this.arrowToken);
1797 		this.stream.add(this.stringIdentifier);
1798 		this.stream.add(this.squareBracketCloseToken);
1799 		this.stream.add(this.semicolonToken);
1800 		this.stream.add(this.curlyBracketCloseToken);
1801 		this.stream.add(this.semicolonToken);
1802 		this.stream.add(this.squareBracketCloseToken);
1803 		this.stream.add(this.semicolonToken);
1804 		this.stream.add(this.endToken);
1805 		
1806 		final Vector<GroupElement> groupVector = new Vector<>();
1807 		final Vector<Attribute> attributes = new Vector<>();
1808 		
1809 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1810 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1811 		
1812 		final Name className = groupName.addName(classIdentifier);
1813 		final ClassType classModel =
1814 				RegularClassType.create(
1815 						className,
1816 						new Vector<ClassModifier>(),
1817 						attributes,
1818 						new Vector<Type>(),
1819 						new Vector<Operation>(),
1820 						new Vector<Constructor>(),
1821 						classIdentifier,
1822 						
1823 						new Vector<ClassType>());
1824 		
1825 		final ByNameState stringReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1826 		final TypeProxy stringType = TypeProxy.create(this.stringIdentifier, stringReferenceState);
1827 		final ByNameState integerReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
1828 		final TypeProxy integerType = TypeProxy.create(this.integerIdentifier, integerReferenceState);
1829 		
1830 		final ProductElementType nameElement = ProductElementType.create("name", stringType, nameIdentifier);
1831 		final ProductElementType countElement = ProductElementType.create("count", integerType, countIdentifier);
1832 		final ProductType product = ProductType.create(this.bracketOpenToken);
1833 		product.addElement(nameElement);
1834 		product.addElement(countElement);
1835 		
1836 		final ListType productList = ListType.create(this.bracketOpenToken, product);
1837 		
1838 		final MapType map = MapType.create(this.bracketOpenToken, productList, stringType);
1839 		
1840 		final Attribute attribute =
1841 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
1842 		attributes.add(attribute);
1843 		groupVector.add(classModel);
1844 		final Model expected = Model.create(groupIdentifier);
1845 		expected.addGroup(group);
1846 		
1847 		final Model actual = this.parser.parse();
1848 		assertEquals(expected, actual);
1849 		assertEquals(0, this.parser.getExceptions().size());
1850 	}
1851 	
1852 	/**
1853 	 * Group:group=[Class:class={Attribute:Integer prior;};.
1854 	 * 
1855 	 * @throws Exception
1856 	 *             : {@link NoValidTokenStreamException}
1857 	 */
1858 	@Test
1859 	public void testAttributeWithModifier() throws Exception {
1860 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
1861 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
1862 		final IdentifierToken attributeIdentifier =
1863 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
1864 		this.stream.add(groupIdentifier);
1865 		this.stream.add(this.colonToken);
1866 		this.stream.add(this.groupToken);
1867 		this.stream.add(this.equalToken);
1868 		this.stream.add(this.squareBracketOpenToken);
1869 		this.stream.add(classIdentifier);
1870 		this.stream.add(this.colonToken);
1871 		this.stream.add(this.classToken);
1872 		this.stream.add(this.equalToken);
1873 		this.stream.add(this.curlyBracketOpenToken);
1874 		this.stream.add(attributeIdentifier);
1875 		this.stream.add(this.colonToken);
1876 		this.stream.add(this.stringIdentifier);
1877 		this.stream.add(PriorToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
1878 		this.stream.add(this.semicolonToken);
1879 		this.stream.add(this.curlyBracketCloseToken);
1880 		this.stream.add(this.semicolonToken);
1881 		this.stream.add(this.squareBracketCloseToken);
1882 		this.stream.add(this.semicolonToken);
1883 		this.stream.add(this.endToken);
1884 		
1885 		final Vector<GroupElement> groupVector = new Vector<>();
1886 		final Vector<Attribute> attributes = new Vector<>();
1887 		
1888 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1889 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1890 		
1891 		final Name className = groupName.addName(classIdentifier);
1892 		final ClassType classModel =
1893 				RegularClassType.create(
1894 						className,
1895 						new Vector<ClassModifier>(),
1896 						attributes,
1897 						new Vector<Type>(),
1898 						new Vector<Operation>(),
1899 						new Vector<Constructor>(),
1900 						classIdentifier,
1901 						
1902 						new Vector<ClassType>());
1903 		
1904 		final ByNameState attributeReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1905 		final TypeProxy type = TypeProxy.create(this.stringIdentifier, attributeReferenceState);
1906 		
1907 		final Vector<AttributeModifier> modifiers = new Vector<>();
1908 		modifiers.add(AttributeModifierPrior.create(PriorToken.create(Position.create("", 0, 0, 0))));
1909 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
1910 		attributes.add(attribute);
1911 		groupVector.add(classModel);
1912 		final Model expected = Model.create(groupIdentifier);
1913 		expected.addGroup(group);
1914 		
1915 		final Model actual = this.parser.parse();
1916 		assertEquals(expected, actual);
1917 		assertEquals(0, this.parser.getExceptions().size());
1918 	}
1919 	
1920 	/**
1921 	 * Group:group=[Class:class={Attribute:Integer prior transient findable mutable;};];.
1922 	 * 
1923 	 * @throws Exception
1924 	 *             : {@link NoValidTokenStreamException}
1925 	 */
1926 	@Test
1927 	public void testAttributeWithAllModifiers() throws Exception {
1928 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
1929 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
1930 		final IdentifierToken attributeIdentifier =
1931 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
1932 		this.stream.add(groupIdentifier);
1933 		this.stream.add(this.colonToken);
1934 		this.stream.add(this.groupToken);
1935 		this.stream.add(this.equalToken);
1936 		this.stream.add(this.squareBracketOpenToken);
1937 		this.stream.add(classIdentifier);
1938 		this.stream.add(this.colonToken);
1939 		this.stream.add(this.classToken);
1940 		this.stream.add(this.equalToken);
1941 		this.stream.add(this.curlyBracketOpenToken);
1942 		this.stream.add(attributeIdentifier);
1943 		this.stream.add(this.colonToken);
1944 		this.stream.add(this.stringIdentifier);
1945 		this.stream.add(PriorToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
1946 		this.stream.add(TransientToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
1947 		this.stream.add(FindableToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
1948 		this.stream.add(MutableToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
1949 		this.stream.add(this.semicolonToken);
1950 		this.stream.add(this.curlyBracketCloseToken);
1951 		this.stream.add(this.semicolonToken);
1952 		this.stream.add(this.squareBracketCloseToken);
1953 		this.stream.add(this.semicolonToken);
1954 		this.stream.add(this.endToken);
1955 		
1956 		final Vector<GroupElement> groupVector = new Vector<>();
1957 		final Vector<Attribute> attributes = new Vector<>();
1958 		
1959 		final Name groupName = UnqualifiedName.create(groupIdentifier);
1960 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
1961 		
1962 		final Name className = groupName.addName(classIdentifier);
1963 		final ClassType classModel =
1964 				RegularClassType.create(
1965 						className,
1966 						new Vector<ClassModifier>(),
1967 						attributes,
1968 						new Vector<Type>(),
1969 						new Vector<Operation>(),
1970 						new Vector<Constructor>(),
1971 						classIdentifier,
1972 						
1973 						new Vector<ClassType>());
1974 		
1975 		final ByNameState attributeReferenceState = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
1976 		final TypeProxy type = TypeProxy.create(this.stringIdentifier, attributeReferenceState);
1977 		
1978 		final Vector<AttributeModifier> modifiers = new Vector<>();
1979 		modifiers.add(AttributeModifierPrior.create(PriorToken.create(Position.create("", 0, 0, 0))));
1980 		modifiers.add(AttributeModifierTransient.create(TransientToken.create(Position.create("", 0 + 1, 0 + 1, 0))));
1981 		modifiers.add(AttributeModifierFindable.create(FindableToken.create(Position.create("", 0 + 1, 0 + 1, 0))));
1982 		modifiers.add(AttributeModifierMutable.create(MutableToken.create(Position.create("", 0 + 1, 0 + 1, 0))));
1983 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
1984 		attributes.add(attribute);
1985 		groupVector.add(classModel);
1986 		final Model expected = Model.create(groupIdentifier);
1987 		expected.addGroup(group);
1988 		
1989 		final Model actual = this.parser.parse();
1990 		assertEquals(expected, actual);
1991 		assertEquals(0, this.parser.getExceptions().size());
1992 	}
1993 	
1994 	/**
1995 	 * Group1:group=[Class1:class={name:String prior prior;};];.
1996 	 * 
1997 	 * @throws Exception
1998 	 *             : {@link NoValidTokenStreamException}
1999 	 */
2000 	@Test
2001 	public void testSimpleClassInGroupWithPriorModifiersComplete() {
2002 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
2003 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
2004 		final IdentifierToken attributeIdentifier =
2005 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2006 		this.stream.add(groupIdentifier);
2007 		this.stream.add(this.colonToken);
2008 		this.stream.add(this.groupToken);
2009 		this.stream.add(this.equalToken);
2010 		this.stream.add(this.squareBracketOpenToken);
2011 		this.stream.add(classIdentifier);
2012 		this.stream.add(this.colonToken);
2013 		this.stream.add(this.classToken);
2014 		this.stream.add(this.equalToken);
2015 		this.stream.add(this.curlyBracketOpenToken);
2016 		this.stream.add(attributeIdentifier);
2017 		this.stream.add(this.colonToken);
2018 		this.stream.add(this.stringIdentifier);
2019 		this.stream.add(PriorToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
2020 		this.stream.add(PriorToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
2021 		this.stream.add(this.semicolonToken);
2022 		this.stream.add(this.curlyBracketCloseToken);
2023 		this.stream.add(this.semicolonToken);
2024 		this.stream.add(this.squareBracketCloseToken);
2025 		this.stream.add(this.semicolonToken);
2026 		this.stream.add(this.endToken);
2027 		
2028 		try {
2029 			this.parser.parse();
2030 			fail();
2031 		} catch (final NoValidTokenStreamException e) {
2032 			assertEquals(1, this.parser.getExceptions().size());
2033 		}
2034 	}
2035 	
2036 	/**
2037 	 * Group1:group=[Class1:class={name:Group1>Class1;};];.
2038 	 * 
2039 	 * @throws Exception
2040 	 *             : {@link NoValidTokenStreamException}
2041 	 */
2042 	@Test
2043 	public void testClassWithAttributeQualifiedType() throws Exception {
2044 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
2045 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
2046 		final IdentifierToken attributeIdentifier =
2047 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2048 		this.stream.add(groupIdentifier);
2049 		this.stream.add(this.colonToken);
2050 		this.stream.add(this.groupToken);
2051 		this.stream.add(this.equalToken);
2052 		this.stream.add(this.squareBracketOpenToken);
2053 		this.stream.add(classIdentifier);
2054 		this.stream.add(this.colonToken);
2055 		this.stream.add(this.classToken);
2056 		this.stream.add(this.equalToken);
2057 		this.stream.add(this.curlyBracketOpenToken);
2058 		this.stream.add(attributeIdentifier);
2059 		this.stream.add(this.colonToken);
2060 		this.stream.add(groupIdentifier);
2061 		this.stream.add(this.greaterSymbol);
2062 		this.stream.add(classIdentifier);
2063 		this.stream.add(this.semicolonToken);
2064 		this.stream.add(this.curlyBracketCloseToken);
2065 		this.stream.add(this.semicolonToken);
2066 		this.stream.add(this.squareBracketCloseToken);
2067 		this.stream.add(this.semicolonToken);
2068 		this.stream.add(EndToken.create(Position.create("", 0 + 1, 0 + 1, 0)));
2069 		
2070 		final Model model = Model.create(groupIdentifier);
2071 		final Vector<GroupElement> groupVector = new Vector<>();
2072 		
2073 		final Name groupName = UnqualifiedName.create(groupIdentifier);
2074 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
2075 		model.addGroup(group);
2076 		
2077 		final Name class1Name = groupName.addName(classIdentifier);
2078 		final Collection<Attribute> classAttributes = new Vector<>();
2079 		final ClassType class1Model =
2080 				RegularClassType.create(
2081 						class1Name,
2082 						new Vector<ClassModifier>(),
2083 						classAttributes,
2084 						new Vector<Type>(),
2085 						new Vector<Operation>(),
2086 						new Vector<Constructor>(),
2087 						classIdentifier,
2088 						
2089 						new Vector<ClassType>());
2090 		groupVector.add(class1Model);
2091 		
2092 		Name attrTypeClass1Name = UnqualifiedName.create(groupIdentifier);
2093 		attrTypeClass1Name = attrTypeClass1Name.addName(classIdentifier);
2094 		final ByNameState attrClassTypeReferenceState = ByNameState.create(attrTypeClass1Name);
2095 		final TypeProxy classType = TypeProxy.create(groupIdentifier, attrClassTypeReferenceState);
2096 		final Collection<AttributeModifier> attrModifiers = new Vector<>();
2097 		final Attribute classAttribute = Attribute.create("Attribute", classType, attrModifiers, groupIdentifier);
2098 		classAttributes.add(classAttribute);
2099 		
2100 		final Model actual = this.parser.parse();
2101 		assertEquals(0, this.parser.getExceptions().size());
2102 		assertEquals(model, actual);
2103 	}
2104 	
2105 	/**
2106 	 * Group:group=[Class:class={Attribute1:Integer symmetric (Attribute2);};];.
2107 	 * 
2108 	 * @throws Exception
2109 	 *             : {@link NoValidTokenStreamException}
2110 	 */
2111 	@Test
2112 	public void testAttributeWithSymmertricModifier() throws Exception {
2113 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 0 + 1, 0 + 1, 0));
2114 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 0 + 1, 0 + 1, 0));
2115 		final IdentifierToken attributeIdentifier1 =
2116 				IdentifierToken.create("Attribute1", Position.create("", 0 + 1, 0 + 1, 0));
2117 		final IdentifierToken attributeIdentifier2 =
2118 				IdentifierToken.create("Attribute2", Position.create("", 0 + 1, 0 + 1, 0));
2119 		this.stream.add(groupIdentifier);
2120 		this.stream.add(this.colonToken);
2121 		this.stream.add(this.groupToken);
2122 		this.stream.add(this.equalToken);
2123 		this.stream.add(this.squareBracketOpenToken);
2124 		this.stream.add(classIdentifier);
2125 		this.stream.add(this.colonToken);
2126 		this.stream.add(this.classToken);
2127 		this.stream.add(this.equalToken);
2128 		this.stream.add(this.curlyBracketOpenToken);
2129 		this.stream.add(attributeIdentifier1);
2130 		this.stream.add(this.colonToken);
2131 		this.stream.add(this.integerIdentifier);
2132 		final SymmetricToken symmetrictoken = SymmetricToken.create(Position.create("", 0 + 1, 0 + 1, 0));
2133 		this.stream.add(symmetrictoken);
2134 		this.stream.add(this.bracketOpenToken);
2135 		this.stream.add(attributeIdentifier2);
2136 		this.stream.add(this.bracketCloseToken);
2137 		this.stream.add(this.semicolonToken);
2138 		this.stream.add(this.curlyBracketCloseToken);
2139 		this.stream.add(this.semicolonToken);
2140 		this.stream.add(this.squareBracketCloseToken);
2141 		this.stream.add(this.semicolonToken);
2142 		this.stream.add(this.endToken);
2143 		
2144 		final Vector<GroupElement> groupVector = new Vector<>();
2145 		final Vector<Attribute> attributes = new Vector<>();
2146 		
2147 		final Name groupName = UnqualifiedName.create(groupIdentifier);
2148 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
2149 		
2150 		final Name className = groupName.addName(classIdentifier);
2151 		final ClassType classModel =
2152 				RegularClassType.create(
2153 						className,
2154 						new Vector<ClassModifier>(),
2155 						attributes,
2156 						new Vector<Type>(),
2157 						new Vector<Operation>(),
2158 						new Vector<Constructor>(),
2159 						classIdentifier,
2160 						
2161 						new Vector<ClassType>());
2162 		
2163 		final ByNameState attributeReferenceState = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
2164 		final TypeProxy type = TypeProxy.create(this.integerIdentifier, attributeReferenceState);
2165 		
2166 		final Vector<AttributeModifier> modifiers = new Vector<>();
2167 		modifiers.add(AttributeModifierSymmetric.create(symmetrictoken, attributeIdentifier2, this.semicolonToken));
2168 		final Attribute attribute = Attribute.create("Attribute1", type, modifiers, attributeIdentifier1);
2169 		attributes.add(attribute);
2170 		groupVector.add(classModel);
2171 		final Model expected = Model.create(groupIdentifier);
2172 		expected.addGroup(group);
2173 		
2174 		final Model actual = this.parser.parse();
2175 		assertEquals(expected, actual);
2176 		assertEquals(0, this.parser.getExceptions().size());
2177 	}
2178 	
2179 	/**
2180 	 * Group1:group=[Class1:class={attribute:[ [Integer->Integer]->String];};];.
2181 	 * 
2182 	 * @throws Exception
2183 	 *             : {@link NoValidTokenStreamException}
2184 	 */
2185 	@Test
2186 	public void testMapAsKey() throws Exception {
2187 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
2188 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
2189 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
2190 		this.stream.add(groupIdentifier);
2191 		this.stream.add(this.colonToken);
2192 		this.stream.add(this.groupToken);
2193 		this.stream.add(this.equalToken);
2194 		this.stream.add(this.squareBracketOpenToken);
2195 		this.stream.add(classIdentifier);
2196 		this.stream.add(this.colonToken);
2197 		this.stream.add(this.classToken);
2198 		this.stream.add(this.equalToken);
2199 		this.stream.add(this.curlyBracketOpenToken);
2200 		this.stream.add(attributeIdentifier);
2201 		this.stream.add(this.colonToken);
2202 		this.stream.add(this.squareBracketOpenToken);
2203 		this.stream.add(this.squareBracketOpenToken);
2204 		this.stream.add(this.integerIdentifier);
2205 		this.stream.add(this.arrowToken);
2206 		this.stream.add(this.integerIdentifier);
2207 		this.stream.add(this.squareBracketCloseToken);
2208 		this.stream.add(this.arrowToken);
2209 		this.stream.add(this.stringIdentifier);
2210 		this.stream.add(this.squareBracketCloseToken);
2211 		this.stream.add(this.semicolonToken);
2212 		this.stream.add(this.curlyBracketCloseToken);
2213 		this.stream.add(this.semicolonToken);
2214 		this.stream.add(this.squareBracketCloseToken);
2215 		this.stream.add(this.semicolonToken);
2216 		this.stream.add(EndToken.create(Position.create("", 1, 1, 0)));
2217 		
2218 		final Model model = Model.create(groupIdentifier);
2219 		final Vector<GroupElement> groupVector = new Vector<>();
2220 		
2221 		final Name groupName = UnqualifiedName.create(groupIdentifier);
2222 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
2223 		model.addGroup(group);
2224 		
2225 		final Name className = groupName.addName(classIdentifier);
2226 		final Collection<Attribute> attributes = new Vector<>();
2227 		final ClassType clazz =
2228 				RegularClassType.create(
2229 						className,
2230 						new Vector<ClassModifier>(),
2231 						attributes,
2232 						new Vector<Type>(),
2233 						new Vector<Operation>(),
2234 						new Vector<Constructor>(),
2235 						classIdentifier,
2236 						
2237 						new Vector<ClassType>());
2238 		groupVector.add(clazz);
2239 		
2240 		final ByNameState stringByName = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
2241 		final TypeProxy typeProxyString = TypeProxy.create(groupIdentifier, stringByName);
2242 		
2243 		final ByNameState integerByName = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
2244 		final TypeProxy typeProxyInteger = TypeProxy.create(groupIdentifier, integerByName);
2245 		
2246 		final MapType map1 = MapType.create(this.integerIdentifier, typeProxyInteger, typeProxyInteger);
2247 		final MapType map2 = MapType.create(this.integerIdentifier, map1, typeProxyString);
2248 		
2249 		final Attribute attribute =
2250 				Attribute.create("Attribute", map2, new Vector<AttributeModifier>(), attributeIdentifier);
2251 		attributes.add(attribute);
2252 		
2253 		final Model actual = this.parser.parse();
2254 		assertEquals(0, this.parser.getExceptions().size());
2255 		assertEquals(model, actual);
2256 	}
2257 	
2258 	/**
2259 	 * Group1:group=[Class1:class={attribute:[{Integer, String}->{Integer, String}];};];.
2260 	 * 
2261 	 * @throws Exception
2262 	 *             : {@link NoValidTokenStreamException}
2263 	 */
2264 	@Test
2265 	public void testSumAsKey() throws Exception {
2266 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
2267 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
2268 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
2269 		this.stream.add(groupIdentifier);
2270 		this.stream.add(this.colonToken);
2271 		this.stream.add(this.groupToken);
2272 		this.stream.add(this.equalToken);
2273 		this.stream.add(this.squareBracketOpenToken);
2274 		this.stream.add(classIdentifier);
2275 		this.stream.add(this.colonToken);
2276 		this.stream.add(this.classToken);
2277 		this.stream.add(this.equalToken);
2278 		this.stream.add(this.curlyBracketOpenToken);
2279 		this.stream.add(attributeIdentifier);
2280 		this.stream.add(this.colonToken);
2281 		this.stream.add(this.squareBracketOpenToken);
2282 		this.stream.add(this.curlyBracketOpenToken);
2283 		this.stream.add(this.integerIdentifier);
2284 		this.stream.add(this.commaToken);
2285 		this.stream.add(this.stringIdentifier);
2286 		this.stream.add(this.curlyBracketCloseToken);
2287 		this.stream.add(this.arrowToken);
2288 		this.stream.add(this.curlyBracketOpenToken);
2289 		this.stream.add(this.integerIdentifier);
2290 		this.stream.add(this.commaToken);
2291 		this.stream.add(this.stringIdentifier);
2292 		this.stream.add(this.curlyBracketCloseToken);
2293 		this.stream.add(this.squareBracketCloseToken);
2294 		this.stream.add(this.semicolonToken);
2295 		this.stream.add(this.curlyBracketCloseToken);
2296 		this.stream.add(this.semicolonToken);
2297 		this.stream.add(this.squareBracketCloseToken);
2298 		this.stream.add(this.semicolonToken);
2299 		this.stream.add(EndToken.create(Position.create("", 1, 1, 0)));
2300 		
2301 		final Model model = Model.create(groupIdentifier);
2302 		final Vector<GroupElement> groupVector = new Vector<>();
2303 		
2304 		final Name groupName = UnqualifiedName.create(groupIdentifier);
2305 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
2306 		model.addGroup(group);
2307 		
2308 		final Name className = groupName.addName(classIdentifier);
2309 		final Collection<Attribute> attributes = new Vector<>();
2310 		final ClassType clazz =
2311 				RegularClassType.create(
2312 						className,
2313 						new Vector<ClassModifier>(),
2314 						attributes,
2315 						new Vector<Type>(),
2316 						new Vector<Operation>(),
2317 						new Vector<Constructor>(),
2318 						classIdentifier,
2319 						
2320 						new Vector<ClassType>());
2321 		groupVector.add(clazz);
2322 		
2323 		final ByNameState stringByName = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
2324 		final TypeProxy typeProxyString = TypeProxy.create(groupIdentifier, stringByName);
2325 		
2326 		final ByNameState integerByName = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
2327 		final TypeProxy typeProxyInteger = TypeProxy.create(groupIdentifier, integerByName);
2328 		
2329 		final SumType sum = SumType.create(this.integerIdentifier);
2330 		sum.add(typeProxyInteger);
2331 		sum.add(typeProxyString);
2332 		
2333 		final MapType map = MapType.create(this.curlyBracketOpenToken, sum, sum);
2334 		final Attribute attribute =
2335 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
2336 		attributes.add(attribute);
2337 		
2338 		final Model actual = this.parser.parse();
2339 		assertEquals(0, this.parser.getExceptions().size());
2340 		assertEquals(model, actual);
2341 	}
2342 	
2343 	/**
2344 	 * Group1:group=[Class1:class={attribute:[(name:String, count:Integer)->{True, False}];};];.
2345 	 * 
2346 	 * @throws Exception
2347 	 *             : {@link NoValidTokenStreamException}
2348 	 */
2349 	@Test
2350 	public void testProductAsKey() throws Exception {
2351 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
2352 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
2353 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
2354 		final IdentifierToken nameIdentifier = IdentifierToken.create("name", Position.create("", 1, 1, 0));
2355 		final IdentifierToken productIdentifier = IdentifierToken.create("product", Position.create("", 1, 1, 0));
2356 		final IdentifierToken trueIdentifier = IdentifierToken.create("true", Position.create("", 1, 1, 0));
2357 		final IdentifierToken falseIdentifier = IdentifierToken.create("false", Position.create("", 1, 1, 0));
2358 		this.stream.add(groupIdentifier);
2359 		this.stream.add(this.colonToken);
2360 		this.stream.add(this.groupToken);
2361 		this.stream.add(this.equalToken);
2362 		this.stream.add(this.squareBracketOpenToken);
2363 		this.stream.add(classIdentifier);
2364 		this.stream.add(this.colonToken);
2365 		this.stream.add(this.classToken);
2366 		this.stream.add(this.equalToken);
2367 		this.stream.add(this.curlyBracketOpenToken);
2368 		this.stream.add(attributeIdentifier);
2369 		this.stream.add(this.colonToken);
2370 		this.stream.add(this.squareBracketOpenToken);
2371 		this.stream.add(this.bracketOpenToken);
2372 		this.stream.add(nameIdentifier);
2373 		this.stream.add(this.colonToken);
2374 		this.stream.add(this.stringIdentifier);
2375 		this.stream.add(this.commaToken);
2376 		this.stream.add(productIdentifier);
2377 		this.stream.add(this.colonToken);
2378 		this.stream.add(this.integerIdentifier);
2379 		this.stream.add(this.bracketCloseToken);
2380 		this.stream.add(this.arrowToken);
2381 		this.stream.add(this.curlyBracketOpenToken);
2382 		this.stream.add(trueIdentifier);
2383 		this.stream.add(this.commaToken);
2384 		this.stream.add(falseIdentifier);
2385 		this.stream.add(this.curlyBracketCloseToken);
2386 		this.stream.add(this.squareBracketCloseToken);
2387 		this.stream.add(this.semicolonToken);
2388 		this.stream.add(this.curlyBracketCloseToken);
2389 		this.stream.add(this.semicolonToken);
2390 		this.stream.add(this.squareBracketCloseToken);
2391 		this.stream.add(this.semicolonToken);
2392 		this.stream.add(EndToken.create(Position.create("", 1, 1, 0)));
2393 		
2394 		final Model model = Model.create(groupIdentifier);
2395 		final Vector<GroupElement> groupVector = new Vector<>();
2396 		
2397 		final Name groupName = UnqualifiedName.create(groupIdentifier);
2398 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
2399 		model.addGroup(group);
2400 		
2401 		final Name className = groupName.addName(classIdentifier);
2402 		final Collection<Attribute> attributes = new Vector<>();
2403 		final ClassType clazz =
2404 				RegularClassType.create(
2405 						className,
2406 						new Vector<ClassModifier>(),
2407 						attributes,
2408 						new Vector<Type>(),
2409 						new Vector<Operation>(),
2410 						new Vector<Constructor>(),
2411 						classIdentifier,
2412 						
2413 						new Vector<ClassType>());
2414 		groupVector.add(clazz);
2415 		
2416 		final ByNameState stringByName = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
2417 		final TypeProxy typeProxyString = TypeProxy.create(groupIdentifier, stringByName);
2418 		
2419 		final ByNameState integerByName = ByNameState.create(UnqualifiedName.create(this.integerIdentifier));
2420 		final TypeProxy typeProxyInteger = TypeProxy.create(groupIdentifier, integerByName);
2421 		
2422 		final ByNameState trueByName = ByNameState.create(UnqualifiedName.create(trueIdentifier));
2423 		final TypeProxy typeProxyTrue = TypeProxy.create(groupIdentifier, trueByName);
2424 		
2425 		final ByNameState falseByName = ByNameState.create(UnqualifiedName.create(falseIdentifier));
2426 		final TypeProxy typeProxyFalse = TypeProxy.create(groupIdentifier, falseByName);
2427 		
2428 		final ProductType product = ProductType.create(this.bracketOpenToken);
2429 		final ProductElementType element1 = ProductElementType.create("name", typeProxyString, nameIdentifier);
2430 		final ProductElementType element2 = ProductElementType.create("product", typeProxyInteger, productIdentifier);
2431 		product.addElement(element1);
2432 		product.addElement(element2);
2433 		
2434 		final SumType sum = SumType.create(this.curlyBracketOpenToken);
2435 		sum.add(typeProxyTrue);
2436 		sum.add(typeProxyFalse);
2437 		
2438 		final MapType map = MapType.create(this.curlyBracketOpenToken, product, sum);
2439 		final Attribute attribute =
2440 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
2441 		attributes.add(attribute);
2442 		
2443 		final Model actual = this.parser.parse();
2444 		assertEquals(0, this.parser.getExceptions().size());
2445 		assertEquals(model, actual);
2446 	}
2447 	
2448 	/**
2449 	 * Group1:group=[Class1:class={attribute:[String*->{True, False}];};];.
2450 	 * 
2451 	 * @throws Exception
2452 	 *             : {@link NoValidTokenStreamException}
2453 	 */
2454 	@Test
2455 	public void testListAsKey() throws Exception {
2456 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
2457 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
2458 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
2459 		final IdentifierToken trueIdentifier = IdentifierToken.create("true", Position.create("", 1, 1, 0));
2460 		final IdentifierToken falseIdentifier = IdentifierToken.create("false", Position.create("", 1, 1, 0));
2461 		
2462 		this.stream.add(groupIdentifier);
2463 		this.stream.add(this.colonToken);
2464 		this.stream.add(this.groupToken);
2465 		this.stream.add(this.equalToken);
2466 		this.stream.add(this.squareBracketOpenToken);
2467 		this.stream.add(classIdentifier);
2468 		this.stream.add(this.colonToken);
2469 		this.stream.add(this.classToken);
2470 		this.stream.add(this.equalToken);
2471 		this.stream.add(this.curlyBracketOpenToken);
2472 		this.stream.add(attributeIdentifier);
2473 		this.stream.add(this.colonToken);
2474 		this.stream.add(this.squareBracketOpenToken);
2475 		this.stream.add(this.stringIdentifier);
2476 		this.stream.add(this.asteriskToken);
2477 		this.stream.add(this.arrowToken);
2478 		this.stream.add(this.curlyBracketOpenToken);
2479 		this.stream.add(trueIdentifier);
2480 		this.stream.add(this.commaToken);
2481 		this.stream.add(falseIdentifier);
2482 		this.stream.add(this.curlyBracketCloseToken);
2483 		this.stream.add(this.squareBracketCloseToken);
2484 		this.stream.add(this.semicolonToken);
2485 		this.stream.add(this.curlyBracketCloseToken);
2486 		this.stream.add(this.semicolonToken);
2487 		this.stream.add(this.squareBracketCloseToken);
2488 		this.stream.add(this.semicolonToken);
2489 		this.stream.add(EndToken.create(Position.create("", 1, 1, 0)));
2490 		
2491 		final Model model = Model.create(groupIdentifier);
2492 		final Vector<GroupElement> groupVector = new Vector<>();
2493 		
2494 		final Name groupName = UnqualifiedName.create(groupIdentifier);
2495 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
2496 		model.addGroup(group);
2497 		
2498 		final Name className = groupName.addName(classIdentifier);
2499 		final Collection<Attribute> attributes = new Vector<>();
2500 		final ClassType clazz =
2501 				RegularClassType.create(
2502 						className,
2503 						new Vector<ClassModifier>(),
2504 						attributes,
2505 						new Vector<Type>(),
2506 						new Vector<Operation>(),
2507 						new Vector<Constructor>(),
2508 						classIdentifier,
2509 						
2510 						new Vector<ClassType>());
2511 		groupVector.add(clazz);
2512 		
2513 		final ByNameState stringByName = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
2514 		final TypeProxy typeProxyString = TypeProxy.create(groupIdentifier, stringByName);
2515 		
2516 		final ByNameState trueByName = ByNameState.create(UnqualifiedName.create(trueIdentifier));
2517 		final TypeProxy typeProxyTrue = TypeProxy.create(groupIdentifier, trueByName);
2518 		
2519 		final ByNameState falseByName = ByNameState.create(UnqualifiedName.create(falseIdentifier));
2520 		final TypeProxy typeProxyFalse = TypeProxy.create(groupIdentifier, falseByName);
2521 		
2522 		final ListType list = ListType.create(this.stringIdentifier, typeProxyString);
2523 		
2524 		final SumType sum = SumType.create(this.curlyBracketOpenToken);
2525 		sum.add(typeProxyTrue);
2526 		sum.add(typeProxyFalse);
2527 		
2528 		final MapType map = MapType.create(this.curlyBracketOpenToken, list, sum);
2529 		final Attribute attribute =
2530 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
2531 		attributes.add(attribute);
2532 		
2533 		final Model actual = this.parser.parse();
2534 		assertEquals(0, this.parser.getExceptions().size());
2535 		assertEquals(model, actual);
2536 	}
2537 	
2538 	/**
2539 	 * Group1:group=[Class1:class={attribute:[String ->{{True}*, False}];};];.
2540 	 * 
2541 	 * @throws Exception
2542 	 *             : {@link NoValidTokenStreamException}
2543 	 */
2544 	@Test
2545 	public void testSumWithListOfSum() throws Exception {
2546 		final IdentifierToken groupIdentifier = IdentifierToken.create("Group", Position.create("", 1, 1, 0));
2547 		final IdentifierToken classIdentifier = IdentifierToken.create("Class", Position.create("", 1, 1, 0));
2548 		final IdentifierToken attributeIdentifier = IdentifierToken.create("Attribute", Position.create("", 1, 1, 0));
2549 		final IdentifierToken trueIdentifier = IdentifierToken.create("true", Position.create("", 1, 1, 0));
2550 		final IdentifierToken falseIdentifier = IdentifierToken.create("false", Position.create("", 1, 1, 0));
2551 		
2552 		this.stream.add(groupIdentifier);
2553 		this.stream.add(this.colonToken);
2554 		this.stream.add(this.groupToken);
2555 		this.stream.add(this.equalToken);
2556 		this.stream.add(this.squareBracketOpenToken);
2557 		this.stream.add(classIdentifier);
2558 		this.stream.add(this.colonToken);
2559 		this.stream.add(this.classToken);
2560 		this.stream.add(this.equalToken);
2561 		this.stream.add(this.curlyBracketOpenToken);
2562 		this.stream.add(attributeIdentifier);
2563 		this.stream.add(this.colonToken);
2564 		this.stream.add(this.squareBracketOpenToken);
2565 		this.stream.add(this.stringIdentifier);
2566 		this.stream.add(this.arrowToken);
2567 		this.stream.add(this.curlyBracketOpenToken);
2568 		this.stream.add(this.curlyBracketOpenToken);
2569 		this.stream.add(trueIdentifier);
2570 		this.stream.add(this.curlyBracketCloseToken);
2571 		this.stream.add(this.asteriskToken);
2572 		this.stream.add(this.commaToken);
2573 		this.stream.add(falseIdentifier);
2574 		this.stream.add(this.curlyBracketCloseToken);
2575 		this.stream.add(this.squareBracketCloseToken);
2576 		this.stream.add(this.semicolonToken);
2577 		this.stream.add(this.curlyBracketCloseToken);
2578 		this.stream.add(this.semicolonToken);
2579 		this.stream.add(this.squareBracketCloseToken);
2580 		this.stream.add(this.semicolonToken);
2581 		this.stream.add(EndToken.create(Position.create("", 1, 1, 0)));
2582 		
2583 		final Model model = Model.create(groupIdentifier);
2584 		final Vector<GroupElement> groupVector = new Vector<>();
2585 		
2586 		final Name groupName = UnqualifiedName.create(groupIdentifier);
2587 		final Group group = Group.create(groupName, groupVector, groupIdentifier);
2588 		model.addGroup(group);
2589 		
2590 		final Name className = groupName.addName(classIdentifier);
2591 		final Collection<Attribute> attributes = new Vector<>();
2592 		final ClassType clazz =
2593 				RegularClassType.create(
2594 						className,
2595 						new Vector<ClassModifier>(),
2596 						attributes,
2597 						new Vector<Type>(),
2598 						new Vector<Operation>(),
2599 						new Vector<Constructor>(),
2600 						classIdentifier,
2601 						
2602 						new Vector<ClassType>());
2603 		groupVector.add(clazz);
2604 		
2605 		final ByNameState stringByName = ByNameState.create(UnqualifiedName.create(this.stringIdentifier));
2606 		final TypeProxy typeProxyString = TypeProxy.create(groupIdentifier, stringByName);
2607 		
2608 		final ByNameState trueByName = ByNameState.create(UnqualifiedName.create(trueIdentifier));
2609 		final TypeProxy typeProxyTrue = TypeProxy.create(groupIdentifier, trueByName);
2610 		
2611 		final ByNameState falseByName = ByNameState.create(UnqualifiedName.create(falseIdentifier));
2612 		final TypeProxy typeProxyFalse = TypeProxy.create(groupIdentifier, falseByName);
2613 		
2614 		final SumType sumInner = SumType.create(this.curlyBracketOpenToken);
2615 		sumInner.add(typeProxyTrue);
2616 		final ListType list = ListType.create(this.curlyBracketOpenToken, sumInner);
2617 		
2618 		final SumType sum = SumType.create(this.curlyBracketOpenToken);
2619 		sum.add(list);
2620 		sum.add(typeProxyFalse);
2621 		
2622 		final MapType map = MapType.create(this.curlyBracketOpenToken, typeProxyString, sum);
2623 		final Attribute attribute =
2624 				Attribute.create("Attribute", map, new Vector<AttributeModifier>(), attributeIdentifier);
2625 		attributes.add(attribute);
2626 		
2627 		final Model actual = this.parser.parse();
2628 		assertEquals(0, this.parser.getExceptions().size());
2629 		assertEquals(model, actual);
2630 	}
2631 	
2632 	/**
2633 	 * Attribute:String prior;.
2634 	 */
2635 	@Test
2636 	public void testAttributeToString() {
2637 		final IdentifierToken string = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
2638 		final IdentifierToken attributeIdentifier =
2639 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2640 		final IdentifierToken prior = IdentifierToken.create("prior", Position.create("", 0 + 1, 0 + 1, 0));
2641 		final UnqualifiedName name = UnqualifiedName.create(string);
2642 		final BaseType type = BaseType.create(name, string, string);
2643 		final Collection<AttributeModifier> modifiers = new ArrayList<AttributeModifier>();
2644 		modifiers.add(AttributeModifierPrior.create(prior));
2645 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
2646 		
2647 		assertEquals("Attribute:String prior;", attribute.toString());
2648 	}
2649 	
2650 	/**
2651 	 * Attribute:String findable;.
2652 	 */
2653 	@Test
2654 	public void testAttributeIsFindable() {
2655 		final IdentifierToken string = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
2656 		final IdentifierToken attributeIdentifier =
2657 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2658 		final IdentifierToken findable = IdentifierToken.create("findable", Position.create("", 0 + 1, 0 + 1, 0));
2659 		final UnqualifiedName name = UnqualifiedName.create(string);
2660 		final BaseType type = BaseType.create(name, string, string);
2661 		final Collection<AttributeModifier> modifiers = new ArrayList<>();
2662 		modifiers.add(AttributeModifierFindable.create(findable));
2663 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
2664 		
2665 		assertTrue(attribute.isFindable());
2666 		assertFalse(attribute.isPrior());
2667 		assertFalse(attribute.isTransient());
2668 		assertFalse(attribute.isMutable());
2669 		assertFalse(attribute.isSymmetric());
2670 	}
2671 	
2672 	/**
2673 	 * Attribute:String prior;.
2674 	 */
2675 	@Test
2676 	public void testAttributeIsPrior() {
2677 		final IdentifierToken string = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
2678 		final IdentifierToken attributeIdentifier =
2679 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2680 		final IdentifierToken prior = IdentifierToken.create("prior", Position.create("", 0 + 1, 0 + 1, 0));
2681 		final UnqualifiedName name = UnqualifiedName.create(string);
2682 		final BaseType type = BaseType.create(name, string, string);
2683 		final Collection<AttributeModifier> modifiers = new ArrayList<>();
2684 		modifiers.add(AttributeModifierPrior.create(prior));
2685 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
2686 		
2687 		assertFalse(attribute.isFindable());
2688 		assertTrue(attribute.isPrior());
2689 		assertFalse(attribute.isTransient());
2690 		assertFalse(attribute.isMutable());
2691 		assertFalse(attribute.isSymmetric());
2692 	}
2693 	
2694 	/**
2695 	 * Attribute:String transient;.
2696 	 */
2697 	@Test
2698 	public void testAttributeIsTransient() {
2699 		final IdentifierToken string = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
2700 		final IdentifierToken attributeIdentifier =
2701 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2702 		final IdentifierToken trans = IdentifierToken.create("transient", Position.create("", 0 + 1, 0 + 1, 0));
2703 		final UnqualifiedName name = UnqualifiedName.create(string);
2704 		final BaseType type = BaseType.create(name, string, string);
2705 		final Collection<AttributeModifier> modifiers = new ArrayList<>();
2706 		modifiers.add(AttributeModifierTransient.create(trans));
2707 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
2708 		
2709 		assertFalse(attribute.isFindable());
2710 		assertFalse(attribute.isPrior());
2711 		assertTrue(attribute.isTransient());
2712 		assertFalse(attribute.isMutable());
2713 		assertFalse(attribute.isSymmetric());
2714 	}
2715 	
2716 	/**
2717 	 * Attribute:String mutable;.
2718 	 */
2719 	@Test
2720 	public void testAttributeIsMutable() {
2721 		final IdentifierToken string = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
2722 		final IdentifierToken attributeIdentifier =
2723 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2724 		final IdentifierToken mutable = IdentifierToken.create("mutable", Position.create("", 0 + 1, 0 + 1, 0));
2725 		final UnqualifiedName name = UnqualifiedName.create(string);
2726 		final BaseType type = BaseType.create(name, string, string);
2727 		final Collection<AttributeModifier> modifiers = new ArrayList<>();
2728 		modifiers.add(AttributeModifierMutable.create(mutable));
2729 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
2730 		
2731 		assertFalse(attribute.isFindable());
2732 		assertFalse(attribute.isPrior());
2733 		assertFalse(attribute.isTransient());
2734 		assertTrue(attribute.isMutable());
2735 		assertFalse(attribute.isSymmetric());
2736 	}
2737 	
2738 	/**
2739 	 * Attribute:String mutable;.
2740 	 */
2741 	@Test
2742 	public void testAttributeHashCoce() {
2743 		final IdentifierToken string = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
2744 		final IdentifierToken attributeIdentifier =
2745 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2746 		final UnqualifiedName name = UnqualifiedName.create(string);
2747 		final BaseType type = BaseType.create(name, string, string);
2748 		final IdentifierToken mutable = IdentifierToken.create("mutable", Position.createDummyPosition());
2749 		final Collection<AttributeModifier> modifiers1 = new ArrayList<>();
2750 		modifiers1.add(AttributeModifierMutable.create(mutable));
2751 		final Attribute attribute1 = Attribute.create("Attribute", type, modifiers1, attributeIdentifier);
2752 		final Collection<AttributeModifier> modifiers2 = new ArrayList<>();
2753 		modifiers2.add(AttributeModifierMutable.create(mutable));
2754 		final Attribute attribute2 = Attribute.create("Attribute", type, modifiers2, attributeIdentifier);
2755 		
2756 		assertEquals(attribute1, attribute2);
2757 		assertEquals(attribute1.hashCode(), attribute2.hashCode());
2758 	}
2759 	
2760 	/**
2761 	 * Attribute:Integer symmetric (Attribute2);.
2762 	 */
2763 	@Test
2764 	public void testAttributeIsSymmetric() {
2765 		final IdentifierToken string = IdentifierToken.create("String", Position.create("", 0 + 1, 0 + 1, 0));
2766 		final IdentifierToken attributeIdentifier =
2767 				IdentifierToken.create("Attribute", Position.create("", 0 + 1, 0 + 1, 0));
2768 		final IdentifierToken symmetric = IdentifierToken.create("symmetric", Position.create("", 0 + 1, 0 + 1, 0));
2769 		final UnqualifiedName name = UnqualifiedName.create(string);
2770 		final BaseType type = BaseType.create(name, string, string);
2771 		final Collection<AttributeModifier> modifiers = new ArrayList<>();
2772 		final AttributeModifierSymmetric modifier = AttributeModifierSymmetric.create(symmetric, symmetric, symmetric);
2773 		modifiers.add(modifier);
2774 		final Attribute attribute = Attribute.create("Attribute", type, modifiers, attributeIdentifier);
2775 		
2776 		assertFalse(attribute.isFindable());
2777 		assertFalse(attribute.isPrior());
2778 		assertFalse(attribute.isTransient());
2779 		assertFalse(attribute.isMutable());
2780 		assertTrue(attribute.isSymmetric());
2781 	}
2782 }