千家信息网

如何进行Docker Compose中scale

发表于:2025-02-05 作者:千家信息网编辑
千家信息网最后更新 2025年02月05日,这篇文章给大家介绍如何进行Docker Compose中scale,内容非常详细,感兴趣的小伙伴们可以参考借鉴,希望对大家能有所帮助。环境准备,flask-redis项目,将项目启动:docker-c
千家信息网最后更新 2025年02月05日如何进行Docker Compose中scale

这篇文章给大家介绍如何进行Docker Compose中scale,内容非常详细,感兴趣的小伙伴们可以参考借鉴,希望对大家能有所帮助。

环境准备,flask-redis项目,将项目启动:

docker-compose up -dStarting flask-redis_web_1   ... doneStarting flask-redis_redis_1 ... done

查看状态:

docker-compose ps       Name                      Command               State           Ports-------------------------------------------------------------------------------------flask-redis_redis_1   docker-entrypoint.sh redis ...   Up      6379/tcpflask-redis_web_1     python app.py                    Up      0.0.0.0:8080->5000/tcp

docker-compose scale

我们目前的docker-compose 中的service容器中各自只有一个,通过scale可以去扩展service。

docker-compose up --help    --scale SERVICE=NUM        Scale SERVICE to NUM instances. Overrides the                               `scale` setting in the Compose file if present.

例如将web服务的数量变为三个:

docker-compose up --scale web=3 -dWARNING: The "web" service specifies a port on the host. If multiple containers for this service are created on a single host, the port will clash.Starting flask-redis_web_1 ...Starting flask-redis_web_1 ... doneCreating flask-redis_web_2 ... errorCreating flask-redis_web_3 ... errorERROR: for flask-redis_web_2  Cannot start service web: driver failed programming external connectivity on endpoint flask-redis_web_2 (952f3eea8bdf14f0a94845fb6ef5039285f7ffe40620faca32f40643b802fa97): Bind for 0.0.0.0:8080 failed: port is already allocatedERROR: for flask-redis_web_3  Cannot start service web: driver failed programming external connectivity on endpoint flask-redis_web_3 (50c776deb73b272d04181a8ab385f27cc31689aeeed804436fd2b92836cf25b9): Bind for 0.0.0.0:8080 failed: port is already allocatedERROR: for web  Cannot start service web: driver failed programming external connectivity on endpoint flask-redis_web_2 (952f3eea8bdf14f0a94845fb6ef5039285f7ffe40620faca32f40643b802fa97): Bind for 0.0.0.0:8080 failed: port is already allocatedERROR: Encountered errors while bringing up the project.

发现报错了,原因是接口已经被分配了。每个容器的端口都想绑定到8080上面,显然是不可能的。

将容器删除:

docker-compose downStopping flask-redis_web_1   ... doneStopping flask-redis_redis_1 ... doneRemoving flask-redis_web_3   ... doneRemoving flask-redis_web_2   ... doneRemoving flask-redis_web_1   ... doneRemoving flask-redis_redis_1 ... doneRemoving network flask-redis_default

将docker-compose.yml中端口绑定删除:

version: "3"services:  redis:    image: redis  web:    build:      context: .      dockerfile: Dockerfile    environment:      REDIS_HOST: redis

执行命令docker-compose up --scale web=3 -d

docker-compose up --scale web=3 -dCreating network "flask-redis_default" with the default driverCreating flask-redis_web_1   ... doneCreating flask-redis_web_2   ... doneCreating flask-redis_web_3   ... doneCreating flask-redis_redis_1 ... done

可以成功执行。

docker-compose ps       Name                      Command               State    Ports-----------------------------------------------------------------------flask-redis_redis_1   docker-entrypoint.sh redis ...   Up      6379/tcpflask-redis_web_1     python app.py                    Up      5000/tcpflask-redis_web_2     python app.py                    Up      5000/tcpflask-redis_web_3     python app.py                    Up      5000/tcp

发现web端口并没有映射到主机的端口,全部是5000container端口。

想象一下假如有多个web服务,都会监听本地的5000端口,都会访问redis,那么我们就可以有一个负载均衡器,可以把访问量平均的分配到web服务,可以减轻单个服务的压力。如下图所示:

如果我们用这种方式来部署web服务的话,以后的扩展性是非常强的。例如我们开启10个web服务:

iie4bu@hostdocker:~/ddy/docker-compose-flask-redis$ docker-compose up --scale web=10 -dWARNING: The Docker Engine you're using is running in swarm mode.Compose does not use swarm mode to deploy services to multiple nodes in a swarm. All containers will be scheduled on the current node.To deploy your application across the swarm, use `docker stack deploy`.Creating network "docker-compose-flask-redis_default" with the default driverCreating docker-compose-flask-redis_redis_1 ... doneCreating docker-compose-flask-redis_web_1   ... doneCreating docker-compose-flask-redis_web_2   ... doneCreating docker-compose-flask-redis_web_3   ... doneCreating docker-compose-flask-redis_web_4   ... doneCreating docker-compose-flask-redis_web_5   ... doneCreating docker-compose-flask-redis_web_6   ... doneCreating docker-compose-flask-redis_web_7   ... doneCreating docker-compose-flask-redis_web_8   ... doneCreating docker-compose-flask-redis_web_9   ... doneCreating docker-compose-flask-redis_web_10  ... done
iie4bu@hostdocker:~/ddy/docker-compose-flask-redis$ docker-compose ps               Name                             Command               State    Ports  --------------------------------------------------------------------------------------docker-compose-flask-redis_redis_1   docker-entrypoint.sh redis ...   Up      6379/tcpdocker-compose-flask-redis_web_1     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_10    python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_2     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_3     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_4     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_5     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_6     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_7     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_8     python app.py                    Up      5000/tcpdocker-compose-flask-redis_web_9     python app.py                    Up      5000/tcp

我们为了演示真实的架构,使用HAproxy做负载均衡

将app.py的端口由5000改为80,app.py如下:

from flask import Flaskfrom redis import Redisimport osimport socketapp = Flask(__name__)redis = Redis(host=os.environ.get('REDIS_HOST', '127.0.0.1'), port=6379)@app.route('/')def hello():    redis.incr('hits')    return 'Hello Container World! I have been seen %s times and my hostname is %s.\n' % (redis.get('hits'),socket.gethostname())if __name__ == "__main__":    app.run(host="0.0.0.0", port=80, debug=True)

Dockerfile的expose也改成80,内容如下:

FROM python:3.5LABEL maintaner="vincent"COPY . /appWORKDIR /appRUN pip install flask redisEXPOSE 80CMD [ "python", "app.py" ]

docker-compose.yml中添加haproxy,内容如下:

version: "3"services:  redis:    image: redis  web:    build:      context: .      dockerfile: Dockerfile    environment:      REDIS_HOST: redis  lb:    image: dockercloud/haproxy    links:      - web    ports:      - 8082:80    volumes:      - /var/run/docker.sock:/var/run/docker.sock

将上面的容器先docker-compose down,将容器删掉。

iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ docker-compose up -dWARNING: The Docker Engine you're using is running in swarm mode.Compose does not use swarm mode to deploy services to multiple nodes in a swarm. All containers will be scheduled on the current node.To deploy your application across the swarm, use `docker stack deploy`.Removing docker-compose-flask-redis-haproxy_lb_1docker-compose-flask-redis-haproxy_redis_1 is up-to-datedocker-compose-flask-redis-haproxy_web_1 is up-to-dateRecreating d2b87be02ede_docker-compose-flask-redis-haproxy_lb_1 ... done

查看状态:

iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ docker-compose ps                   Name                                 Command               State                    Ports                 -----------------------------------------------------------------------------------------------------------------------------docker-compose-flask-redis-haproxy_lb_1      /sbin/tini -- dockercloud- ...   Up      1936/tcp, 443/tcp, 0.0.0.0:8082->80/tcpdocker-compose-flask-redis-haproxy_redis_1   docker-entrypoint.sh redis ...   Up      6379/tcp                               docker-compose-flask-redis-haproxy_web_1     python app.py                    Up      80/tcp

测试访问:

iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ curl 127.0.0.1:8082Hello Container World! I have been seen b'1' times and my hostname is 9603ec0f2527.

测试通过。

接下来测试使用多个web服务:

先将之前的docker-compose down。

启动三个web服务:

iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ docker-compose up --scale web=3 -dWARNING: The Docker Engine you're using is running in swarm mode.Compose does not use swarm mode to deploy services to multiple nodes in a swarm. All containers will be scheduled on the current node.To deploy your application across the swarm, use `docker stack deploy`.Creating network "docker-compose-flask-redis-haproxy_default" with the default driverCreating docker-compose-flask-redis-haproxy_web_1   ... doneCreating docker-compose-flask-redis-haproxy_web_2   ... doneCreating docker-compose-flask-redis-haproxy_web_3   ... doneCreating docker-compose-flask-redis-haproxy_redis_1 ... doneCreating docker-compose-flask-redis-haproxy_lb_1    ... done
iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ docker-compose ps                   Name                                 Command               State                    Ports                 -----------------------------------------------------------------------------------------------------------------------------docker-compose-flask-redis-haproxy_lb_1      /sbin/tini -- dockercloud- ...   Up      1936/tcp, 443/tcp, 0.0.0.0:8082->80/tcpdocker-compose-flask-redis-haproxy_redis_1   docker-entrypoint.sh redis ...   Up      6379/tcp                               docker-compose-flask-redis-haproxy_web_1     python app.py                    Up      80/tcp                                 docker-compose-flask-redis-haproxy_web_2     python app.py                    Up      80/tcp                                 docker-compose-flask-redis-haproxy_web_3     python app.py                    Up      80/tcp

依次访问我们的HAproxy:

iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ curl 127.0.0.1:8082Hello Container World! I have been seen b'1' times and my hostname is 9a2d714aadad.iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ curl 127.0.0.1:8082Hello Container World! I have been seen b'2' times and my hostname is eda311882f3f.iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ curl 127.0.0.1:8082Hello Container World! I have been seen b'3' times and my hostname is 43f69f733c5e.iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ curl 127.0.0.1:8082Hello Container World! I have been seen b'4' times and my hostname is 9a2d714aadad.iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ curl 127.0.0.1:8082Hello Container World! I have been seen b'5' times and my hostname is eda311882f3f.iie4bu@hostdocker:~/ddy/docker-compose-flask-redis-haproxy$ curl 127.0.0.1:8082Hello Container World! I have been seen b'6' times and my hostname is 43f69f733c5e.

发现是轮询我们的web服务,haproxy会转发请求到三个web服务上。

我们目前的扩展是单机环境下的scale,无论将service扩展到多少,只能限制在单机环境下。但是一台服务器的资源是有限的,那么如何扩展多台服务器?那么就是需要使用swarm技术了。

关于如何进行Docker Compose中scale就分享到这里了,希望以上内容可以对大家有一定的帮助,可以学到更多知识。如果觉得文章不错,可以把它分享出去让更多的人看到。

0