Java Testing with Spock
Description
This GIT repository contains all source code for the book Java Testing With Spock published by Manning. Each chapter is offered as an independent Maven project.
Free chapter 1 - (intro to testing)
You can get an overview of Spock and read a brief discussion on its features in the first chapter of the book. This chapter is freely available in PDF format.
Free chapter 3 - (comparison with JUnit)
The book contains a comparison of JUnit and Spock using semi-real world code examples. If you are a die-hard JUnit believer, you will find this part of the book very interesting. This chapter is also freely available in PDF format.
Requirements
To use the code samples you need the following:
- Java Development Kit version 7+
- Maven installed (mvn should be available in the command line)
- Internet access (for fetching library dependencies)
Usage
You can checkout/run any chapter on its own. You can either work directly on Github or download the code as a ZIP file For each chapter entering the command mvn test will compile and run all JUnit/Spock tests.
IDE support
Each chapter is self-contained. There is no super POM file. This repository is NOT a multimodule project. If you use Eclipse just import any chapter as a Maven project. If you use IntelliJ make sure that you import each chapter on its own project (and not as modules in a single project). To gain syntax highlighting you also need to install Groovy support in your IDE. This is optional because the build is fully automated via Maven.
Gradle Support
There are also build.gradle files along side each maven pom.xml file in each chapter if you would like to see what an analogous gradle build file looks like. You also do not have to download and install Gradle either as the gradle wrapper files are also included in this repository. Simply type ./gradlew clean test at the project root and Gradle will build the project and run the tests.
You can also import the build.gradle files into Eclipse if you have the Gradle Buildship plugin installed. If you are using Intellij IDEA, you can also import each chapter on its own similar to how Maven projects are imported. The idea and eclipse plugins are also configured in each build.gradle file if you want to generate the metadata files for Eclipse and IDEA projects.
Note that Gradle support was contributed by [Mike Smithson] (https://github.com/mikesmithson) and is considered a bonus feature. I will provide no support for Gradle and any related issues, i.e., you are on your own.
Code listings
Chapter 1
- Listing 1.1 Sample Spock test
- Listing 1.2 Java class under test
- Listing 1.2 JUnit test
- Listing 1.3 Spock test for the Adder Java class
- Listing 1.4 JUnit test for two Java classes
- Listing 1.5 Spock test for two Java classes
- Listing 1.6 Introducing an artificial bug in the Java class under test
- Listing 1.7 A JUnit test where method names are unrelated to business value
- Listing 1.8 A Spock test where methods explain the business requirements
Chapter 2
- Listing 2.1 Groovy class conventions
- Listing 2.1 Groovy class conventions
- Listing 2.2 Groovy field conventions
- Listing 2.3 A complete Groovy script
- Listing 2.4 A Spock test using concise Groovy code
- Listing 2.5 Creating and using a Java class from Groovy
- Listing 2.5 Creating and using a Java class from Groovy
- Listing 2.6 Groovy optional typing in variables
- Listing 2.7 Groovy optional typing in methods
- Listing 2.8 Using dynamic typing in Spock methods
- Listing 2.9 Groovy can convert everything to a boolean
- Listing 2.10 Groovy truth used in Spock tests
- Listing 2.11 JUnit test with multiple object creation statements
- Listing 2.12 Spock test with map-based constructors
- Listing 2.13 Groovy versus Java maps
- Listing 2.14 Groovy maps with non-scalar keys and values
- Listing 2.15 Groovy versus Java lists
- Listing 2.16 Creating Groovy lists and maps in test code
- Listing 2.17 Using Groovy lists
- Listing 2.18 Using Groovy maps
- Listing 2.19 Using Groovy String
- Listing 2.20 Using Groovy multiline strings
- Listing 2.21 Reading test data from a file in a Spock test
- Listing 2.22 Reading XML in Groovy
- Listing 2.23 Reading JSON in Groovy
- Listing 2.24 Groovy closures
- Listing 2.25 Using Groovy closures in Spock tests
- Listing 2.26 Domain classes in Java
- Listing 2.27 Using a Groovy builder for quick object creation
- Bonus listing - Complex object creation in Java
- Listing 2.28 Using Expandos to mock interfaces
- Listing 2.29 Using a Groovy Expando as test data generator
Chapter 3
- Listing 3.1 A fire control system in Java
- Listing 3.1 A fire control system in Java
- Listing 3.2 A JUnit test for the fire control system
- Listing 3.3 JUnit test with complex structure (real example)
- Listing 3.4 JUnit test that tests two things - DO NOT DO THIS
- Listing 3.5 The full Spock test for the fire control system
- Listing 3.6 Testing the nuclear reactor scenarios with JUnit
- Listing 3.7 Testing the nuclear reactor scenarios with Spock
- Listing 3.8 Java classes for the temperature monitor and reader
- Listing 3.9 Stubbing with Spock
- Listing 3.10 Java classes for the temperature monitor, reader and reactor control
- Listing 3.11 Mocking and Stubbing with Spock
- Bonus Listing - Mocking and Stubbing with JUnit and Mockito
- Listing 3.12 Mocking/Stubbing in a Spock parameterized test
Chapter 4
- Listing 4.1 Spock blocks inside a test method
- Listing 4.2 Java skeleton for an electronic basket
- Listing 4.2 Java skeleton for an electronic basket
- Listing 4.3 The given-when-then triad
- Listing 4.4 Using the setup alias
- Listing 4.5 A non-trivial when: block - DO NOT DO THIS
- Listing 4.6 Descriptive when: blocks
- Listing 4.7 Invalid then: block
- Listing 4.8 - Using and: to split the given: block
- Listing 4.9 Using and: to split the when: block
- Listing 4.10 Using and: as an extension to a then: block
- Listing 4.11 Trivial tests with the expect: block
- Listing 4.12 Expect block replaces when: and then:
- Listing 4.13 Using expect: for pre-conditions
- Listing 4.14 Using cleanup: to release resources even if test fails
- Listing 4.15 test method describes exactly what is being tested.
- Listing 4.16 Marking the class under test
- Listing 4.17 Writing a Spock specification
- Listing 4.18 Writing a full Spock specification
- Listing 4.19 Extracting common initialization code
- Listing 4.20 Extracting common pre/post conditions
- Listing 4.21 All Spock lifecycle methods
- Listing 4.22 Using the @Shared annotation
- Listing 4.23 Asserting with the old() method
- Listing 4.24 Multiple when-then blocks
- Listing 4.25 Missing block descriptions - DO NOT DO THIS
- Listing 4.26 Adding a product twice in the basket
- Listing 4.27 Helping failure rendering in the toString() method
- Listing 4.28 Spock support for Hamcrest matchers
- Listing 4.29 Alternative Spock support for Hamcrest matchers
- Listing 4.30 Using Groovy closures in Spock assertions
- Listing 4.31 An imaginary warehouse
- Listing 4.32 An enterprisy basket
- Listing 4.33 Assertions and setup on the same object
- Listing 4.34 Grouping similar code with Groovy and Spock
Chapter 5
- Listing 5.1 Duplicate tests - DO NOT DO THIS
- Listing 5.2 Simple Spock parameterized test
- Listing 5.3 The given-when-then-where structure
- Listing 5.4 Using data tables in Spock
- Listing 5.5 Using data tables in Spock with typed parameters
- Listing 5.6 Data tables with one column
- Listing 5.7 Capturing business needs in data tables
- Listing 5.8 Lifecycle of parameterized tests
- Listing 5.9 Unrolling parameterized scenarios
- Listing 5.10 Printing parameters of each scenario
- Listing 5.11 Parameter rendering on the test method
- Listing 5.12 Custom expressions in data tables
- Listing 5.13 Trivial example of data pipes
- Listing 5.14 Using Groovy ranges as data generators
- Listing 5.15 Using Groovy combinations
- Listing 5.16 Constant parameters in Spock tests
- Listing 5.17 Derived parameters in Spock tests
- Data file validImageNames.txt
- Listing 5.18 Using existing data generators
- Data file invalidImageNames.txt
- Listing 5.19 Java iterator that processes invalidImageNames.txt
- Listing 5.20 Using Java iterators in Spock
- Data file imageNames.txt
- Listing 5.21 Java multi-valued iterator
- Listing 5.22 Using multi-valued iterators in Spock
- Listing 5.23 Using multi-valued assignments in Spock
Chapter 6
- Listing 6.1 Java skeleton code for the eshop
- Listing 6.1 Java skeleton code for the eshop
- Listing 6.1 Java skeleton code for the eshop
- Listing 6.2 Creating a Simple Stub with Spock
- Listing 6.3 Stubbing specific arguments
- Listing 6.4 Argument based stub differentiation
- Listing 6.5 Grouping all stubbed methods
- Listing 6.6 Using argument matchers in stubs
- Listing 6.7 Ignoring all arguments of a stubbed method when returning a response
- Listing 6.8 Stubbing subsequent method calls
- Listing 6.9 Instructing stubs to throw exceptions
- Listing 6.10 Stubs that respond according to arguments
- Listing 6.11 A smart stub that looks at both its arguments
- Listing 6.12 Stubbing responses with other stubs
- Listing 6.13 Mocks can be stubbed too
- Listing 6.14 Java skeleton for credit card charging
- Listing 6.14 Java skeleton for credit card charging
- Listing 6.14 Java skeleton for credit card charging
- Listing 6.14 Java skeleton for credit card charging
- Listing 6.15 Verification of a mocked method
- Listing 6.16 Verification of a specific order of mocked methods
- Listing 6.17 Explicit declaration of interactions
- Listing 6.18 Verifying interactions for all methods of a class
- Listing 6.19 Verifying non-interactions for all mocks
- Listing 6.20 Verifying that arguments were not null when a mocked method is called
- Listing 6.21 Verifying the type of arguments
- Listing 6.22 Verifying exact arguments of a mocked method
- Listing 6.23 Verifying part of a object instance used as a mock argument
- Listing 6.24 Using full Groovy closures for argument verification
- Listing 6.25 Using Mocks and Stubs in the same test
- Listing 6.26 Verifying a sequence of events with interconnected method calls
- Solution to exercise
Chapter 7
- Listing 7.1 Access Spring context from a Spock test
- Listing 7.2 Rolling back database changes automatically
- Listing 7.3 Using a reduced Spring context for unit testing
- Listing 7.4 Using Groovy SQL to prepare the DB in a Spock test
- Listing 7.5 Using Groovy SQL to prepare the DB in a Spock test - improved
- Listing 7.6 Manual Spring context creation
- Listing 7.7 Testing REST services with Spock and Spring RestTemplate
- Listing 7.8 Running multiple test methods in order
- Listing 7.9 Using Groovy Rest Client in a Spock test
- Listing 7.10 Using Geb and Spock together
- Listing 7.11 Using Geb to access page content
- Listing 7.12 Using Geb to submit HTML forms
- Listing 7.13 Running Spock functional tests on a Tomcat instance
- Listing 7.14 Using JaCoCo with Spock
Chapter 8
- Listing 8.1 Expecting an exception in a Spock test
- Listing 8.2 Detailed examination of an expected exception
- Listing 8.3 Explicit declaration that an exception should not happen
- Listing 8.4 Marking a test method with the issue it solves
- Listing 8.5 Using the URL of an issue solved by a Spock test
- Listing 8.6 Marking a Spock test with multiple issues
- Listing 8.7 Declaring a test timeout
- Listing 8.8 Declaring a test timeout - custom unit
- Listing 8.9 Ignoring a single test
- Listing 8.10 Ignoring all tests apart from one
- Listing 8.11 Skipping Spock tests according to the environment
- Listing 8.12 Skipping a Spock test based on a dynamic precondition
- Listing 8.13 Requires is the opposite of IgnoreIf
- Listing 8.14 Release resources with AutoCleanup
- Listing 8.15 A Spock test with very long setup - DO NOT DO THIS
- Listing 8.16 Spock test with helper methods
- Listing 8.17 Using arguments that imply their importance in the test
- Listing 8.18 Spock test with dubious then: block
- Listing 8.19 Improved Spock test with clear separation of checks
- Listing 8.20 Using helper methods for assertions
- Listing 8.21 Spock tests with questionable then: block
- Listing 8.22 Helper methods with interactions need to be declared explicitly
- Listing 8.23 Java code with questionable design
- Listing 8.23 Java code with questionable design
- Listing 8.23 Java code with questionable design
- Listing 8.24 Creating a spy with Spock
- Listing 8.25 Refactoring Java code to avoid spies
- Listing 8.26 Using a mock instead of a spy
Issues with the code.
If you find a problem with the code feel free to open an issue. If you feel like contributing you can even create a pull request!
Issues with the book
If you have comments and suggestions for the book please use the Manning forum. I monitor it regularly and it is helpful if other readers can see and respond to your comments.
Enjoy!