跳至主要内容

将 Deno 部署到 Amazon Lightsail

Amazon Lightsail 是开始使用 Amazon Web Services 最简单、最便宜的方式。它允许您托管虚拟机,甚至托管整个容器服务。

本指南将向您展示如何使用 Docker、Docker Hub 和 GitHub Actions 将 Deno 应用程序部署到 Amazon Lightsail。

在继续之前,请确保您拥有以下内容:

创建 Dockerfile 和 docker-compose.yml

为了专注于部署,我们的应用程序将只是一个返回字符串作为 HTTP 响应的 main.ts 文件。

import { Application } from "https://deno.land/x/oak/mod.ts";

const app = new Application();

app.use((ctx) => {
ctx.response.body = "Hello from Deno and AWS Lightsail!";
});

await app.listen({ port: 8000 });

然后,我们将创建两个文件 - Dockerfiledocker-compose.yml - 来构建 Docker 镜像。

在我们的 Dockerfile 中,让我们添加

FROM denoland/deno

EXPOSE 8000

WORKDIR /app

ADD . /app

RUN deno cache main.ts

CMD ["run", "--allow-net", "main.ts"]

然后,在我们的 docker-compose.yml

version: '3'

services:
web:
build: .
container_name: deno-container
image: deno-image
ports:
- "8000:8000"

让我们通过运行 docker compose -f docker-compose.yml build,然后 docker compose up,并访问 localhost:8000 来在本地测试它。

hello world from localhost

它有效!

构建、标记和推送到 Docker Hub

首先,让我们登录 Docker Hub 并创建一个仓库。让我们将其命名为 deno-on-aws-lightsail

然后,让我们标记并推送我们的新镜像,将 username 替换为您的用户名

然后,让我们在本地构建镜像。请注意,我们的 docker-compose.yml 文件将构建命名为 deno-image

docker compose -f docker-compose.yml build

让我们 标记 本地镜像为 {{ username }}/deno-on-aws-lightsail

docker tag deno-image {{ username }}/deno-on-aws-lightsail

我们现在可以将镜像推送到 Docker Hub

docker push {{ username }}/deno-on-aws-lightsail

成功后,您应该能够在您的 Docker Hub 仓库中看到新的镜像。

new image on docker hub

创建并部署到 Lightsail 容器

让我们前往 Amazon Lightsail 控制台

然后点击“容器”和“创建容器服务”。在页面下方,点击“设置您的第一个部署”并选择“指定自定义部署”。

您可以随意输入容器名称。

Image中,请确保使用您在 Docker Hub 中设置的{{ username }}/{{ image }}。在本例中,它是lambtron/deno-on-aws-lightsail

让我们点击Add open ports并添加8000

最后,在PUBLIC ENDPOINT下,选择您刚刚创建的容器名称。

完整形式应如下所示

create container service interface

准备就绪后,点击“创建容器服务”。

片刻之后,您的新容器将部署完毕。点击公共地址,您应该会看到您的 Deno 应用程序。

Hello world from Deno and AWS Lightsail

使用 GitHub Actions 自动化

为了自动化该过程,我们将使用aws CLI 和lightsail 子命令

我们 GitHub Actions 工作流程中的步骤将是

  1. 检出仓库
  2. 在本地将我们的应用程序构建为 Docker 镜像
  3. 安装并验证 AWS CLI
  4. 通过 CLI 将本地 Docker 镜像推送到 AWS Lightsail 容器服务

此 GitHub Action 工作流程正常运行的先决条件

让我们创建一个名为container.template.json 的新文件,其中包含有关如何进行服务容器部署的配置。请注意,这些选项值与我们在上一节中手动输入的值非常相似。

{
"containers": {
"app": {
"image": "",
"environment": {
"APP_ENV": "release"
},
"ports": {
"8000": "HTTP"
}
}
},
"publicEndpoint": {
"containerName": "app",
"containerPort": 8000,
"healthCheck": {
"healthyThreshold": 2,
"unhealthyThreshold": 2,
"timeoutSeconds": 5,
"intervalSeconds": 10,
"path": "/",
"successCodes": "200-499"
}
}
}

让我们将以下内容添加到您的.github/workflows/deploy.yml 文件中

name: Build and Deploy to AWS Lightsail

on:
push:
branches:
- main

env:
AWS_REGION: us-west-2
AWS_LIGHTSAIL_SERVICE_NAME: container-service-2
jobs:
build_and_deploy:
name: Build and Deploy
runs-on: ubuntu-latest
steps:
- name: Checkout main
uses: actions/checkout@v2

- name: Install Utilities
run: |
sudo apt-get update
sudo apt-get install -y jq unzip
- name: Install AWS Client
run: |
curl "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" -o "awscliv2.zip"
unzip awscliv2.zip
sudo ./aws/install || true
aws --version
curl "https://s3.us-west-2.amazonaws.com/lightsailctl/latest/linux-amd64/lightsailctl" -o "lightsailctl"
sudo mv "lightsailctl" "/usr/local/bin/lightsailctl"
sudo chmod +x /usr/local/bin/lightsailctl
- name: Configure AWS credentials
uses: aws-actions/configure-aws-credentials@v1
with:
aws-region: ${{ env.AWS_REGION }}
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
- name: Build Docker Image
run: docker build -t ${{ env.AWS_LIGHTSAIL_SERVICE_NAME }}:release .
- name: Push and Deploy
run: |
service_name=${{ env.AWS_LIGHTSAIL_SERVICE_NAME }}
aws lightsail push-container-image \
--region ${{ env.AWS_REGION }} \
--service-name ${service_name} \
--label ${service_name} \
--image ${service_name}:release
aws lightsail get-container-images --service-name ${service_name} | jq --raw-output ".containerImages[0].image" > image.txt
jq --arg image $(cat image.txt) '.containers.app.image = $image' container.template.json > container.json
aws lightsail create-container-service-deployment --service-name ${service_name} --cli-input-json file://$(pwd)/container.json

这里有很多内容!最后两个步骤是最重要的:Build Docker ImagePush and Deploy

docker build -t ${{ env.AWS_LIGHTSAIL_SERVICE_NAME }}:release .

此命令使用名称container-service-2 构建我们的 Docker 镜像,并将其标记为release

aws lightsail push-container-image ...

此命令将本地镜像推送到我们的 Lightsail 容器。

aws lightsail get-container-images --service-name ${service_name} | jq --raw-output ".containerImages[0].image" > image.txt

此命令检索镜像信息,并使用jq对其进行解析,并将镜像名称保存在本地文件image.txt 中。

jq --arg image $(cat image.txt) '.containers.app.image = $image' container.template.json > container.json

此命令使用保存在 image.txtcontainer.template.json 中的镜像名称,并创建一个名为 container.json 的新选项文件。此选项文件将在下一步中传递给 aws lightsail 用于最终部署。

aws lightsail create-container-service-deployment --service-name ${service_name} --cli-input-json file://$(pwd)/container.json

最后,此命令使用 service_name 以及 container.json 中的配置设置创建一个新的部署。

当您推送到 GitHub 并且操作成功时,您将能够在 AWS 上看到您的新 Deno 应用程序。

deno on aws