Why do I get Unable to create container with image Unable to pull image error pulling image when using multiple Docker hosts?

Viewed 935

I am trying to perform a simple deployment using terraform (0.12.24), and multiple Docker providers (plugin version 2.7.0). My aim using the terraform template below is to deploy two different containers to two different Docker-enabled hosts.

# Configure the Docker provider
provider "docker" {
  host = "tcp://192.168.1.10:2375/"
}

provider "docker" {
  alias = "worker"
  host = "tcp://127.0.0.1:2375/"
}

# Create a container
resource "docker_container" "hello" {
  image = docker_image.world.latest
  name  = "hello"
}

resource "docker_container" "test" {
  provider = docker.worker
  image = docker_image.world.latest
  name  = "test"
}

resource "docker_image" "world" {
  name = "hello-world:latest"
}

The docker command runs successfully without root privileges. The Docker daemons of both machines 192.168.1.10 and 127.0.0.1 listen on 2375, are reachable from the host machine and can respond to direct Docker REST API calls (create,pull etc.) performed with curl. Manually pulling images also works in both hosts, and I did that to be sure that the latest hello-world image exists in both.

However, the terraform deployment (terraform apply) fails with the following error:

docker_container.hello: Creating...
docker_container.test: Creating...
docker_container.hello: Creation complete after 1s [id=77e515b4269aed255d4becac61f40d38e09838cdf8285294bf51f3c7cddbf2bf]

Error: Unable to create container with image sha256:a29f45ccde2ac0bde957b1277b1501f471960c8ca49f1588c6c885941640ae60: Unable to pull image sha256:a29f45ccde2ac0bde957b1277b1501f471960c8ca49f1588c6c885941640ae60: error pulling image sha256:a29f45ccde2ac0bde957b1277b1501f471960c8ca49f1588c6c885941640ae60: Error response from daemon: pull access denied for sha256, repository does not exist or may require 'docker login'

  on test.tf line 17, in resource "docker_container" "test":
  17: resource "docker_container" "test" {

Why do I get Unable to create container with image Unable to pull image error pulling image when using multiple Docker hosts?

2 Answers

docker_container.test references docker_image.world, but they use different providers (default and docker.worker):

resource "docker_container" "test" {
  provider = docker.worker
  image = docker_image.world.latest
  name  = "test"
}

resource "docker_image" "world" {
  name = "hello-world:latest"
}

This is fatal as docker_image.world uses provided default which runs the docker pull on tcp://192.168.1.10:2375/ (not on tcp://127.0.0.1:2375/).

This can be fixed by creating a docker_image using provider docker.world_worker to match docker_container.test as follows:

resource "docker_container" "test" {
  provider = docker.world_worker
  image = docker_image.world.latest
  name  = "test"
}

resource "docker_image" "world_worker" {
  provider = docker.world_worker
  name = "hello-world:latest"
}

There are some problems with the template which was originally used in the question. Firstly, short-running hello-world containers are used, which leads to at least one of the services exiting with an error message by Terraform. Then, with the important help of @Alain O'Dea (see relevant answer and comments) I created the following modified template, which works and accomplishes my goal.

# Configure the Docker provider
provider "docker" {
  host = "tcp://192.168.1.10:2375/"
}

provider "docker" {
  alias = "worker"
  host = "tcp://127.0.0.1:2375/"
}

# Create a container
resource "docker_container" "hello" {
  image = docker_image.world.latest
  name  = "hello"
}

resource "docker_container" "test" {
  provider = docker.worker
  image = docker_image.world_image.latest
  name  = "test"
}

resource "docker_image" "world" {
  name = "prom/prometheus:latest"
}

resource "docker_image" "world_image" {
  provider = docker.worker
  name = "nextcloud:latest"
}
Related