Search code examples
scaladockerscalatestdocker-javatestcontainers

Can't connect to Cassandra docker container in Scala Tests


I am quite desperately trying to set up docker tests in Scala.

I have created an example project on GitHub to understand how should I set up the environment. It is available here: https://github.com/atais/sbt-scala-docker-cassandra


I have selected spotify/cassandra:latest image https://github.com/spotify/docker-cassandra.

Since I am using ScalaTest I wanted to use one of the Scala wrappers, but both fail on me.

1. https://github.com/whisklabs/docker-it-scala

The container is defined as:

val cassandraContainer: DockerContainer = DockerContainer("spotify/cassandra:latest")
    .withPorts(9042 -> None, 9060 -> None)

It is CassandraDockerTest in the project.

2. https://github.com/testcontainers/testcontainers-scala

The container is defined as:

override val container = GenericContainer(
  "spotify/cassandra:latest",
  exposedPorts = Seq(9042, 9160)
) 

It is CassandraContainerTest in the project.

My assumption

What seems to be an issue (in both cases) is that the container starts, but the ports are never accessible:

CONTAINER ID        IMAGE                      COMMAND                  CREATED             STATUS              PORTS                                                                                                                                                                                                   NAMES
7cb5fc91a97d        spotify/cassandra:latest   "cassandra-singlenode"   3 seconds ago       Up 2 seconds        0.0.0.0:33121->22/tcp, 0.0.0.0:33120->7000/tcp, 0.0.0.0:33119->7001/tcp, 0.0.0.0:33118->7199/tcp, 0.0.0.0:33117->8012/tcp, 0.0.0.0:33116->9042/tcp, 0.0.0.0:33115->9160/tcp, 0.0.0.0:33114->61621/tcp   quirky_chandrasekhar

And I would like 9042 and 9160 to be available on 0.0.0.0, and for some reason, they are not, even though the configuration for them is specified.

Thanks!


Solution

  • I have managed to find the solution(s)

    docker-it-scala

    Working container definition

    val cassandraContainer: DockerContainer = DockerContainer("spotify/cassandra:latest")
        .withPorts(9042 -> Some(9042), 9160 -> Some(9160))
        .withReadyChecker(DockerReadyChecker.LogLineContains("Listening for thrift clients"))
    
    1. To bind the ports properly use (Port -> Some(Port))
    2. It is necessary to wait for the container to start (silly me)

    testcontainers-scala

    Working container definition

    override val container = GenericContainer(
        "spotify/cassandra:latest",
        exposedPorts = Seq(9042, 9160),
        waitStrategy = new LogMessageContainsStrategy("Listening for thrift clients")
    )
    
    1. testcontainers do not allow to define ports redirection. Instead, one must use getMappedPort method to obtain the port on host. Thanks @bsideup
    2. Wait for container is necessary.

    A more detailed description is available on GitHub. Also one can use it as a reference/example. https://github.com/atais/sbt-scala-docker-cassandra