Testcontainers and Java: Using properties instead of hardcoded configuration
Recently working with Testcontainers I had a goal, externalize the variant values, eg, docker image name, ports, users, etc. In this article I’ll explain how to do it, and remember this is the 3rd item on The Twelve-Factor app.
1. Definitions
- Testcontainers → Testcontainers is a Java library that supports JUnit tests, providing lightweight, throwaway instances of common databases, Selenium web browsers, or anything else that can run in a Docker container. (Testcontainers)
- Java → Java is the #1 programming language and development platform. It reduces costs, shortens development timeframes, drives innovation, and improves application services. With millions of developers running more than 51 billion Java Virtual Machines worldwide, Java continues to be the development platform of choice for enterprises and developers.(Oracle)
- Docker → Docker is a set of platform as a service (PaaS) products that use OS-level virtualization to deliver software in packages called containers. (Docker)
2. Problem
Following The Twelve-Factor app, I want to expose all my configuration in the application configuration and have zero hard code values.
3. Test scope
The scope for the test is: Call the Movie API using Testcontainers, and the Testcontainers will have to start the image using in-memory profile, check below
4. Hands on
In this hands on I’ll show how to move from a hard coded configuration to a property configuration, in my opinion the best choice.
4.1. Works but not ideal
The code below works a charm, but becomes less flexible to change the docker version, profile, port, users and so on.
4.2. Meet the goal
Let’s work 👷 to make it feasible. Follow the instructions below
- Create a new property file, eg, application-testcontainers.properties
- A new class to read the configuration and make available to the test
- And the last but not the least, change all hard-coded configuration by config properties
4.2.1. New property file
This property has few keys and values, but enough for the scope.
4.2.2. New class
This new class will use the Singleton pattern and load the file, parse it.
4.2.3. Hard coded by config values
5. Tech stack
- Java → openJDK11
- Gradle → 7.4
- Testcontainers →1.17.2
- Docker Desktop → 4.9.0
- Docker →20.10.16
If you like this article, please subscribe and give your claps 👏 :).
6. Conclusion
The change made in the configuration file is smoother than code change, and enables anyone to do it, moreover is less error prone.