Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Populate MongoDb TestContainers in a SpringBoot for integration test

My question is similar to Populate a database with TestContainers in a SpringBoot integration test but instead I have a mongo db test container as follows:

@Container
private static MongoDBContainer mongoDBContainer = new MongoDBContainer(DockerImageName.parse("mongo:3.4.20")) 

I can use mongorepository.save() but that's not really feasible as there are multiple collections and I need populate several fields (and a bunch of them are nested fields). What are some other ways to achieve the same?

like image 896
Diluted Dev Avatar asked Jan 18 '26 18:01

Diluted Dev


2 Answers

A way I've done it in the past when I need some initial data in the database is by adding an ApplicationContextInitializer that boots up the testcontainer and then run a mongorestore inside the container for loading a mongodump I prepared separately.

This way you can keep your dump folder in your test-resources folder. Ofcourse, if you have other files there be sure to use to the correct classpath resource path.

Hope this helps!

public class TestContainerInitializer implements ApplicationContextInitializer<ConfigurableApplicationContext> {
    
    @SneakyThrows
    @Override
    public void initialize(ConfigurableApplicationContext context) {
        MongoDBContainer instance = MongoContainerSingleton.getInstance();
        instance.copyFileToContainer(
                    MountableFile.forClasspathResource("/"), "/IT-dump");
        Container.ExecResult mongorestore = instance.execInContainer("mongorestore", "/IT-dump/dump/");
    }
    
    public static class MongoContainerSingleton {
    
        private static volatile MongoDBContainer instance = null;
    
        public static MongoDBContainer getInstance() {
            synchronized (MongoContainerSingleton.class) {
                if (instance == null) {
                    instance = new MongoDBContainer("mongo:4.2.11")
                            .withReuse(true);
                    instance.start();
                }
            }
            return instance;
        }
    }
}
like image 180
kristof.taveirne Avatar answered Jan 21 '26 08:01

kristof.taveirne


There is a liquibase mongodb project which can be used. You can take a look at this project. There is a db.changelog-master.json where the schema creation is defined as a first changelog (you can define more) and as you can see in the test just defined the container, set the spring.data.mongodb.uri and manually run the migration due to spring boot does not offer autoconfigure for liquibase mongodb extension.

 @Container
    private static final MongoDBContainer mongo = new MongoDBContainer("mongo:4.0.10");

    @Autowired
    private PersonRepository repository;

    @DynamicPropertySource
    static void mongoProperties(DynamicPropertyRegistry registry) {
        registry.add("spring.data.mongodb.uri", mongo::getConnectionString);
    }

    @Test
    void test() throws LiquibaseException {
        var database = (MongoLiquibaseDatabase) DatabaseFactory.getInstance().openDatabase(mongo.getReplicaSetUrl("test"), null, null, null, null);
        var liquibase = new Liquibase("db/changelog/db.changelog-master.json", new ClassLoaderResourceAccessor(), database);
        liquibase.update("");

        var books = this.repository.findAll();
        assertThat(books).hasSize(3);
    }

This sample project is based in spring boot too.

Also, check Initializing a fresh instance

like image 39
Eddú Meléndez Avatar answered Jan 21 '26 06:01

Eddú Meléndez



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!