亚马逊AWS官方博客

Lightsail 容器:一种在云中运行容器的简单方法

我向开发人员介绍 AWS 云时,通常会花一点时间来介绍并演示 Amazon Lightsail。它是迄今为止开始使用 AWS 的最简单方法。使用它,您在几分钟内即可在自己的虚拟服务器上运行您的应用程序。今天,我们增加了在 Amazon Lightsail 上部署基于容器的工作负载的可能性。您现在可以将您的容器映像部署到云中,其简单性和捆绑定价与 Amazon Lightsail 为您的虚拟服务器提供的相同。

Amazon Lightsail 是一项易于使用的云服务,可为您提供部署应用程序或网站所需的一切,从而实现经济高效且易于理解的月度计划。它是部署简单的工作负载、网站或开始使用 AWS 的理想选择。典型的 Lightsail 客户包括开发人员、小型企业或初创公司等,他们希望快速开始使用云和 AWS。当您更熟悉 AWS 云时,您可以稍后随时采用广泛的 AWS 服务。

Lightsail 在后台由 Amazon Elastic Compute Cloud (EC2)Amazon Relational Database Service (RDS)Application Load Balancer 和其他 AWS 服务提供支持。它提供了您期望从 AWS 获得的安全性、可靠性和可扩展性级别。

部署到 Lightsail 时,您可以在六种操作系统(4 个 Linux 发行版、FreeBSD 或 Windows)、七种应用程序(例如 WordPressDrupalJoomlaPlesk…)和七种堆栈(例如 Node.jsLampGitLabDjango…)之间选择。但是 Docker 容器呢?

即日起,Amazon Lightsail 为开发人员提供一种简单的方式来将其容器部署到云中。您只需要为您的容器提供一个 Docker 映像,我们将为您自动容器化该映像。Amazon Lightsail 为您提供了一个 HTTPS 终端节点,可以为在云容器中运行的应用程序提供服务。它会自动设置负载均衡的 TLS 终端节点,并处理 TLS 证书。它会为您自动替换无响应的容器,会为终端节点分配一个 DNS 名称,维护旧版本,直到新版本运行正常并准备好上线,等等。

让我们通过将简单的 Python Web 应用程序部署为容器来看看它是如何工作的。假设您的笔记本电脑上安装了 AWS 命令行界面 (CLI)Docker。不需要 Python,它将仅安装在容器中。

我首先使用 Flask 简单应用程序框架创建一个 Python REST API。任何可以在容器内运行的编程语言和框架都可以工作。我选择了 Python 和 Flask,因为它们简单又简洁。

您可以安全地复制/粘贴以下命令:

mkdir helloworld-python
cd helloworld-python
# create a simple Flask application in helloworld.py
echo "

from flask import Flask, request
from flask_restful import Resource, Api

app = Flask(__name__)
api = Api(app)

class Greeting (Resource):
   def get(self):
      return { "message" : "Hello Flask API World!" }
api.add_resource(Greeting, '/') # Route_1

if __name__ == '__main__':
   app.run('0.0.0.0','8080')

"  > helloworld.py

然后我创建一个 Dockerfile,其中包含构建容器映像所需的步骤和信息:

# create a Dockerfile
echo '
FROM python:3
ADD helloworld.py /
RUN pip install flask
RUN pip install flask_restful
EXPOSE 8080
CMD [ "python", "./helloworld.py"]
 '  > Dockerfile

现在我可以构建我的容器了:

docker build -t lightsail-hello-world。

build 命令在构建容器时会输出许多行,它最终以以下消息结束(实际 ID 将不同):

Successfully built 7848e055edff
Successfully tagged lightsail-hello-world:latest

我通过在笔记本电脑上启动容器来测试它:

docker run -it --rm -p 8080:8080 lightsail-hello-world

并将浏览器连接到 localhost:8080

在容器中测试 Flask API

当我对应用程序感到满意时,我会将容器推送到 Docker Hub。

docker tag lightsail-hello-world sebsto/lightsail-hello-world
docker login
docker push sebsto/lightsail-hello-world

现在,我已经在 Docker Hub 上准备好容器,下面我们来创建 Lightsail 容器服务。

我将浏览器指向 Amazon Lightsail 控制台。我可以看到容器服务已经部署好,我可以管理它们。为创建新服务,我点击 Create container service(创建容器服务):Lighsail Container Console(Lighsail 容器控制台)

在下一个屏幕上,我根据可供应用程序使用的 vCPU 和内存来选择要使用的容器大小。出于高可用性或可扩展性的原因,我还选择了希望并行运行的容器实例的数量。我可以随时更改容器实例的数量或其能力(vCPU 和 RAM),而不会中断服务。这两个参数都会影响 AWS 每月收取的价格。价格在屏幕上显示并动态调整,如以下视频所示。

Lightsail 选择容量

在屏幕稍微下面的位置,我选择现在跳过部署。我将服务命名为(“hello-world”)。我单击 Create container service(创建容器服务)。

Lightsail 容器名称

创建服务后,我单击 Create your first deployment(创建第一个部署)以创建部署。部署指的是要在我刚创建的服务上部署的特定容器映像和版本的组合。

我为我的映像选择了一个名称,然后在 Docker Hub 上使用格式 user/<my container name>:tag 提供映像的地址。在这个地方,我也可以输入环境变量、端口映射或启动命令。

我的容器在端口 TCP 8080 上提供网络服务,因此我将该端口添加到部署配置中。开放端口配置指定哪些端口和协议对容器网络中的其他系统开放。其他容器或虚拟机只能在端口在控制台中显式配置或公开在我的 Dockerfile 中时连接到我的容器。这些端口都不会在公共互联网中公开。

但是在这个示例中,我还希望 Lightsail 将流量从公共互联网路由到此容器中。因此,我将此容器作为我刚创建的 hello-world 服务的终端节点添加。终端节点会为 TLS 自动配置,没有要安装或管理的证书。

我最多可以为单个部署添加 10 个容器。准备好后,我单击 Save and deploy(保存并部署)。

Lightsail 部署

过了一段时间,我的部署处于活动状态,我可以测试终端节点。

Lightsail 部署处于活动状态

终端节点 DNS 地址位于控制台的右上角。如果必须的话,我可以配置自己的 DNS 域名。

Lightsail 终端节点 DNS我在浏览器中打开另一个选项卡并将它指向 https 终端节点 URL:

测试容器部署当我必须部署新版本时,我再次使用控制台来修改部署。我为您省去了修改应用程序代码、构建和推送新版本容器的详细信息。假设我在名称 sebsto/lightsail-hello-world:v2 下有第二个容器映像版本可用。我返回到 Amazon Lightsail 控制台,单击 Deployments(部署),然后单击 Modify your Deployments(修改部署)。我输入容器映像新版本的完整名称,包括标签,然后单击 Save and Deploy(保存并部署)。

Lightsail 部署更新的版本过了一段时间后,部署并自动激活新版本。

Lightsail 部署成功

我在浏览器中打开一个新选项卡,然后将其指向 Amazon Lightsail 控制台右上角提供的终端节点 URI。我观察到 JSON 版本不同。它现在有一个值为 2版本属性。

lightsail 版本 2 已部署

当我的部署过程中出现问题时, Amazon Lightsail 会自动使上次部署保持活动状态,以避免任何服务中断。我还可以手动激活以前的部署版本以撤消任何不需要的更改。

我刚从 Docker Hub 部署了我的第一个容器映像。我还可以使用 AWS 命令行界面 (CLI) 管理我的服务并从笔记本电脑部署本地容器映像。要直接从笔记本电脑将容器映像推送到我的 Amazon Lightsail 容器服务,我必须安装 LightSail 控制器插件。(TL;DR curlcpchmod 都适合您在此使用,我还维护了一个 DockerFile 来使用容器内的 CLI)。

为创建、列出或删除容器服务,我键入:

aws lightsail create-container-service --service-name myservice --power nano --scale 1

aws lightsail get-container-services
{
   "containerServices": [{
      "containerServiceName": "myservice",
      "arn": "arn:aws:lightsail:us-west-2:012345678901:ContainerService/1b50c121-eac7-4ee2-9078-425b0665b3d7",
      "createdAt": "2020-07-31T09:36:48.226999998Z",
      "location": {
         "availabilityZone": "all",
         "regionName": "us-west-2"
      },
      "resourceType": "ContainerService",
      "power": "nano",
      "powerId": "",
      "state": "READY",
      "scale": 1,
      "privateDomainName": "",
      "isDisabled": false,
      "roleArn": ""
   }]
}

aws lightsail delete-container-service --service myservice

我还可以使用 CLI 直接从笔记本电脑部署容器映像。确保已安装 lightsailctl

# Build the new version of my image (v3)
docker build -t sebsto/lightsail-hello-world:v3 .

# Push the new image.
aws lightsail push-container-image --service-name hello-world --label hello-world --image sebsto/lightsail-hello-world:v3

过了一会,我看到以下输出:

Image "sebsto/lightsail-hello-world:v3" registered.
Refer to this image as ":hello-world.hello-world.1" in deployments.

我创建一个 lc.json 文件来保存部署配置的详细信息。它与我在控制台上看到的选项一致。我报告了上一个命令映像 属性中给出的名称:

{
  "serviceName": "hello-world",
  "containers": {
     "hello-world": {
        "image": ":hello-world.hello-world.1",
        "ports": {
           "8080": "HTTP"
        }
     }
  },
  "publicEndpoint": {
     "containerName": "hello-world",
     "containerPort": 8080
  }
}

最后,我用以下命令创建一个新的服务版本:
aws lightsail create-container-service-deployment --cli-input-json file://lc.json

我可以使用以下命令查询部署状态
aws lightsail get-container-services

...
"nextDeployment": {
   "version": 4,
   "state": "ACTIVATING",
   "containers": {
      "hello-world": {
      "image": ":hello-world.hello-world.1",
      "command": [],
      "environment": {},
      "ports": {
         "8080": "HTTP"
      }
     }
},
...

过了一段时间后,状态变为 ACTIVE(活动),我可以测试我的终端节点。

curl https://hello-world.nxxxxxxxxxxx.lightsail.ec2.aws.dev/
{"message": "Hello Flask API World!", "version": 3}

如果您计划稍后将容器部署到 Amazon ECSAmazon Elastic Kubernetes Service,则无需进行任何更改。您可以从存储库中提取容器映像,就像使用 Amazon Lightsail 一样。

您可以在提供 Amazon Lightsail 的所有 AWS 区域中将容器部署到 Lightsail 上。截止今天,已在美国东部(俄亥俄)美国东部(弗吉尼亚北部)美国西部(俄勒冈)亚太地区(孟买)亚太地区(首尔)亚太地区(新加坡)亚太地区(悉尼)亚太地区(东京)加拿大(中部)欧洲(法兰克福)欧洲(爱尔兰)欧洲(伦敦)欧洲(巴黎)区域提供。

与往常一样,使用 Amazon Lightsail 时,定价易于理解且可预测。Amazon Lightsail 容器每月每个容器的价格固定,具体取决于容器的大小(您使用的 vCPU/ 内存组合)。您需要按保持服务运行的时间按比例付费。每月价格是全天候运行服务时将向您收取的最高价格。所有 AWS 区域的价格都相同。价格从 Nano 容器每月 7 USD(512MB 内存和 0.25 vCPU)到 X-Large 容器(8GB 内存和 4 个 vCPU 核心)每月 160 USD 不等。这个价格不仅包括容器本身,还包括负载均衡器、DNS 和充足的数据传输层。其他 AWS 区域的详细信息和价格在 Lightsail 定价页面上。

我迫不及待地想要发现您将在 Amazon Lightsail 容器上构建和部署哪些解决方案!

— seb