15
15
use ThenLabs \PyramidalTests \Annotation \ImportDecorators ;
16
16
use ThenLabs \PyramidalTests \Decorator \DecoratorsRegistry ;
17
17
use ThenLabs \PyramidalTests \Decorator \PackageInterface as DecoratorPackageInterface ;
18
+ use ThenLabs \PyramidalTests \Extension \SystemSnapshot ;
19
+ use ThenLabs \PyramidalTests \Extension \SystemSnapshot \SnapshotsInDecoratorsInterface ;
18
20
19
21
AnnotationRegistry::registerFile (__DIR__ .'/../Annotation/Decorator.php ' );
20
22
AnnotationRegistry::registerFile (__DIR__ .'/../Annotation/ImportDecorators.php ' );
@@ -61,6 +63,16 @@ class TestCaseModel extends AbstractModel implements CompositeComponentInterface
61
63
*/
62
64
protected $ invokedSetUpBeforeClass = false ;
63
65
66
+ /**
67
+ * @var array
68
+ */
69
+ protected $ systemSnapshotBeforeFirstSetUpBeforeClassDecorator = [];
70
+
71
+ /**
72
+ * @var bool
73
+ */
74
+ protected $ includedSetUpBeforeClassDecoratorForSystemSnapshot = false ;
75
+
64
76
/**
65
77
* @var Closure
66
78
*/
@@ -86,6 +98,11 @@ class TestCaseModel extends AbstractModel implements CompositeComponentInterface
86
98
*/
87
99
protected $ tearDownAfterClassClosure ;
88
100
101
+ /**
102
+ * @var array<string, Closure>
103
+ */
104
+ protected $ tearDownAfterClassDecorators = [];
105
+
89
106
/**
90
107
* @var bool
91
108
*/
@@ -96,11 +113,26 @@ class TestCaseModel extends AbstractModel implements CompositeComponentInterface
96
113
*/
97
114
protected $ invokedTearDownAfterClass = false ;
98
115
116
+ /**
117
+ * @var array
118
+ */
119
+ protected $ systemSnapshotAfterLastTearDownAfterClassDecorator = [];
120
+
121
+ /**
122
+ * @var bool
123
+ */
124
+ protected $ includedTearDownAfterClassDecoratorForSystemSnapshot = false ;
125
+
99
126
/**
100
127
* @var array
101
128
*/
102
129
protected $ macros = [];
103
130
131
+ /**
132
+ * @var array
133
+ */
134
+ protected $ diffExpectationsForSystemSnapshot = [];
135
+
104
136
public function __construct (string $ title , Closure $ closure )
105
137
{
106
138
parent ::__construct ($ title , $ closure );
@@ -141,7 +173,7 @@ public function buildClass(): void
141
173
142
174
if (count ($ setUpBeforeClassDecorators )) {
143
175
$ this ->setUpBeforeClassClosure = function () use ($ setUpBeforeClassDecorators , $ currentSetUpBeforeClassClosure ) {
144
- foreach ($ setUpBeforeClassDecorators as $ title => $ setUpBeforeClassDecorator ) {
176
+ foreach ($ setUpBeforeClassDecorators as $ setUpBeforeClassDecorator ) {
145
177
$ setUpBeforeClassDecorator ();
146
178
}
147
179
@@ -227,6 +259,21 @@ public function buildClass(): void
227
259
}
228
260
229
261
// tearDownAfterClass
262
+ $ tearDownAfterClassDecorators = $ this ->tearDownAfterClassDecorators ;
263
+ $ currentTearDownAfterClassClosure = $ this ->tearDownAfterClassClosure ;
264
+
265
+ if (count ($ tearDownAfterClassDecorators )) {
266
+ $ this ->tearDownAfterClassClosure = function () use ($ tearDownAfterClassDecorators , $ currentTearDownAfterClassClosure ) {
267
+ foreach ($ tearDownAfterClassDecorators as $ tearDownAfterClassDecorator ) {
268
+ $ tearDownAfterClassDecorator ();
269
+ }
270
+
271
+ if ($ currentTearDownAfterClassClosure instanceof Closure) {
272
+ $ currentTearDownAfterClassClosure ();
273
+ }
274
+ };
275
+ }
276
+
230
277
if ($ this ->tearDownAfterClassClosure instanceof Closure) {
231
278
$ tearDownAfterClassClosure = $ this ->tearDownAfterClassClosure ;
232
279
@@ -446,6 +493,33 @@ public function __call($decoratorName, $arguments)
446
493
throw new Exception ("Decorator ' {$ decoratorName }' for class ' {$ this ->baseClassBuilder ->getParentClass ()}' is missing. " );
447
494
}
448
495
496
+ if ($ this ->hasSnapshotsInDecoratorsInterface ()) {
497
+ if (! $ this ->includedSetUpBeforeClassDecoratorForSystemSnapshot ) {
498
+ $ setUpBeforeClassDecoratorForSystemSnapshot = function () use ($ thisTestCaseModel ) {
499
+ $ thisTestCaseModel ->setSystemSnapshotBeforeFirstSetUpBeforeClassDecorator (SystemSnapshot::getSnapshot ());
500
+ };
501
+
502
+ $ this ->setUpBeforeClassDecorators [] = $ setUpBeforeClassDecoratorForSystemSnapshot ;
503
+ $ this ->includedSetUpBeforeClassDecoratorForSystemSnapshot = true ;
504
+ }
505
+
506
+ if (! $ this ->includedTearDownAfterClassDecoratorForSystemSnapshot ) {
507
+ $ tearDownAfterClassDecoratorForSystemSnapshot = function () use ($ thisTestCaseModel ) {
508
+ $ systemSnapshot = SystemSnapshot::getSnapshot ();
509
+ $ thisTestCaseModel ->setSystemSnapshotAfterLastTearDownAfterClassDecorator ($ systemSnapshot );
510
+
511
+ SystemSnapshot \Assert::assertExpectedArrayDiff (
512
+ $ thisTestCaseModel ->getSystemSnapshotBeforeFirstSetUpBeforeClassDecorator (),
513
+ $ thisTestCaseModel ->getSystemSnapshotAfterLastTearDownAfterClassDecorator (),
514
+ $ thisTestCaseModel ->getDiffExpectationsForSystemSnapshot ()
515
+ );
516
+ };
517
+
518
+ $ this ->tearDownAfterClassDecorators [] = $ tearDownAfterClassDecoratorForSystemSnapshot ;
519
+ $ this ->includedTearDownAfterClassDecoratorForSystemSnapshot = true ;
520
+ }
521
+ }
522
+
449
523
$ setUpBeforeClassDecorator = $ decorator ->getClosure ($ arguments );
450
524
451
525
if ($ setUpBeforeClassDecorator instanceof Closure) {
@@ -525,4 +599,55 @@ public function addExecutedDecorator(string $title): void
525
599
{
526
600
$ this ->executedDecorators [] = $ title ;
527
601
}
602
+
603
+ public function hasSnapshotsInDecoratorsInterface (): bool
604
+ {
605
+ $ interfaceNames = [
606
+ ...$ this ->classBuilder ->getInterfaces (),
607
+ ...$ this ->baseClassBuilder ->getInterfaces (),
608
+ ];
609
+
610
+ foreach ($ interfaceNames as $ interfaceName ) {
611
+ if ($ interfaceName === SnapshotsInDecoratorsInterface::class) {
612
+ return true ;
613
+ }
614
+ }
615
+
616
+ $ reflection = new ReflectionClass ($ this ->baseClassBuilder ->getParentClass ());
617
+
618
+ return $ reflection ->implementsInterface (SnapshotsInDecoratorsInterface::class);
619
+ }
620
+
621
+ public function setSystemSnapshotBeforeFirstSetUpBeforeClassDecorator (array $ systemSnapshot ): void
622
+ {
623
+ $ this ->systemSnapshotBeforeFirstSetUpBeforeClassDecorator = $ systemSnapshot ;
624
+ }
625
+
626
+ public function getSystemSnapshotBeforeFirstSetUpBeforeClassDecorator (): array
627
+ {
628
+ return $ this ->systemSnapshotBeforeFirstSetUpBeforeClassDecorator ;
629
+ }
630
+
631
+ public function setSystemSnapshotAfterLastTearDownAfterClassDecorator (array $ systemSnapshot ): void
632
+ {
633
+ $ this ->systemSnapshotAfterLastTearDownAfterClassDecorator = $ systemSnapshot ;
634
+ }
635
+
636
+ public function getSystemSnapshotAfterLastTearDownAfterClassDecorator (): array
637
+ {
638
+ return $ this ->systemSnapshotAfterLastTearDownAfterClassDecorator ;
639
+ }
640
+
641
+ public function addDiffExpectationsForSystemSnapshot (array $ expectations ): void
642
+ {
643
+ $ this ->diffExpectationsForSystemSnapshot = array_merge_recursive (
644
+ $ this ->diffExpectationsForSystemSnapshot ,
645
+ $ expectations
646
+ );
647
+ }
648
+
649
+ public function getDiffExpectationsForSystemSnapshot (): array
650
+ {
651
+ return $ this ->diffExpectationsForSystemSnapshot ;
652
+ }
528
653
}
0 commit comments