如何使用docker compose将docker容器相互链接
我必须用docker compose设置mongo副本集。对于副本集,容器必须相互了解 我在docker compose.yml中尝试了如何使用docker compose将docker容器相互链接,docker,docker-compose,Docker,Docker Compose,我必须用docker compose设置mongo副本集。对于副本集,容器必须相互了解 我在docker compose.yml中尝试了 dbreplicasetpart1: image: mongo:2.6.8 expose: - '27018' links: - replicasetpart2 - replicasetpart3 cap_add: - NET_ADMIN
dbreplicasetpart1:
image: mongo:2.6.8
expose:
- '27018'
links:
- replicasetpart2
- replicasetpart3
cap_add:
- NET_ADMIN
dbreplicasetpart2:
image: mongo:2.6.8
links:
- replicasetpart1
- replicasetpart3
expose:
- '27019'
cap_add:
- NET_ADMIN
...
我收到一条循环导入消息。但是,如果删除指向DBReplicateSetPart1的反向链接,则无法从DBReplicateSetPart2 ping到DBReplicateSetPart1。
解决方案是什么?您应该使用大使模式:
基本上,您可以创建一个中间组件,将这两个组件连接在一起。您可以看到我们在Spring Cloud的Eureka发现服务中使用的一个示例:
ambassador:
image: cpuguy83/docker-grand-ambassador
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
command: "-name eureka_1 -name eureka2_1 "
eureka:
links:
- "ambassador:eureka2"
eureka2:
links:
- "ambassador:eureka"
为了简单起见,我只复制了我们想出的使用大使解决方案的链接。这确实是一个更舒适的解决方案。
适用于我们的配置:
amba1:
image: cpuguy83/docker-grand-ambassador
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
command: "-name cucumber_dbreplicasetpart1_1"
amba2:
image: cpuguy83/docker-grand-ambassador
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
command: "-name cucumber_dbreplicasetpart2_1"
amba3:
image: cpuguy83/docker-grand-ambassador
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
command: "-name cucumber_dbreplicasetpart3_1"
dbreplicasetpart1:
image: 'mongo:2.6.8'
hostname: dbreplicasetpart1
command: >
bash -c
'
mongod --fork --logpath mongo.log --smallfiles --replSet rs1
echo "
printjson(
rs.initiate(
{
_id : \"rs1\",
members : [
{_id : 0, host : \"dbreplicasetpart1:27017\"},
{_id : 1, host : \"dbreplicasetpart2:27017\"},
{_id : 2, host : \"dbreplicasetpart3:27017\"},
]
}
)
);
" | mongo;
tail -f mongo.log
'
links:
- "amba2:dbreplicasetpart2"
- "amba3:dbreplicasetpart3"
dbreplicasetpart2:
image: 'mongo:2.6.8'
hostname: dbreplicasetpart2
command: >
bash -c
'
mongod --fork --logpath mongo.log --smallfiles --replSet rs1
echo "
printjson(
rs.initiate(
{
_id : \"rs1\",
members : [
{_id : 0, host : \"dbreplicasetpart1:27017\"},
{_id : 1, host : \"dbreplicasetpart2:27017\"},
{_id : 2, host : \"dbreplicasetpart3:27017\"},
]
}
)
);
" | mongo;
tail -f mongo.log
'
links:
- "amba1:dbreplicasetpart1"
- "amba3:dbreplicasetpart3"
dbreplicasetpart3:
image: 'mongo:2.6.8'
hostname: dbreplicasetpart3
command: >
bash -c
'
mongod --fork --logpath mongo.log --smallfiles --replSet rs1
echo "
printjson(
rs.initiate(
{
_id : \"rs1\",
members : [
{_id : 0, host : \"dbreplicasetpart1:27017\"},
{_id : 1, host : \"dbreplicasetpart2:27017\"},
{_id : 2, host : \"dbreplicasetpart3:27017\"},
]
}
)
);
" | mongo;
tail -f mongo.log
'
links:
- "amba1:dbreplicasetpart1"
- "amba2:dbreplicasetpart2"
为Docker 1.10更新
Docker 1.10允许在compose文件中定义网络。
这是更新后的代码
version: "2"
services:
replica1:
image: mongo:2.6.8
container_name: replica1
networks:
- my-net
ports:
- "27018"
environment:
REPLICA2_URL: "http://replica2:27019"
replica2:
image: mongo:2.6.8
container_name: replica2
networks:
- my-net
ports:
- "27019"
environment:
REPLICA1_URL: "http://replica1:27018"
networks:
my-net:
driver: bridge
Docker 1.9之前的答案
从Docker 1.9开始,解决方案是创建一个自定义网络并将其传递给Docker compose up
命令
创建网络
docker网络创建--驱动程序桥接我的网络
在docker-compose.yml文件中将该网络作为环境变量引用(${network}
)。例如:
```
```
请注意,replica1
inhttp://replica1:27018
将解析为replica1服务(容器)的ip地址。无需硬编码ip地址;replica1的条目将自动添加到replica2容器的/etc/host中。replica1容器也是如此。Docker将在其/etc/host文件中为replica2添加一个条目
调用docker compose,将创建的网络传递给它
NETWORK=my net docker compose up-d-f docker-compose.yml
我在上面创建了一个只在一个节点(主机)内工作的。对开发人员来说很好。如果需要让两个节点相互通信,则需要创建一个。但原则是一样的。您将网络名称传递给docker compose up命令。以下是docker 1.7.1中仍应使用的内容(如果您坚持使用CentOS 6):
dns\u添加
脚本:
#!/usr/bin/env sh
# This script configures resov.conf to use
# "skydns" name server with "docker" domain
# and adds a service name specified in the first argument
SERVICE_NAME=$1
waitforit () {
HOST=$1
PORT=$2
TIME_OUT=${3:-30};
END=$(($(date "+%s+$TIME_OUT")))
while [ $(date "+%s") -lt $END ]
do nc -z -w1 $HOST $PORT && break
done
return $END
}
# Use skydns to resolve names
echo "nameserver `resolveip -s skydns`" > /etc/resolv.conf
echo "search docker" >> /etc/resolv.conf
# Put yourself to DNS
ETCD_HOST=etcd
ETCD_PORT=4001
waitforit $ETCD_HOST $ETCD_PORT
HOST_IP=`resolveip -s $HOSTNAME`
apk update && apk add curl
curl -XPUT http://$ETCD_HOST:$ETCD_PORT/v2/keys/my/docker/$SERVICE_NAME -d value="{\"host\":\"$HOST_IP\"}"
这里有一个解释:
我们在一个容器中设置了自己的DNS服务器
我们将容器配置为使用该服务器
我们使用特殊的HTTP请求配置DNS服务器
不更新docker compose.yml
文件
docker network connect docker-compose-network-you-want-to-connect conatianer-name-from-another-docker-compose
更多像您这样的配置,我遇到了以下错误:ambassador|1 | time=“2015-03-30T11:34:06Z”level=info msg=“为%s%s创建代理时出错:%s-%vdockerfoo_dbreplicasetpart1_1172.17.0.0.17927017:绑定:地址已在使用”ambassador|time=“2015-03-30T11:34:06Z”level=info msg=“为容器dockerfoo\u dbreplicasetpart1\u创建代理时出错”“
你能把你的配置文件发给大使吗?下面的黑客攻击不是最好的方法,因为IP地址可能会在不同的环境中发生变化。Miguel,我们找到了使用大使解决方案的方法,请参见下面答案中的我的配置。在docker compose环境中,您必须调整docker grand ambassador的-name参数,如@MichaelK。下面的解决方案显示:_1,see和-p标志不使用此方法>=Docker 1.10查看桥接网络答案这里的所有答案都早于Docker 1.9中引入的新Docker网络。您现在要做的是首先创建一个网络并将其传递给docker compose up。我将在下面添加一个示例作为答案。由于Docker 1.9中的更改,这是一个更好的解决方案。因此,这应该是一个被接受的答案,试图让同样的东西为mysql工作,已经尝试了上面的方法,也许我遗漏了一些东西,无法让它工作。如果您能看一下,我将不胜感激:
#!/usr/bin/env sh
# This script configures resov.conf to use
# "skydns" name server with "docker" domain
# and adds a service name specified in the first argument
SERVICE_NAME=$1
waitforit () {
HOST=$1
PORT=$2
TIME_OUT=${3:-30};
END=$(($(date "+%s+$TIME_OUT")))
while [ $(date "+%s") -lt $END ]
do nc -z -w1 $HOST $PORT && break
done
return $END
}
# Use skydns to resolve names
echo "nameserver `resolveip -s skydns`" > /etc/resolv.conf
echo "search docker" >> /etc/resolv.conf
# Put yourself to DNS
ETCD_HOST=etcd
ETCD_PORT=4001
waitforit $ETCD_HOST $ETCD_PORT
HOST_IP=`resolveip -s $HOSTNAME`
apk update && apk add curl
curl -XPUT http://$ETCD_HOST:$ETCD_PORT/v2/keys/my/docker/$SERVICE_NAME -d value="{\"host\":\"$HOST_IP\"}"
docker network connect docker-compose-network-you-want-to-connect conatianer-name-from-another-docker-compose