1
1
[ ![ Build Status] ( https://github.com/origin-energy/java-snapshot-testing/workflows/build/badge.svg )] ( https://github.com/origin-energy/java-snapshot-testing/actions )
2
- [ ![ Maven Central] ( https://maven-badges.herokuapp.com/maven-central/io.github.origin-energy/java-snapshot-testing-core/badge.svg )] ( https://maven-badges.herokuapp.com/maven-central /io.github.origin-energy/java-snapshot-testing-core )
2
+ [ ![ Maven Central] ( https://maven-badges.herokuapp.com/maven-central/io.github.origin-energy/java-snapshot-testing-core/badge.svg?version=3.2.7 )] ( https://search. maven.org/artifact /io.github.origin-energy/java-snapshot-testing-core/3.2.7/jar )
3
3
4
4
# Java Snapshot Testing
5
5
- Inspired by [ facebook's Jest framework] ( https://facebook.github.io/jest/docs/en/snapshot-testing.html )
6
6
7
- 🎉 3.X is live - parallel test support, easily override configuration via ` snapshot.properties ` yet * .snap format remains unchanged! This release will require some mechanical refactoring for those upgrading as ` expect ` is no longer a static method.
7
+ 🎉 4.0.0.Beta1 is live - We need testers
8
+ [ ![ Maven Central] ( https://maven-badges.herokuapp.com/maven-central/io.github.origin-energy/java-snapshot-testing-core/badge.svg?subject=4.0.0-Beta1 )] ( https://maven-badges.herokuapp.com/maven-central/io.github.origin-energy/java-snapshot-testing-core )
9
+ - Report bugs to "Issues" clearly marking them as 4.0.0-Beta
8
10
9
- Upgrade guide from 2.X to 3.X [ here] ( https://github.com/origin-energy/java-snapshot-testing/discussions/73 )
11
+ ## Upgrading
12
+ - Upgrade guild from 3.X to 4.X [ here] ( https://github.com/origin-energy/java-snapshot-testing/discussions/94 )
13
+ - Upgrade guide from 2.X to 3.X [ here] ( https://github.com/origin-energy/java-snapshot-testing/discussions/73 )
10
14
11
15
## The testing framework loved by ~~ lazy~~ __ productive__ devs
12
16
@@ -60,36 +64,36 @@ ci-env-var=CI
60
64
``` java
61
65
package au.com.origin.snapshots.docs ;
62
66
67
+ import au.com.origin.snapshots.Expect ;
63
68
import au.com.origin.snapshots.annotations.SnapshotName ;
64
69
import au.com.origin.snapshots.junit5.SnapshotExtension ;
65
70
import org.junit.jupiter.api.Test ;
66
71
import org.junit.jupiter.api.extension.ExtendWith ;
67
72
68
73
import java.util.HashMap ;
69
74
import java.util.Map ;
70
- import au.com.origin.snapshots.Expect ;
71
75
72
76
@ExtendWith ({SnapshotExtension . class})
73
77
public class MyFirstSnapshotTest {
74
78
75
- private Expect expect;
79
+ private Expect expect;
76
80
77
- @SnapshotName (" i_can_give_custom_names_to_my_snapshots" )
78
- @Test
79
- public void toStringSerializationTest () {
80
- expect. toMatchSnapshot(" Hello World" );
81
- }
81
+ @SnapshotName (" i_can_give_custom_names_to_my_snapshots" )
82
+ @Test
83
+ public void toStringSerializationTest () {
84
+ expect. toMatchSnapshot(" Hello World" );
85
+ }
82
86
83
- @Test
84
- public void jsonSerializationTest () {
85
- Map<String , Object > map = new HashMap<> ();
86
- map. put(" name" , " John Doe" );
87
- map. put(" age" , 40 );
88
-
89
- expect
90
- .serializer(" json" )
91
- .toMatchSnapshot(map);
92
- }
87
+ @Test
88
+ public void jsonSerializationTest () {
89
+ Map<String , Object > map = new HashMap<> ();
90
+ map. put(" name" , " John Doe" );
91
+ map. put(" age" , 40 );
92
+
93
+ expect
94
+ .serializer(" json" )
95
+ .toMatchSnapshot(map);
96
+ }
93
97
94
98
}
95
99
```
@@ -375,8 +379,8 @@ Here is a JUnit5 example that does not use the JUnit5 extension
375
379
package au.com.origin.snapshots.docs ;
376
380
377
381
import au.com.origin.snapshots.Expect ;
378
- import au.com.origin.snapshots.PropertyResolvingSnapshotConfig ;
379
382
import au.com.origin.snapshots.SnapshotVerifier ;
383
+ import au.com.origin.snapshots.config.PropertyResolvingSnapshotConfig ;
380
384
import org.junit.jupiter.api.AfterAll ;
381
385
import org.junit.jupiter.api.BeforeAll ;
382
386
import org.junit.jupiter.api.Test ;
@@ -385,23 +389,23 @@ import org.junit.jupiter.api.TestInfo;
385
389
// Notice we aren't using any framework extensions
386
390
public class CustomFrameworkExample {
387
391
388
- private static SnapshotVerifier snapshotVerifier;
392
+ private static SnapshotVerifier snapshotVerifier;
389
393
390
- @BeforeAll
391
- static void beforeAll () {
392
- snapshotVerifier = new SnapshotVerifier (new PropertyResolvingSnapshotConfig (), CustomFrameworkExample . class);
393
- }
394
+ @BeforeAll
395
+ static void beforeAll () {
396
+ snapshotVerifier = new SnapshotVerifier (new PropertyResolvingSnapshotConfig (), CustomFrameworkExample . class);
397
+ }
394
398
395
- @AfterAll
396
- static void afterAll () {
397
- snapshotVerifier. validateSnapshots();
398
- }
399
+ @AfterAll
400
+ static void afterAll () {
401
+ snapshotVerifier. validateSnapshots();
402
+ }
399
403
400
- @Test
401
- void shouldMatchSnapshotOne (TestInfo testInfo ) {
402
- Expect expect = Expect . of(snapshotVerifier, testInfo. getTestMethod(). get());
403
- expect. toMatchSnapshot(" Hello World" );
404
- }
404
+ @Test
405
+ void shouldMatchSnapshotOne (TestInfo testInfo ) {
406
+ Expect expect = Expect . of(snapshotVerifier, testInfo. getTestMethod(). get());
407
+ expect. toMatchSnapshot(" Hello World" );
408
+ }
405
409
406
410
}
407
411
```
@@ -444,15 +448,17 @@ Often your IDE has an excellent file comparison tool.
444
448
445
449
This file allows you to conveniently setup global defaults
446
450
447
- | key | Description |
448
- | ------------------| ----------------------------------------------------------------------------------------------------------------|
449
- | serializer | Class name of the [ serializer] ( #supplying-a-custom-snapshotserializer ) , default serializer |
450
- | serializer.{name} | Class name of the [ serializer] ( #supplying-a-custom-snapshotserializer ) , accessible via ` .serializer("{name}") ` |
451
- | comparator | Class name of the [ comparator] ( #supplying-a-custom-snapshotcomparator ) |
452
- | reporters | Comma separated list of class names to use as [ reporters] ( #supplying-a-custom-snapshotreporter ) |
453
- | snapshot-dir | Name of sub-folder holding your snapshots |
454
- | output-dir | Base directory of your test files (although it can be a different directory if you want) |
455
- | ci-env-var | Name of environment variable used to detect if we are running on a Build Server |
451
+ | key | Description |
452
+ | ------------------| ----------------------------------------------------------------------------------------------------------------------------------------|
453
+ | serializer | Class name of the [ serializer] ( #supplying-a-custom-snapshotserializer ) , default serializer |
454
+ | serializer.{name} | Class name of the [ serializer] ( #supplying-a-custom-snapshotserializer ) , accessible via ` .serializer("{name}") ` |
455
+ | comparator | Class name of the [ comparator] ( #supplying-a-custom-snapshotcomparator ) |
456
+ | comparator.{name} | Class name of the [ comparator] ( #supplying-a-custom-snapshotcomparator ) , accessible via ` .comparator("{name}") ` |
457
+ | reporters | Comma separated list of class names to use as [ reporters] ( #supplying-a-custom-snapshotreporter ) |
458
+ | reporters.{name} | Comma separated list of class names to use as [ reporters] ( #supplying-a-custom-snapshotreporter ) , accessible via ` .reporters("{name}") ` |
459
+ | snapshot-dir | Name of sub-folder holding your snapshots |
460
+ | output-dir | Base directory of your test files (although it can be a different directory if you want) |
461
+ | ci-env-var | Name of environment variable used to detect if we are running on a Build Server |
456
462
457
463
For example:
458
464
@@ -549,25 +555,27 @@ import org.junit.jupiter.api.extension.ExtendWith;
549
555
@UseSnapshotConfig (LowercaseToStringSnapshotConfig . class)
550
556
public class JUnit5ResolutionHierarchyExample {
551
557
552
- @Test
553
- public void aliasMethodTest (Expect expect ) {
554
- expect
555
- .serializer(" json" ) // <------ Using snapshot.properties
556
- .toMatchSnapshot(new TestObject ());
557
- }
558
+ private Expect expect;
558
559
559
- @Test
560
- public void customSerializerTest ( Expect expect ) {
561
- expect
562
- .serializer(UppercaseToStringSerializer . class) // <------ Using custom serializer
563
- .toMatchSnapshot(new TestObject ());
564
- }
560
+ @Test
561
+ public void aliasMethodTest ( ) {
562
+ expect
563
+ .serializer(" json " ) // <------ Using snapshot.properties
564
+ .toMatchSnapshot(new TestObject ());
565
+ }
565
566
566
- // Read from LowercaseToStringSnapshotConfig defined on the class
567
- @Test
568
- public void lowercaseTest (Expect expect ) {
569
- expect. toMatchSnapshot(new TestObject ());
570
- }
567
+ @Test
568
+ public void customSerializerTest () {
569
+ expect
570
+ .serializer(UppercaseToStringSerializer . class) // <------ Using custom serializer
571
+ .toMatchSnapshot(new TestObject ());
572
+ }
573
+
574
+ // Read from LowercaseToStringSnapshotConfig defined on the class
575
+ @Test
576
+ public void lowercaseTest () {
577
+ expect. toMatchSnapshot(new TestObject ());
578
+ }
571
579
}
572
580
```
573
581
@@ -588,39 +596,40 @@ import au.com.origin.snapshots.jackson.serializers.DeterministicJacksonSnapshotS
588
596
import com.fasterxml.jackson.databind.ObjectMapper ;
589
597
import com.fasterxml.jackson.annotation.JsonIgnore ;
590
598
import com.fasterxml.jackson.annotation.JsonIgnoreType ;
599
+ import com.fasterxml.jackson.databind.ObjectMapper ;
591
600
592
601
import java.time.Instant ;
593
602
import java.util.List ;
594
603
import java.util.Set ;
595
604
596
605
public class HibernateSnapshotSerializer extends DeterministicJacksonSnapshotSerializer {
597
606
598
- @Override
599
- public void configure (ObjectMapper objectMapper ) {
600
- super . configure(objectMapper);
607
+ @Override
608
+ public void configure (ObjectMapper objectMapper ) {
609
+ super . configure(objectMapper);
601
610
602
- // Ignore Hibernate Lists to prevent infinite recursion
603
- objectMapper. addMixIn(List . class, IgnoreTypeMixin . class);
604
- objectMapper. addMixIn(Set . class, IgnoreTypeMixin . class);
611
+ // Ignore Hibernate Lists to prevent infinite recursion
612
+ objectMapper. addMixIn(List . class, IgnoreTypeMixin . class);
613
+ objectMapper. addMixIn(Set . class, IgnoreTypeMixin . class);
605
614
606
- // Ignore Fields that Hibernate generates for us automatically
607
- objectMapper. addMixIn(BaseEntity . class, IgnoreHibernateEntityFields . class);
608
- }
615
+ // Ignore Fields that Hibernate generates for us automatically
616
+ objectMapper. addMixIn(BaseEntity . class, IgnoreHibernateEntityFields . class);
617
+ }
609
618
610
- @JsonIgnoreType
611
- class IgnoreTypeMixin {
612
- }
619
+ @JsonIgnoreType
620
+ class IgnoreTypeMixin {
621
+ }
613
622
614
- abstract class IgnoreHibernateEntityFields {
615
- @JsonIgnore
616
- abstract Long getId ();
623
+ abstract class IgnoreHibernateEntityFields {
624
+ @JsonIgnore
625
+ abstract Long getId ();
617
626
618
- @JsonIgnore
619
- abstract Instant getCreatedDate ();
627
+ @JsonIgnore
628
+ abstract Instant getCreatedDate ();
620
629
621
- @JsonIgnore
622
- abstract Instant getLastModifiedDate ();
623
- }
630
+ @JsonIgnore
631
+ abstract Instant getLastModifiedDate ();
632
+ }
624
633
}
625
634
```
626
635
@@ -650,20 +659,21 @@ and field order are ignored.
650
659
``` java
651
660
package au.com.origin.snapshots.docs ;
652
661
662
+ import au.com.origin.snapshots.Snapshot ;
653
663
import au.com.origin.snapshots.comparators.SnapshotComparator ;
654
664
import com.fasterxml.jackson.databind.ObjectMapper ;
655
665
import lombok.SneakyThrows ;
656
666
657
667
public class JsonObjectComparator implements SnapshotComparator {
658
- @Override
659
- public boolean matches (String snapshotName , String rawSnapshot , String currentObject ) {
660
- return asObject(snapshotName, rawSnapshot) . equals(asObject(snapshotName, currentObject ));
661
- }
668
+ @Override
669
+ public boolean matches (Snapshot previous , Snapshot current ) {
670
+ return asObject(previous . getName(), previous . getBody()) . equals(asObject(current . getName(), current . getBody() ));
671
+ }
662
672
663
- @SneakyThrows
664
- private static Object asObject (String snapshotName , String json ) {
665
- return new ObjectMapper (). readValue(json. replaceFirst(snapshotName, " " ), Object . class);
666
- }
673
+ @SneakyThrows
674
+ private static Object asObject (String snapshotName , String json ) {
675
+ return new ObjectMapper (). readValue(json. replaceFirst(snapshotName + " = " , " " ), Object . class);
676
+ }
667
677
}
668
678
```
669
679
@@ -686,23 +696,24 @@ a custom reporter can be created like the one below.
686
696
``` java
687
697
package au.com.origin.snapshots.docs ;
688
698
699
+ import au.com.origin.snapshots.Snapshot ;
689
700
import au.com.origin.snapshots.reporters.SnapshotReporter ;
690
701
import au.com.origin.snapshots.serializers.SerializerType ;
691
702
import lombok.SneakyThrows ;
692
703
import org.skyscreamer.jsonassert.JSONAssert ;
693
704
import org.skyscreamer.jsonassert.JSONCompareMode ;
694
705
695
706
public class JsonAssertReporter implements SnapshotReporter {
696
- @Override
697
- public boolean supportsFormat (String outputFormat ) {
698
- return SerializerType . JSON. name(). equalsIgnoreCase(outputFormat);
699
- }
707
+ @Override
708
+ public boolean supportsFormat (String outputFormat ) {
709
+ return SerializerType . JSON. name(). equalsIgnoreCase(outputFormat);
710
+ }
700
711
701
- @Override
702
- @SneakyThrows
703
- public void report (String snapshotName , String rawSnapshot , String currentObject ) {
704
- JSONAssert . assertEquals(rawSnapshot, currentObject , JSONCompareMode . STRICT );
705
- }
712
+ @Override
713
+ @SneakyThrows
714
+ public void report (Snapshot previous , Snapshot current ) {
715
+ JSONAssert . assertEquals(previous . getBody(), current . getBody() , JSONCompareMode . STRICT );
716
+ }
706
717
}
707
718
```
708
719
@@ -722,14 +733,30 @@ import org.junit.jupiter.api.Test;
722
733
import org.junit.jupiter.api.extension.ExtendWith ;
723
734
724
735
@ExtendWith (SnapshotExtension . class)
725
- // apply your custom snapshot configuration to this test class
726
736
@UseSnapshotConfig (LowercaseToStringSnapshotConfig . class)
727
- public class CustomSnapshotConfigExample {
737
+ public class JUnit5ResolutionHierarchyExample {
728
738
729
- @Test
730
- public void myTest (Expect expect ) {
731
- expect. toMatchSnapshot(" hello world" );
732
- }
739
+ private Expect expect;
740
+
741
+ @Test
742
+ public void aliasMethodTest () {
743
+ expect
744
+ .serializer(" json" ) // <------ Using snapshot.properties
745
+ .toMatchSnapshot(new TestObject ());
746
+ }
747
+
748
+ @Test
749
+ public void customSerializerTest () {
750
+ expect
751
+ .serializer(UppercaseToStringSerializer . class) // <------ Using custom serializer
752
+ .toMatchSnapshot(new TestObject ());
753
+ }
754
+
755
+ // Read from LowercaseToStringSnapshotConfig defined on the class
756
+ @Test
757
+ public void lowercaseTest () {
758
+ expect. toMatchSnapshot(new TestObject ());
759
+ }
733
760
}
734
761
```
735
762
0 commit comments