15.5 KB658 lines
Blame
1import { imgSnapshotTest } from '../../helpers/util.ts';
2describe('Class diagram V2', () => {
3 it('0: should render a simple class diagram', () => {
4 imgSnapshotTest(
5 `
6 classDiagram-v2
7
8 classA -- classB : Inheritance
9 classA -- classC : link
10 classC -- classD : link
11 classB -- classD
12
13 `,
14 { logLevel: 1, flowchart: { htmlLabels: false } }
15 );
16 });
17
18 it('1: should render a simple class diagram', () => {
19 imgSnapshotTest(
20 `
21 classDiagram-v2
22 Class01 <|-- AveryLongClass : Cool
23 &lt;&lt;interface&gt;&gt; Class01
24 Class03 *-- Class04
25 Class05 o-- Class06
26 Class07 .. Class08
27 Class09 --> C2 : Where am i?
28 Class09 --* C3
29 Class09 --|> Class07
30 Class12 <|.. Class08
31 Class11 ..>Class12
32 Class07 : equals()
33 Class07 : Object[] elementData
34 Class01 : size()
35 Class01 : int chimp
36 Class01 : int gorilla
37 Class01 : -int privateChimp
38 Class01 : +int publicGorilla
39 Class01 : #int protectedMarmoset
40 Class08 <--> C2: Cool label
41 class Class10 {
42 &lt;&lt;service&gt;&gt;
43 int id
44 test()
45 }
46 `,
47 { logLevel: 1, flowchart: { htmlLabels: false } }
48 );
49 });
50
51 it('2: should render a simple class diagrams with cardinality', () => {
52 imgSnapshotTest(
53 `
54 classDiagram-v2
55 Class01 "1" <|--|> "*" AveryLongClass : Cool
56 &lt;&lt;interface&gt;&gt; Class01
57 Class03 "1" *-- "*" Class04
58 Class05 "1" o-- "many" Class06
59 Class07 "1" .. "*" Class08
60 Class09 "1" --> "*" C2 : Where am i?
61 Class09 "*" --* "*" C3
62 Class09 "1" --|> "1" Class07
63 Class07 : equals()
64 Class07 : Object[] elementData
65 Class01 : size()
66 Class01 : int chimp
67 Class01 : int gorilla
68 Class08 "1" <--> "*" C2: Cool label
69 class Class10 {
70 &lt;&lt;service&gt;&gt;
71 int id
72 test()
73 }
74 `,
75 { logLevel: 1, flowchart: { htmlLabels: false } }
76 );
77 });
78
79 it('2.1 should render a simple class diagram with different visibilities', () => {
80 imgSnapshotTest(
81 `
82 classDiagram-v2
83 Class01 <|-- AveryLongClass : Cool
84 &lt;&lt;interface&gt;&gt; Class01
85 Class01 : -privateMethod()
86 Class01 : +publicMethod()
87 Class01 : #protectedMethod()
88 Class01 : -int privateChimp
89 Class01 : +int publicGorilla
90 Class01 : #int protectedMarmoset
91 `,
92 { logLevel: 1, flowchart: { htmlLabels: false } }
93 );
94 });
95
96 it('3: should render multiple class diagrams', () => {
97 imgSnapshotTest(
98 [
99 `
100 classDiagram-v2
101 Class01 "1" <|--|> "*" AveryLongClass : Cool
102 &lt;&lt;interface&gt;&gt; Class01
103 Class03 "1" *-- "*" Class04
104 Class05 "1" o-- "many" Class06
105 Class07 "1" .. "*" Class08
106 Class09 "1" --> "*" C2 : Where am i?
107 Class09 "*" --* "*" C3
108 Class09 "1" --|> "1" Class07
109 Class07 : equals()
110 Class07 : Object[] elementData
111 Class01 : size()
112 Class01 : int chimp
113 Class01 : int gorilla
114 Class08 "1" <--> "*" C2: Cool label
115 class Class10 {
116 &lt;&lt;service&gt;&gt;
117 int id
118 test()
119 }
120 `,
121 `
122 classDiagram-v2
123 Class01 "1" <|--|> "*" AveryLongClass : Cool
124 &lt;&lt;interface&gt;&gt; Class01
125 Class03 "1" *-- "*" Class04
126 Class05 "1" o-- "many" Class06
127 Class07 "1" .. "*" Class08
128 Class09 "1" --> "*" C2 : Where am i?
129 Class09 "*" --* "*" C3
130 Class09 "1" --|> "1" Class07
131 Class07 : equals()
132 Class07 : Object[] elementData
133 Class01 : size()
134 Class01 : int chimp
135 Class01 : int gorilla
136 Class08 "1" <--> "*" C2: Cool label
137 class Class10 {
138 &lt;&lt;service&gt;&gt;
139 int id
140 test()
141 }
142 `,
143 ],
144 { logLevel: 1, flowchart: { htmlLabels: false } }
145 );
146 });
147
148 it('4: should render a simple class diagram with comments', () => {
149 imgSnapshotTest(
150 `
151 classDiagram-v2
152 %% this is a comment
153 Class01 <|-- AveryLongClass : Cool
154 &lt;&lt;interface&gt;&gt; Class01
155 Class03 *-- Class04
156 Class05 o-- Class06
157 Class07 .. Class08
158 Class09 --> C2 : Where am i?
159 Class09 --* C3
160 Class09 --|> Class07
161 Class07 : equals()
162 Class07 : Object[] elementData
163 Class01 : size()
164 Class01 : int chimp
165 Class01 : int gorilla
166 Class08 <--> C2: Cool label
167 class Class10 {
168 &lt;&lt;service&gt;&gt;
169 int id
170 test()
171 }
172 `,
173 { logLevel: 1, flowchart: { htmlLabels: false } }
174 );
175 });
176
177 it('5: should render a simple class diagram with abstract method', () => {
178 imgSnapshotTest(
179 `
180 classDiagram-v2
181 Class01 <|-- AveryLongClass : Cool
182 Class01 : someMethod()*
183 `,
184 { logLevel: 1, flowchart: { htmlLabels: false } }
185 );
186 });
187
188 it('6: should render a simple class diagram with static method', () => {
189 imgSnapshotTest(
190 `
191 classDiagram-v2
192 Class01 <|-- AveryLongClass : Cool
193 Class01 : someMethod()$
194 `,
195 { logLevel: 1, flowchart: { htmlLabels: false } }
196 );
197 });
198
199 it('7: should render a simple class diagram with Generic class', () => {
200 imgSnapshotTest(
201 `
202 classDiagram-v2
203 class Class01~T~
204 Class01 : size()
205 Class01 : int chimp
206 Class01 : int gorilla
207 Class08 <--> C2: Cool label
208 class Class10~T~ {
209 &lt;&lt;service&gt;&gt;
210 int id
211 test()
212 }
213 `,
214 { logLevel: 1, flowchart: { htmlLabels: false } }
215 );
216 });
217
218 it('8: should render a simple class diagram with Generic class and relations', () => {
219 imgSnapshotTest(
220 `
221 classDiagram-v2
222 Class01~T~ <|-- AveryLongClass : Cool
223 Class03~T~ *-- Class04~T~
224 Class01 : size()
225 Class01 : int chimp
226 Class01 : int gorilla
227 Class08 <--> C2: Cool label
228 class Class10~T~ {
229 &lt;&lt;service&gt;&gt;
230 int id
231 test()
232 }
233 `,
234 { logLevel: 1, flowchart: { htmlLabels: false } }
235 );
236 });
237
238 it('9: should render a simple class diagram with clickable link', () => {
239 imgSnapshotTest(
240 `
241 classDiagram-v2
242 Class01~T~ <|-- AveryLongClass : Cool
243 Class03~T~ *-- Class04~T~
244 Class01 : size()
245 Class01 : int chimp
246 Class01 : int gorilla
247 Class08 <--> C2: Cool label
248 class Class10~T~ {
249 &lt;&lt;service&gt;&gt;
250 int id
251 test()
252 }
253 link Class01 "google.com" "A Tooltip"
254 `,
255 { logLevel: 1, flowchart: { htmlLabels: false } }
256 );
257 });
258
259 it('10: should render a simple class diagram with clickable callback', () => {
260 imgSnapshotTest(
261 `
262 classDiagram-v2
263 Class01~T~ <|-- AveryLongClass : Cool
264 Class03~T~ *-- Class04~T~
265 Class01 : size()
266 Class01 : int chimp
267 Class01 : int gorilla
268 Class08 <--> C2: Cool label
269 class Class10~T~ {
270 &lt;&lt;service&gt;&gt;
271 int id
272 test()
273 }
274 callback Class01 "functionCall" "A Tooltip"
275 `,
276 { logLevel: 1, flowchart: { htmlLabels: false } }
277 );
278 });
279
280 it('11: should render a simple class diagram with return type on method', () => {
281 imgSnapshotTest(
282 `
283 classDiagram-v2
284 class Class10~T~ {
285 int[] id
286 test(int[] ids) bool
287 testArray() bool[]
288 }
289 `,
290 { logLevel: 1, flowchart: { htmlLabels: false } }
291 );
292 });
293
294 it('12: should render a simple class diagram with generic types', () => {
295 imgSnapshotTest(
296 `
297 classDiagram-v2
298 class Class10~T~ {
299 int[] id
300 List~int~ ids
301 test(List~int~ ids) List~bool~
302 testArray() bool[]
303 }
304 `,
305 { logLevel: 1, flowchart: { htmlLabels: false } }
306 );
307 });
308
309 it('13: should render a simple class diagram with css classes applied', () => {
310 imgSnapshotTest(
311 `
312 classDiagram-v2
313 class Class10 {
314 int[] id
315 List~int~ ids
316 test(List~int~ ids) List~bool~
317 testArray() bool[]
318 }
319
320 cssClass "Class10" exClass2
321 `,
322 { logLevel: 1, flowchart: { htmlLabels: false } }
323 );
324 });
325
326 it('14: should render a simple class diagram with css classes applied directly', () => {
327 imgSnapshotTest(
328 `
329 classDiagram-v2
330 class Class10:::exClass2 {
331 int[] id
332 List~int~ ids
333 test(List~int~ ids) List~bool~
334 testArray() bool[]
335 }
336 `,
337 { logLevel: 1, flowchart: { htmlLabels: false } }
338 );
339 });
340
341 it('15: should render a simple class diagram with css classes applied two multiple classes', () => {
342 imgSnapshotTest(
343 `
344 classDiagram-v2
345 class Class10
346 class Class20
347
348 cssClass "Class10, class20" exClass2
349 `,
350 { logLevel: 1, flowchart: { htmlLabels: false } }
351 );
352 });
353
354 it('16a: should render a simple class diagram with static field', () => {
355 imgSnapshotTest(
356 `
357 classDiagram-v2
358 class Foo {
359 +String bar$
360 }
361 `,
362 { logLevel: 1, flowchart: { htmlLabels: false } }
363 );
364 });
365
366 it('16b: should handle the direction statement with TB', () => {
367 imgSnapshotTest(
368 `
369 classDiagram
370 direction TB
371 class Student {
372 -idCard : IdCard
373 }
374 class IdCard{
375 -id : int
376 -name : string
377 }
378 class Bike{
379 -id : int
380 -name : string
381 }
382 Student "1" --o "1" IdCard : carries
383 Student "1" --o "1" Bike : rides
384
385 `,
386 { logLevel: 1, flowchart: { htmlLabels: false } }
387 );
388 });
389 it('17a: should handle the direction statement with BT', () => {
390 imgSnapshotTest(
391 `
392 classDiagram
393 direction BT
394 class Student {
395 -idCard : IdCard
396 }
397 class IdCard{
398 -id : int
399 -name : string
400 }
401 class Bike{
402 -id : int
403 -name : string
404 }
405 Student "1" --o "1" IdCard : carries
406 Student "1" --o "1" Bike : rides
407
408 `,
409 { logLevel: 1, flowchart: { htmlLabels: false } }
410 );
411 });
412 it('17b: should handle the direction statement with RL', () => {
413 imgSnapshotTest(
414 `
415 classDiagram
416 direction RL
417 class Student {
418 -idCard : IdCard
419 }
420 class IdCard{
421 -id : int
422 -name : string
423 }
424 class Bike{
425 -id : int
426 -name : string
427 }
428 Student "1" --o "1" IdCard : carries
429 Student "1" --o "1" Bike : rides
430
431 `,
432 { logLevel: 1, flowchart: { htmlLabels: false } }
433 );
434 });
435
436 it('18a: should handle the direction statement with LR', () => {
437 imgSnapshotTest(
438 `
439 classDiagram
440 direction LR
441 class Student {
442 -idCard : IdCard
443 }
444 class IdCard{
445 -id : int
446 -name : string
447 }
448 class Bike{
449 -id : int
450 -name : string
451 }
452 Student "1" --o "1" IdCard : carries
453 Student "1" --o "1" Bike : rides
454
455 `,
456 { logLevel: 1, flowchart: { htmlLabels: false } }
457 );
458 });
459
460 it('18b: should render a simple class diagram with notes', () => {
461 imgSnapshotTest(
462 `
463 classDiagram-v2
464 note "I love this diagram!\nDo you love it?"
465 class Class10 {
466 int id
467 size()
468 }
469 note for Class10 "Cool class\nI said it's very cool class!"
470
471 `,
472 { logLevel: 1, flowchart: { htmlLabels: false } }
473 );
474 });
475
476 it('1433: should render a simple class with a title', () => {
477 imgSnapshotTest(
478 `---
479title: simple class diagram
480---
481classDiagram-v2
482class Class10
483`
484 );
485 });
486
487 it('should render a class with text label', () => {
488 imgSnapshotTest(
489 `classDiagram
490 class C1["Class 1 with text label"]
491 C1 --> C2`
492 );
493 });
494
495 it('should render two classes with text labels', () => {
496 imgSnapshotTest(
497 `classDiagram
498 class C1["Class 1 with text label"]
499 class C2["Class 2 with chars @?"]
500 C1 --> C2`
501 );
502 });
503 it('should render a class with a text label, members and annotation', () => {
504 imgSnapshotTest(
505 `classDiagram
506 class C1["Class 1 with text label"] {
507 &lt;&lt;interface&gt;&gt;
508 +member1
509 }
510 C1 --> C2`
511 );
512 });
513 it('should render multiple classes with same text labels', () => {
514 imgSnapshotTest(
515 `classDiagram
516class C1["Class with text label"]
517class C2["Class with text label"]
518class C3["Class with text label"]
519C1 --> C2
520C3 ..> C2
521 `
522 );
523 });
524 it('should render classes with different text labels', () => {
525 imgSnapshotTest(
526 `classDiagram
527class C1["OneWord"]
528class C2["With, Comma"]
529class C3["With (Brackets)"]
530class C4["With [Brackets]"]
531class C5["With {Brackets}"]
532class C7["With 1 number"]
533class C8["With . period..."]
534class C9["With - dash"]
535class C10["With _ underscore"]
536class C11["With ' single quote"]
537class C12["With ~!@#$%^&*()_+=-/?"]
538class C13["With Città foreign language"]
539 `
540 );
541 });
542
543 it('should render classLabel if class has already been defined earlier', () => {
544 imgSnapshotTest(
545 `classDiagram
546 Animal <|-- Duck
547 class Duck["Duck with text label"]
548`
549 );
550 });
551 it('should add classes namespaces', function () {
552 imgSnapshotTest(
553 `
554 classDiagram
555 namespace Namespace1 {
556 class C1
557 class C2
558 }
559 C1 --> C2
560 class C3
561 class C4
562 `
563 );
564 });
565 it('should add notes in namespaces', function () {
566 imgSnapshotTest(
567 `
568 classDiagram
569 note "This is a outer note"
570 note for C1 "This is a outer note for C1"
571 namespace Namespace1 {
572 note "This is a inner note"
573 note for C1 "This is a inner note for C1"
574 class C1
575 }
576 `
577 );
578 });
579 it('should render a simple class diagram with no members', () => {
580 imgSnapshotTest(
581 `
582 classDiagram-v2
583 class Class10
584 `,
585 { logLevel: 1, flowchart: { htmlLabels: false } }
586 );
587 });
588 it('should render a simple class diagram with style definition', () => {
589 imgSnapshotTest(
590 `
591 classDiagram-v2
592 class Class10
593 style Class10 fill:#f9f,stroke:#333,stroke-width:4px
594 `,
595 { logLevel: 1, flowchart: { htmlLabels: false } }
596 );
597 });
598
599 it('renders a class diagram with a generic class in a namespace', () => {
600 const diagramDefinition = `
601 classDiagram-v2
602 namespace Company.Project.Module {
603 class GenericClass~T~ {
604 +addItem(item: T)
605 +getItem() T
606 }
607 }
608 `;
609
610 imgSnapshotTest(diagramDefinition);
611 });
612
613 it('renders a class diagram with nested namespaces and relationships', () => {
614 const diagramDefinition = `
615 classDiagram-v2
616 namespace Company.Project.Module.SubModule {
617 class Report {
618 +generatePDF(data: List)
619 +generateCSV(data: List)
620 }
621 }
622 namespace Company.Project.Module {
623 class Admin {
624 +generateReport()
625 }
626 }
627 Admin --> Report : generates
628 `;
629
630 imgSnapshotTest(diagramDefinition);
631 });
632
633 it('renders a class diagram with multiple classes and relationships in a namespace', () => {
634 const diagramDefinition = `
635 classDiagram-v2
636 namespace Company.Project.Module {
637 class User {
638 +login(username: String, password: String)
639 +logout()
640 }
641 class Admin {
642 +addUser(user: User)
643 +removeUser(user: User)
644 +generateReport()
645 }
646 class Report {
647 +generatePDF(reportData: List)
648 +generateCSV(reportData: List)
649 }
650 }
651 Admin --> User : manages
652 Admin --> Report : generates
653 `;
654
655 imgSnapshotTest(diagramDefinition);
656 });
657});
658