CDK 應用程式開發過程中,測試與除錯至關重要。斷言測試驗證特定資源屬性,快照測試確保 CloudFormation 範本一致性。CDK 佈署日誌提供詳細錯誤訊息,VSCode 除錯工具則能逐步追蹤程式碼執行。無伺服器應用程式開發可簡化伺服器管理,提升效率。透過 API Gateway 建立 API 介面,Lambda 函式處理業務邏輯,Step Functions 協調工作流程,DynamoDB 提供資料儲存。整合這些服務,能快速構建可擴充套件、高彈性的無伺服器應用程式。
測試與故障排除 AWS CDK 應用程式
斷言測試與快照測試
在開發 AWS CDK 應用程式時,測試是確保基礎設施正確佈署和資源狀態符合預期的關鍵步驟。其中,斷言測試和快照測試是兩種重要的測試方法。
斷言測試
斷言測試允許開發者驗證 CDK 建構模組的特定屬性或子元件是否符合預期。以下是一個簡單的例子:
const template = Template.fromStack(chapter6Stack);
template.hasResourceProperties("AWS::ECS::TaskDefinition", {
Cpu: 256,
Memory: 256,
});
在這個例子中,我們使用 Template.hasResourceProperties 方法來驗證 ECS TaskDefinition 資源的 CPU 和記憶體屬性是否正確。
快照測試
快照測試則是比較目前的 CloudFormation 範本輸出與之前的版本,以確保輸出的一致性和正確性。這種方法特別適合用於驗證複雜系統的輸出或確保系統輸出在時間上的穩定性。
it("Matches the snapshot.", () => {
const stack = new Stack();
const chapter6Stack = new Chapter6Stack(stack, "Chapter6Stack", {
env: {
region: parsed?.CDK_DEFAULT_REGION,
account: parsed?.CDK_DEFAULT_ACCOUNT,
},
});
const template = Template.fromStack(chapter6Stack);
expect(template.toJSON()).toMatchSnapshot();
});
執行測試
執行測試時,Jest 會自動比較目前的輸出與之前的快照。如果輸出不符,Jest 會提示錯誤並顯示差異。
快照測試與 CI/CD
在 CI/CD 管道中加入快照測試,可以確保任何對基礎設施的變更都經過審查和批准。
比較斷言測試和快照測試
斷言測試關注特定資源屬性的正確性,而快照測試則檢查整個 CloudFormation 範本的一致性。兩者結合使用,可以提供全面的測試覆寫。
檢視 CDK 佈署日誌
當資源建立過程中出現問題時,檢視 CDK 佈署日誌可以幫助診斷問題。可以使用 -v、-vv 或 -vvv 引數來增加日誌的詳細程度。
$ cdk deploy --profile cdk -vv
這種方法特別適用於 ECS 容器無法穩定執行的情況,可以提供更詳細的錯誤訊息。
程式碼範例:
// lib/chapter-6-stack.ts
import * as cdk from "aws-cdk-lib";
import * as ecs from "aws-cdk-lib/aws-ecs";
export class Chapter6Stack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
// 建立 ECS TaskDefinition
const taskDefinition = new ecs.TaskDefinition(this, "TaskDefinition", {
cpu: "256",
memory: "256",
});
// 設定 TaskDefinition 的角色許可權
taskDefinition.addToTaskRolePolicy(
new iam.PolicyStatement({
effect: iam.Effect.ALLOW,
actions: [
"secretsmanager:GetSecretValue",
"secretsmanager:ListSecrets", // 新增的許可權
],
resources: ["*"],
})
);
}
}
內容解密:
上述程式碼展示瞭如何在 CDK 中定義一個 ECS TaskDefinition,並為其任務角色新增特定的 IAM 許可權。程式碼中特別新增了 secretsmanager:ListSecrets 許可權,這將會在快照測試中被捕捉到。
圖表翻譯: 此圖表展示了 CDK 應用程式從合成到佈署,再到測試的流程。首先,CDK 應用程式被合成為 CloudFormation 範本,接著佈署到 AWS 資源。佈署後,透過斷言測試和快照測試來驗證資源的正確性和一致性。
使用 VSCode 除錯 CDK 應用程式
在開發 AWS CDK 應用程式時,除錯是不可或缺的一環。透過 VSCode 的內建除錯工具,您可以輕鬆地識別和修復程式碼中的問題。
設定 VSCode 除錯環境
要在 VSCode 中除錯 AWS CDK 應用程式,您需要設定一個啟動組態(launch configuration)在您的 launch.json 檔案中。首先,在您的基礎設施資料夾中建立一個名為 .vscode 的新資料夾,並在其中建立一個 launch.json 檔案:
{
"version": "0.2.0",
"configurations": [
{
"type": "node",
"request": "launch",
"name": "啟動程式",
"skipFiles": ["<node_internals>/**"],
"runtimeArgs": ["-r", "./node_modules/ts-node/register/transpile-only"],
"args": ["${workspaceFolder}/bin/chapter-6.ts"],
"env": {
"CDK_MODE": "ONLY_DEV",
"CDK_DEFAULT_ACCOUNT": "123456789123",
"NODE_ENV": "Development",
"CDK_DEFAULT_REGION": "us-east-1"
}
}
]
}
內容解密:
"type": "node"指定了除錯器的型別為 Node.js。"request": "launch"表示我們要啟動一個新的 Node.js 程式進行除錯。"name": "啟動程式"是這個除錯組態的名稱,可以在 VSCode 的除錯面板中看到。"skipFiles"用於指定除錯時要跳過的檔案或資料夾。"runtimeArgs"傳遞給 Node.js 執行環境的引數,這裡啟用了ts-node以支援 TypeScript。"args"指定了要執行的程式入口點。"env"設定了環境變數,這些變數將在除錯過程中可用。
新增斷點和執行除錯
設定好 launch.json 後,您就可以在 CDK 程式碼中新增斷點。開啟 infrastructure/bin/chapter-6.ts 檔案,並在想要暫停執行的行號左側點選,新增一個斷點。
接著,開啟 VSCode 的除錯面板(按 Ctrl + Shift + D),您會看到一個名為「啟動程式」的除錯組態。點選旁邊的「播放」按鈕或按 F5 鍵啟動除錯。
觀察變數和控制除錯流程
當程式執行到斷點處暫停時,您可以在除錯面板中檢視當前的區域性變數、閉包變數和全域變數。同時,VSCode 會在螢幕頂部顯示一個除錯控制列,允許您繼續、重新啟動或結束除錯會話。
疑難排解常見 CDK 問題
在使用 CDK 開發過程中,您可能會遇到一些常見的問題。本文將討論如何解決這些問題。
環境未引導(Bootstrapping)
當您嘗試佈署到一個新的 AWS 環境時,可能會遇到錯誤提示該環境尚未被引導。引導是指向特定區域佈署一個預先建立的 AWS 堆積疊,以設定佈署任何堆積疊所需的資源,如 S3 儲存桶、ECR 倉函式庫等。
要解決這個問題,您可以使用以下命令:
$ cdk bootstrap
每次在新的 AWS 帳戶中佈署 CDK 專案時,都需要執行此命令。
IAM 許可權
在佈署堆積疊或設定環境時,需要確保使用的 AWS 帳戶具有執行這些操作的適當許可權。這包括建立 S3 物件、上傳 Docker 映像到 ECR、建立 EC2 例項等。
您可以登入 AWS 管理主控台,導航到 IAM 儀錶板,檢查並更新您的帳戶許可權。
圖表翻譯:
此圖示說明瞭在 VSCode 中設定和執行 CDK 除錯的流程。
@startuml
skinparam backgroundColor #FEFEFE
skinparam sequenceArrowThickness 2
title AWS CDK 應用程式測試與無伺服器開發
actor "客戶端" as client
participant "API Gateway" as gateway
participant "認證服務" as auth
participant "業務服務" as service
database "資料庫" as db
queue "訊息佇列" as mq
client -> gateway : HTTP 請求
gateway -> auth : 驗證 Token
auth --> gateway : 認證結果
alt 認證成功
gateway -> service : 轉發請求
service -> db : 查詢/更新資料
db --> service : 回傳結果
service -> mq : 發送事件
service --> gateway : 回應資料
gateway --> client : HTTP 200 OK
else 認證失敗
gateway --> client : HTTP 401 Unauthorized
end
@enduml圖表翻譯: 此圖示詳細展示了從建立 .vscode 資料夾到啟動除錯的整個過程。首先,您需要在專案中建立 .vscode 資料夾並在其中建立 launch.json 檔案。接著,您需要在 launch.json 中設定除錯組態,包括指定 Node.js 型別、執行引數和環境變數等。完成這些設定後,您就可以在程式碼中新增斷點並啟動除錯。在除錯過程中,您可以觀察當前的變數值,並透過 VSCode 提供的控制列來控制除錯流程。透過這個過程,您可以更有效地識別和修復 CDK 程式碼中的問題。
使用 AWS CDK 進行無伺服器應用程式開發
在前一章中,我們學習瞭如何測試我們的 CDK 程式碼。在本章中,我們將學習如何使我們的程式碼無伺服器,透過放棄 RDS 和 ECS,轉而使用 API Gateway 和 AWS Lambda。
以下是我們將在本章中涵蓋的內容:
- 解釋什麼是無伺服器
- 使用 CDK 建立和設定 API gateway
- 建立和設定一些 Lambda 函式,並將它們連線到 API gateway
- 建立一個 step function 狀態機,並將其連結到 AWS SES
- 建立和設定一個 DynamoDB 表,並在堆積疊佈署期間自動填充它
設定專案
開啟本章的程式碼在您選擇的編輯器中。就像在前面的章節中一樣,我們將程式碼分成基礎設施、伺服器和網頁目錄。
首先,讓我們建立我們應用的前端,以便 CDK 可以將建置目錄的內容上傳到 S3。前往網頁目錄,並在終端機中執行以下命令:
$ yarn
接著執行以下命令:
$ yarn build:prod
然後,回到基礎設施目錄,執行以下命令:
$ yarn
這將安裝專案的所有依賴項。
什麼是無伺服器?
無伺服器運算是一種開發和執行雲端應用程式和服務的方式,無需擔心管理伺服器。與傳統運算不同,您不需要設定和維護伺服器,雲端提供商(例如 AWS)會處理所有繁瑣的伺服器事務。這意味著您可以專注於撰寫程式碼和開發您的應用程式。
您的應用程式會根據事件(例如使用者請求或佇列中的訊息)執行,而雲端提供商會自動處理程式碼執行並根據需要擴充套件或縮減規模。這節省了您時間和金錢,同時也降低了停機和其他問題的風險。
如同前述,無伺服器運算讓您可以專注於重要的事情:您的應用程式功能。雲端提供商處理所有技術層面,讓您可以更快地開發並利用最先進的技術,而不必擔心相容性問題。
這是一個雙贏的局面——它具有成本效益、彈性和可擴充套件性,使其成為許多公司的熱門選擇。一旦您開始使用它並進行編碼,一切都會變得更加有意義。所以,讓我們開始吧。
使用 CDK 建立 API Gateway
首先,我們需要使用 CDK 建立 API Gateway。以下是一個範例程式碼:
import * as cdk from "aws-cdk-lib";
import * as apigateway from "aws-cdk-lib/aws-apigateway";
export class ApiGatewayStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
const api = new apigateway.RestApi(this, "api", {
restApiName: "My API",
description: "This is my API",
});
// ...
}
}
內容解密:
在上述程式碼中,我們使用 aws-cdk-lib 和 aws-cdk-lib/aws-apigateway 模組來建立 API Gateway。首先,我們建立一個新的 RestApi 例項,並傳遞必要的屬性,例如 restApiName 和 description。接著,我們可以新增資源和方法到 API Gateway。
建立 Lambda 函式並連線到 API Gateway
接下來,我們需要建立 Lambda 函式並將其連線到 API Gateway。以下是一個範例程式碼:
import * as cdk from "aws-cdk-lib";
import * as lambda from "aws-cdk-lib/aws-lambda";
export class LambdaStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
const func = new lambda.Function(this, "func", {
functionName: "My Lambda Function",
runtime: lambda.Runtime.NODEJS_14_X,
handler: "index.handler",
code: lambda.Code.fromAsset("lambda"),
});
// ...
}
}
內容解密:
在上述程式碼中,我們使用 aws-cdk-lib 和 aws-cdk-lib/aws-lambda 模組來建立 Lambda 函式。首先,我們建立一個新的 Function 例項,並傳遞必要的屬性,例如 functionName、runtime、handler 和 code。接著,我們可以將 Lambda 函式連線到 API Gateway。
建立 Step Function 狀態機並連結到 AWS SES
最後,我們需要建立 Step Function 狀態機並將其連結到 AWS SES。以下是一個範例程式碼:
import * as cdk from "aws-cdk-lib";
import * as stepfunctions from "aws-cdk-lib/aws-stepfunctions";
export class StepFunctionStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
const stateMachine = new stepfunctions.StateMachine(this, "stateMachine", {
stateMachineName: "My State Machine",
definition: stepfunctions.Chain.start(
new stepfunctions.Pass(this, "pass")
),
});
// ...
}
}
內容解密:
在上述程式碼中,我們使用 aws-cdk-lib 和 aws-cdk-lib/aws-stepfunctions 模組來建立 Step Function 狀態機。首先,我們建立一個新的 StateMachine 例項,並傳遞必要的屬性,例如 stateMachineName 和 definition。接著,我們可以將 Step Function 狀態機連結到 AWS SES。
本章中,我們學習瞭如何使用 AWS CDK 建立無伺服器應用程式,包括建立 API Gateway、Lambda 函式、Step Function 狀態機和 DynamoDB 表。在下一章中,我們將繼續探索如何使用 AWS CDK 建立更複雜的無伺服器應用程式。