虽说我已经从docker-compose走上了docker swarm的邪门歪道,目前被迫走在k8s这条康庄大道, 但是我还是喜欢docker-compose简洁有效的部署方式。

曾其何时

docker-compose非常适合开发、测试、快速验证原型,这个小工具让单机部署容器变得简洁、高效。 正如我在《docker-compose,docker-stack前世今生》里面说的,所有人都认为docker-compose是单机部署多容器的瑞士军刀,没有docker stack由deploy配置节体现的生产特性(多实例、滚动部署、故障重启、负载均衡)。

最近我发现我错了:docker-compose还是具备服务多实例的能力的。

在docker-compose -h中发现了一个scale参数,这是个啥?

docker-compose还能水平扩展,实现多容器?

docker-compose定义的容器映射的主机端口不会冲突吗?

号主精心分析,才找到一个完备的理论来支持scale参数的合理性。
在此文中,我们将演示一个示例,说明如何使用Docker Compose运行服务的多实例

version: "3"
services:
webapp:
image: "luksa/kubia"
depends_on:
- db
ports:
- "8080:8080" # 主机Port: 容器暴露Port

在此文件中,我们定义了一个webapp服务(nodejs程序在8080端口监听

为webapp容器定义了端口映射:从容器8080端口映射到主机的8080端口,这样我们可以在主机上使用http://localhost:8080URL访问服务器。

Docker Compose --scale flag

当我们运行docker-compose up -h命令时, 其中--scale选项显示为服务指定多实例

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

很显然,使用目前的DockerCompose配置运行docker-compose up --scale webapp=3

将导致failed: port is already allocated错误

问题在于,我们试图运行webapp服务的三个实例,并将它们全部映射到主机同一端口,而「主机的8080端口只能绑定给一个容器」

解决错误的一种方法是将Docker Compose文件中的端口映射更改为- "8080", 这会将容器的端口8080暴露给主机上的临时未分配端口。

这个操作延伸出另一个问题:在启动容器之前,我们将不知道用于访问服务的端口。

要列出端口映射,请在运行docker-compose up --scale webapp=3之后运行docker-compose ps来查看容器:

   Name          Command     State            Ports
-------------------------------------------------------------
test_webapp_1 node app.js Up 0.0.0.0:32828->8080/tcp
test_webapp_2 node app.js Up 0.0.0.0:32830->8080/tcp
test_webapp_3 node app.js Up 0.0.0.0:32829->8080/tcp

添加负载均衡器

为了能够在不知道特定容器的端口的情况下访问webapp服务,并使用负载均衡机制将请求分发到容器,我们需要在容器堆栈中添加负载均衡器。

在此示例中,我们将使用nginx作为负载均衡器:来完成对外接收、对内转发


在与docker-compose.yml文件相同的目录中创建以下nginx.conf文件,代理&转发请求

user  nginx;
events {
worker_connections 1000;
}
http {
server {
listen 80;
location / {
proxy_pass http://webapp:8080;
}
}
}

这将配置nginx将请求从主机端口80转发到http://webapp:8080。然后将由Docker’s embedded DNS解决寻址:该DNS服务器使用轮询实现来根据服务名称解析DNS请求,并将其分发给Docker容器。

由于nginx服务负责对外接收请求、对内转发,因此webapp服务可不直接对外暴露。实际上我们可以从Docker Compose文件中删除webapp端口映射配置,而仅将端口8080通知给链接的nginx服务。

version: "3"
services:
webapp:
image: "luksa/kubia"
nginx:
image: nginx:latest
volumes:
- type: bind
source: /home/root/test/nginx.conf
target: /etc/nginx/nginx.conf
depends_on:
- webapp
ports:
- "80:80"

通过此配置,我们现在可以利用Docker Compose工具的scale水平扩展、实现服务多实例。 docker-compose up -d --scale webapp=3

CONTAINER ID     IMAGE             COMMAND                  CREATED             STATUS          PORTS                NAMES
05b024964274 luksa/kubia "node app.js" 15 minutes ago Up 15 minutes test_webapp_1
2fb56a22810a luksa/kubia "node app.js" 15 minutes ago Up 15 minutes test_webapp_3
84041c727b6e luksa/kubia "node app.js" 15 minutes ago Up 15 minutes test_webapp_2
3882beae8b56 nginx:latest "nginx -g 'daemon of…" 15 minutes ago Up 15 minutes 0.0.0.0:80->80/tcp test_nginx_1

总结输出

  • docker-compose利用Docker引擎内嵌DNS,提炼出水平扩展容器、服务多实例的能力(用一个代理就能应用这个能力)

  • Docker引擎内嵌DNS也是docker-compose利用服务名发现其他容器的关键

在需要测试具备水平扩展能力的web服务时,docker-compose up -d --scale 提供了一种快速、简便的途径。

以后谁再说docker-compose没有水平扩展容器、服务多实例的时候,就把这篇文章丢给他。

  • https://pspdfkit.com/blog/2018/how-to-use-docker-compose-to-run-multiple-instances-of-a-service-in-development/#

  • https://docs.docker.com/engine/userguide/networking/configure-dns/

谁说docker-compose不能水平扩展容器、服务多实例?的更多相关文章

  1. Docker Compose部署项目到容器-基于Tomcat和mysql的项目yml配置文件代码

    场景 Docker-Compose简介与Ubuntu Server 上安装Compose: https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/deta ...

  2. 【转载】docker 应用之动态扩展容器空间大小

    docker 容器默认的空间是 10G, 如果想指定默认容器的大小(在启动容器的时候指定),可以在 docker 配置文件里通过 dm.basesize 参数指定,比如 docker -d --sto ...

  3. Docker Compose部署项目到容器-基于Tomcat和mysql的商城项目(附源码和sql下载)

    场景 Docker-Compose简介与Ubuntu Server 上安装Compose: https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/deta ...

  4. 基于Docker Compose的.NET Core微服务持续发布

    是不是现在每个团队都需要上K8s才够潮流,不用K8s是不是就落伍了.今天,我就通过这篇文章来回答一下. 一.先给出我的看法和建议 我想说的是,对于很多的微小团队来说,可能都不是一定要上K8s,毕竟上K ...

  5. 使用Docker Compose编排Spring Cloud微服务

    文章目录 微服务构建实例 简化Compose的编写 编排高可用的Eureka Server 编排高可用Spring Cloud微服务集群及动态伸缩 微服务项目名称 项目微服务中的角色 microser ...

  6. Docker学习之搭建MySql容器服务

    描述 MySQL 5.6 SQL数据库服务器Docker镜像,此容器映像包含用于OpenShift的MySQL 5.6 SQL数据库服务器和一般用法.用户可以选择RHEL和基于CentOS的图像.然后 ...

  7. Docker学习笔记之使用 Docker Compose 管理容器

    0x00 概述 通过之前的介绍,我们已经基本掌握了构建.运行容器的方法,但这还远远不够,由于 Docker 采用轻量级容器的设计,每个容器一般只运行一个软件,而目前绝大多数应用系统都绝不是一个软件所能 ...

  8. Docker Compose 容器编排 NET Core 6+MySQL 8+Nginx + Redis

    环境: CentOS 8.5.2111Docker 20.10.10Docker-Compose 2.1.0 服务: db  redis  web nginx NET Core 6+MySQL 8+N ...

  9. Docker | Compose创建mysql容器

    本文通过Docker Compose来创建mysql容器 在linux服务器上创建文件,用于管理容器 mkdir docker-mysql cd docker-mysql vim docker-com ...

  10. Docker 三剑客之 Docker Compose

    Docker Compose 项目是 Docker 官方的开源项目,负责实现对 Docker 容器集群的快速编排,开源地址:https://github.com/docker/compose Dock ...

随机推荐

  1. [转帖]Nginx 性能优化

    目录 1.调整 worker 进程数 2.调整 worker 连接数 3.调整 work 进程最大打开文件数 4.开启高效文件传输模式 5.限制文件上传大小 6.开启 gzip 压缩 7.本地缓存静态 ...

  2. [转帖]SMEMBERS:获取集合包含的所有元素

    https://www.bookstack.cn/read/redisguide/spilt.4.291fab46a3b4f05c.md SMEMBERS set 以下代码展示了如何使用 SMEMBE ...

  3. [转帖]TIDB-Error 1105: Out Of Memory Quota问题解决

    一.背景 复杂sql查询报错 二.原因 单条s q l使用内存默认为1G 三.解决 tiup cluster edit_config tidb-test server_configs: tidb: m ...

  4. [转帖]TiDB系统调参实战经验

    https://tidb.net/blog/c9466c40#TiDB%E7%B3%BB%E7%BB%9F%E8%B0%83%E5%8F%82%E5%AE%9E%E6%88%98%E7%BB%8F%E ...

  5. [转帖]MySQL InnoDB存储引擎大观

      https://baijiahao.baidu.com/s?id=1709263187856706948&wfr=spider&for=pc MySQL InnoDB 引擎现在广为 ...

  6. [转帖]总结:nginx502:Tomcat调优之acceptCount

    问题背景:UI页面点击会偶尔返回error,检查调用日志,发现nginx报502报错,因此本文即排查502报错原因. 如下红框可知,访问本机个备机的服务502了,用时3秒左右(可见并不是超时) 先给出 ...

  7. mysql 的outfile以及infile 语法简单备份恢复表

    今天学习 姜老师的 mysql技术内存innodb存储引擎时看到了有一个outfile和infile的语法,感觉挺好的, 这里面进行一下简单的学习与验证. oufile 可以到处文件 infile 可 ...

  8. git提交出现running pre-commit hook: lint-staged

    现象 今天提交代码的时候出现了 > running pre-commit hook: lint-staged Stashing changes... [started] Stashing cha ...

  9. docker 发布web项目到linux

    一.准备工作 1.连接到Liunx的工具 MobaXterm 填好Ip 直接点ok就行 输入用户名和密码进入系统 2.已发布的.netcore网站或微服务 在要发布的项目上右键---->添加-- ...

  10. es从线上库导出数据并导入开发环境

    背景 来了个需求,需要从某个线上es库查询一些数据出来并进行大屏展示.问需求方有没有开发环境的es库,答:没有,说要不直连他们的线上库. 后面想想也行吧,业务方都这么说了,结果开网络的流程被打回了,理 ...