当使用AWS Fargate时,如何实现容器之间的通信

本文是2017年AWS Fargate系列日历活动的第19篇文章。

我是Cloudpack大阪的佐々木。
我要谈的是在Fargate上实现容器间通信的问题。

简而言之

Docker環境で、コンテナ間で通信させるためにLinkという機能があります。1

ECS上でLink機能を使用しているタスク定義を、Fargateで実行しようとしてもエラーになって動きません。

执行结果

假设有一个简单的示例,包括WordPress + MySQL。有一个WordPress容器和一个MySQL容器,通过在WordPress容器中指定链接,可以通过“mysql”名称进行通信。

version: '2'
services:
  wordpress:
    image: wordpress
    ports:
      - "80:80"
    links:
      - mysql
  mysql:
    image: mysql
    environment:
      MYSQL_ROOT_PASSWORD: password

ECSであれば、この構成で問題なく動くんですが、Fargateで起動させると下のようなエラーになります。

$ ecs-cli compose service up --launch-type FARGATE                                          
WARN[0000] Skipping unsupported YAML option...           option name=networks
WARN[0000] Skipping unsupported YAML option for service...  option name=networks service name=mysql
WARN[0000] Skipping unsupported YAML option for service...  option name=networks service name=wordpress
ERRO[0001] Error registering task definition             error="ClientException: Links are not supported when networkMode=awsvpc.\n\tstatus code: 400, request id:  axxxxx-e39c-11e7-a22a-xxxxxxxxx" family=wordpress
ERRO[0001] Create task definition failed                 error="ClientException: Links are not supported when networkMode=awsvpc.\n\tstatus code: 400, request id:  axxxxx-e39c-11e7-a22a-xxxxxxxxx"
FATA[0001] ClientException: Links are not supported when networkMode=awsvpc.
    status code: 400, request id: axxxxx-e39c-11e7-a22a-xxxxxxxxx

つまりFargateではLink機能はサポートされていないということです。

AWSのドキュメントには下記のように記載されてました。

只有在任务定义的网络模式设置为桥接时才支持。

由于Fargate的网络模式是awsvpc,因此不支持该功能。

问题的解决方案

我尝试找到替代Link功能的选项,但没能找到。于是我向@riywo问了一下,她很快就告诉了我。

在相同的任务定义中,容器共享本地主机,所以通过 localhost+端口号来访问是一个好办法。

我懂了。。。 (Wǒ le…)

哦?其他容器的正在运行的端口也能在本地主机上显示出来吗?

我查证了一下。

确认

我在同一任务定义中启动了一个额外的用于ssh连接的容器,并尝试从该容器中确认其外观。我参考了这方面的创建ssh连接容器的方法。

version: '2'
services:
  sshd:
    image: taishin/amazonlinux-sshd
    ports:
      - "22:22"
  wordpress:
    image: wordpress
    ports:
      - "80:80"
    # links:
    #   - mysql
  mysql:
    image: mysql
    environment:
      MYSQL_ROOT_PASSWORD: password

我将启动并通过SSH登录来确认一下。

-bash-4.2# netstat -nl
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address               Foreign Address             State
tcp        0      0 0.0.0.0:80                  0.0.0.0:*                   LISTEN
tcp        0      0 0.0.0.0:3128                0.0.0.0:*                   LISTEN
tcp        0      0 :::3306                     :::*                        LISTEN
tcp        0      0 :::3128                     :::*                        LISTEN
udp        0      0 0.0.0.0:68                  0.0.0.0:*
Active UNIX domain sockets (only servers)
Proto RefCnt Flags       Type       State         I-Node Path
unix  2      [ ACC ]     STREAM     LISTENING     17520  /var/run/mysqld/mysqld.sock

嗯,确实本地有其他容器使用的TCP/80和TCP/3306端口被监听着。

我会尝试使用浏览器进行访问。

image.png
image.png

数据库报了没有的错误,但是连接到MySQL没有问题。
顺便提一下,数据库主机名不是localhost,而是需要输入127.0.0.1才不会出错。
原因在这里:
https://qiita.com/TanukiTam/items/f6a08740d0fcda0db7be

完成形

最后创建的 docker-compose.yml 如下所示。

version: '2'
services:
  wordpress:
    image: wordpress
    ports:
      - "80:80"
    environment:
      WORDPRESS_DB_HOST: 127.0.0.1
      WORDPRESS_DB_PASSWORD: password
  mysql:
    image: mysql
    environment:
      MYSQL_ROOT_PASSWORD: password

请在此处参考WordPress容器的环境变量
https://hub.docker.com/_/wordpress/

ecs-cli compose service up --launch-type FARGATE                                          [15:20:08]
WARN[0000] Skipping unsupported YAML option...           option name=networks
WARN[0000] Skipping unsupported YAML option for service...  option name=networks service name=wordpress
WARN[0000] Skipping unsupported YAML option for service...  option name=networks service name=mysql
WARN[0000] Skipping unsupported YAML option for service...  option name=networks service name=sshd
INFO[0001] Using ECS task definition                     TaskDefinition="wordpress:11"
INFO[0002] Created an ECS service                        service=ecscompose-service-wordpress taskDefinition="wordpress:11"
INFO[0002] Updated ECS service successfully              desiredCount=1 serviceName=ecscompose-service-wordpress
INFO[0018] (service ecscompose-service-wordpress) has started 1 tasks: (task xxxxxxx-46f4-4b29-b09f-5484982bd294).  timestamp=2017-12-18 06:22:45 +0000 UTC
INFO[0124] Service status                                desiredCount=1 runningCount=1 serviceName=ecscompose-service-wordpress
INFO[0124] (service ecscompose-service-wordpress) has reached a steady state.  timestamp=2017-12-18 06:24:31 +0000 UTC
INFO[0124] ECS Service has reached a stable state        desiredCount=1 runningCount=1 serviceName=ecscompose-service-wordpress

当您使用浏览器访问时,

image.png

一切正常,运作顺畅。

总结

如果想要在Fargate上容器之间进行通信,虽然无法使用Link功能,但可以通过localhost:端口号进行访问!


Docker的链接功能似乎已经过时了。https://docs.docker.com/engine/userguide/networking/default_network/dockerlinks/

由于Fargate无法进行卷挂载,因此我认为很少会运行用于保持数据持久性的MySQL容器。

广告
将在 10 秒后关闭
bannerAds