问题:

我正在尝试在Digital Ocean上构建一个Docker Swarm集群,它由3个“管理器”节点和许多工作节点组成 . 工作节点的数量与此问题不是特别相关 . 我正在尝试模块化Docker Swarm配置的东西,因此它没有专门连接到digitalocean提供程序,而是可以接收一个ip地址列表来对配置集群起作用 .

为了供应主节点,需要将第一节点置于群集模式,其生成其他主节点将用于加入第一节点的连接密钥 . "null_resource"用于对主节点执行远程配置器,但是,我无法弄清楚dafuq如何确保第一个主节点完成其内容("docker swarm init ..."),然后让另一个"null_resource"配置器针对需要的其他主节点执行加入第一个 . 它们都是并行运行的,并且可以预见,它不起作用 .

此外,试图弄清楚如何收集第一个节点生成的连接令牌并使其可用于其他节点 . 我已经考虑过与Consul这样做,并将连接令牌存储为密钥,并将该密钥存储在其他节点上 - 但这并不理想......因为仍然存在确保Consul群集已配置并准备就绪的问题(所以同样的问题) .

main.tf

variable "master_count" { default = 3 }

# master nodes
resource "digitalocean_droplet" "master_nodes" {
  count               = "${var.master_count}"
  ... etc, etc
}

module "docker_master" {
  source          = "./docker/master"
  private_ip      = "${digitalocean_droplet.master_nodes.*.ipv4_address_private}"
  public_ip       = "${digitalocean_droplet.master_nodes.*.ipv4_address}"
  instances       = "${var.master_count}"
}

搬运工/主/ main.tf

variable "instances" {}
variable "private_ip" { type = "list" }
variable "public_ip" { type = "list" }


# Act only on the first item in the list of masters...
resource "null_resource" "swarm_master" {
  count = 1

  # Just to ensure this gets run every time
  triggers {
    version = "${timestamp()}"
  }

  connection {
    ...
    host = "${element(var.public_ip, 0)}"
  }

  provisioner "remote-exec" {
    inline = [<<EOF
      ... install docker, then ...

      docker swarm init --advertise-addr ${element(var.private_ip, 0)}

      MANAGER_JOIN_TOKEN=$(docker swarm join-token manager -q)
      # need to do something with the join token, like make it available
      # as an attribute for interpolation in the next "null_resource" block
    EOF
    ]
  }
}


# Act on the other 2 swarm master nodes (*not* the first one)
resource "null_resource" "other_swarm_masters" {
  count = "${var.instances - 1}"

  triggers {
    version = "${timestamp()}"
  }

  # Host key slices the 3-element IP list and excludes the first one
  connection {
    ...
    host = "${element(slice(var.public_ip, 1, length(var.public_ip)), count.index)}"
  }

  provisioner "remote-exec" {
    inline = [<<EOF
      SWARM_MASTER_JOIN_TOKEN=$(consul kv get docker/swarm/manager/join_token)
      docker swarm join --token ??? ${element(var.private_ip, 0)}:2377
    EOF
    ]
  }

  ##### THIS IS THE MEAT OF THE QUESTION ###
  # How do I make this "null_resource" block not run until the other one has
  # completed and generated the swarm token output? depends_on doesn't
  # seem to do it :(
}

从阅读github问题,我感觉这不是一个不寻常的问题...但它踢我的屁股 . 任何建议赞赏!