使用 Cargo Lambda in 構建銹函數 AWS SAM - AWS Serverless Application Model

本文為英文版的機器翻譯版本,如內容有任何歧義或不一致之處,概以英文版為準。

使用 Cargo Lambda in 構建銹函數 AWS SAM

此功能正在的預覽版中, AWS SAM 且可能會變更。

使用指 AWS Serverless Application Model 令行介面 (AWS SAMCLI) 搭配 Rust AWS Lambda 函數。

必要條件

Rust語言

若要安裝Rust,請參閱Rust在Rust語言網站裝。

Cargo Lambda

AWS SAMCLI需要安裝Cargo Lambda的子指令。Cargo如需安裝指示,請參閱Cargo Lambda文件中的安裝

Docker

需要建置和測試 Rust Lambda 函數Docker。如需安裝指示,請參閱安裝 Docker

選擇加入 AWS SAMCLI測試版功能

由於此功能處於預覽狀態,因此您必須使用下列其中一種方法來選擇加入:

  1. 使用環境變數:SAM_CLI_BETA_RUST_CARGO_LAMBDA=1

  2. 將以下內容新增到您的 samconfig.toml 檔案:

    [default.build.parameters] beta_features = true [default.sync.parameters] beta_features = true
  3. 使用支援的 AWS SAMCLI指令時,請使用--beta-features此選項。例如:

    $ sam build --beta-features
  4. y當 AWS SAMCLI提示您選擇加入時選擇選項。以下是範例:

    $ sam build Starting Build use cache Build method "rust-cargolambda" is a beta feature. Please confirm if you would like to proceed You can also enable this beta feature with "sam build --beta-features". [y/N]: y

設定 AWS SAM 為與 Rust 函數搭 Lambda 使用

步驟 1:設定 AWS SAM 範本

使用以下內容配置您的 AWS SAM 模板:

  • 二進位 — 選用。指定您的範本何時包含多個 Rust Lambda 函數。

  • BuildMethodrust-cargolambda.

  • CodeUriCargo.toml 檔案的路徑。

  • 處理程序bootstrap.

  • 運行時-provided.al2

若要深入瞭解自訂執行階段,請參閱AWS Lambda 開發人員指南中的自 AWS Lambda 訂執行階段

以下是已設定範 AWS SAM 本的範例:

AWSTemplateFormatVersion: '2010-09-09' Transform: AWS::Serverless-2016-10-31 ... Resources: MyFunction: Type: AWS::Serverless::Function Metadata: BuildMethod: rust-cargolambda BuildProperties: function_a Properties: CodeUri: ./rust_app Handler: bootstrap Runtime: provided.al2 ...

步驟 2:搭 AWS SAMCLI配您的 Rust Lambda 函數使用

對 AWS SAM 範本使用任何 AWS SAMCLI指令。如需詳細資訊,請參閱 該 AWS SAMCLI

範例

你好世界的例子

在這個例子中,我們使用Rust作為我們的運行時構建示例 Hello World 應用程序。

首先,我們使用sam init. 在互動式流程中,我們選取 Hello World 應用程式並選擇 Rust 執行階段。

$ sam init ... Which template source would you like to use? 1 - AWS Quick Start Templates 2 - Custom Template Location Choice: 1 Choose an AWS Quick Start application template 1 - Hello World Example 2 - Multi-step workflow 3 - Serverless API ... Template: 1 Use the most popular runtime and package type? (Python and zip) [y/N]: ENTER Which runtime would you like to use? 1 - aot.dotnet7 (provided.al2) 2 - dotnet6 3 - dotnet5.0 ... 18 - python3.7 19 - python3.10 20 - ruby2.7 21 - rust (provided.al2) Runtime: 21 Based on your selections, the only Package type available is Zip. We will proceed to selecting the Package type as Zip. Based on your selections, the only dependency manager available is cargo. We will proceed copying the template using cargo. Would you like to enable X-Ray tracing on the function(s) in your application? [y/N]: ENTER Would you like to enable monitoring using CloudWatch Application Insights? For more info, please view https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/cloudwatch-application-insights.html [y/N]: ENTER Project name [sam-app]: hello-rust ----------------------- Generating application: ----------------------- Name: hello-rust Runtime: rust (provided.al2) Architectures: x86_64 Dependency Manager: cargo Application Template: hello-world Output Directory: . Configuration file: hello-rust/samconfig.toml Next steps can be found in the README file at hello-rust/README.md Commands you can use next ========================= [*] Create pipeline: cd hello-rust && sam pipeline init --bootstrap [*] Validate SAM template: cd hello-rust && sam validate [*] Test Function in the Cloud: cd hello-rust && sam sync --stack-name {stack-name} --watch

以下是我們的 Hello World 應用程序的結構:

hello-rust
├── README.md
├── events
│   └── event.json
├── rust_app
│   ├── Cargo.toml
│   └── src
│       └── main.rs
├── samconfig.toml
└── template.yaml

在我們的 AWS SAM 模板中,我們的Rust函數定義如下:

AWSTemplateFormatVersion: '2010-09-09' Transform: AWS::Serverless-2016-10-31 ... Resources: HelloWorldFunction: Type: AWS::Serverless::Function Metadata: BuildMethod: rust-cargolambda Properties: CodeUri: ./rust_app Handler: bootstrap Runtime: provided.al2 Architectures: - x86_64 Events: HelloWorld: Type: Api Path: /hello Method: get

接下來,我們執sam build行建置應用程式並準備部署。 AWS SAMCLI創建一個.aws-sam目錄並在那裡組織我們的構建工件。我們的函數是使用構建Cargo Lambda並存儲為可執行二進製文件在.aws-sam/build/HelloWorldFunction/bootstrap.

注意

如果您打算在 MacOS 中運行sam local invoke命令,則需要在調用之前構建不同的功能。若要這麼做,請使用下列命令:

  • SAM_BUILD_MODE=debug sam build

只有在本地測試將完成時才需要此命令。建置進行部署時,不建議這樣做。

hello-rust$ sam build Starting Build use cache Build method "rust-cargolambda" is a beta feature. Please confirm if you would like to proceed You can also enable this beta feature with "sam build --beta-features". [y/N]: y Experimental features are enabled for this session. Visit the docs page to learn more about the AWS Beta terms https://aws.amazon.com/service-terms/. Cache is invalid, running build and copying resources for following functions (HelloWorldFunction) Building codeuri: /Users/.../hello-rust/rust_app runtime: provided.al2 metadata: {'BuildMethod': 'rust-cargolambda'} architecture: x86_64 functions: HelloWorldFunction Running RustCargoLambdaBuilder:CargoLambdaBuild Running RustCargoLambdaBuilder:RustCopyAndRename Build Succeeded Built Artifacts : .aws-sam/build Built Template : .aws-sam/build/template.yaml Commands you can use next ========================= [*] Validate SAM template: sam validate [*] Invoke Function: sam local invoke [*] Test Function in the Cloud: sam sync --stack-name {{stack-name}} --watch [*] Deploy: sam deploy --guided

接下來,我們部署應用程式使用sam deploy --guided.

hello-rust$ sam deploy --guided Configuring SAM deploy ====================== Looking for config file [samconfig.toml] : Found Reading default arguments : Success Setting default arguments for 'sam deploy' ========================================= Stack Name [hello-rust]: ENTER AWS Region [us-west-2]: ENTER #Shows you resources changes to be deployed and require a 'Y' to initiate deploy Confirm changes before deploy [Y/n]: ENTER #SAM needs permission to be able to create roles to connect to the resources in your template Allow SAM CLI IAM role creation [Y/n]: ENTER #Preserves the state of previously provisioned resources when an operation fails Disable rollback [y/N]: ENTER HelloWorldFunction may not have authorization defined, Is this okay? [y/N]: y Save arguments to configuration file [Y/n]: ENTER SAM configuration file [samconfig.toml]: ENTER SAM configuration environment [default]: ENTER Looking for resources needed for deployment: ... Uploading to hello-rust/56ba6585d80577dd82a7eaaee5945c0b 817973 / 817973 (100.00%) Deploying with following values =============================== Stack name : hello-rust Region : us-west-2 Confirm changeset : True Disable rollback : False Deployment s3 bucket : aws-sam-cli-managed-default-samclisourcebucket-1a4x26zbcdkqr Capabilities : ["CAPABILITY_IAM"] Parameter overrides : {} Signing Profiles : {} Initiating deployment ===================== Uploading to hello-rust/a4fc54cb6ab75dd0129e4cdb564b5e89.template 1239 / 1239 (100.00%) Waiting for changeset to be created.. CloudFormation stack changeset --------------------------------------------------------------------------------------------------------- Operation LogicalResourceId ResourceType Replacement --------------------------------------------------------------------------------------------------------- + Add HelloWorldFunctionHelloW AWS::Lambda::Permission N/A orldPermissionProd ... --------------------------------------------------------------------------------------------------------- Changeset created successfully. arn:aws:cloudformation:us-west-2:012345678910:changeSet/samcli-deploy1681427201/f0ef1563-5ab6-4b07-9361-864ca3de6ad6 Previewing CloudFormation changeset before deployment ====================================================== Deploy this changeset? [y/N]: y 2023-04-13 13:07:17 - Waiting for stack create/update to complete CloudFormation events from stack operations (refresh every 5.0 seconds) --------------------------------------------------------------------------------------------------------- ResourceStatus ResourceType LogicalResourceId ResourceStatusReason --------------------------------------------------------------------------------------------------------- CREATE_IN_PROGRESS AWS::IAM::Role HelloWorldFunctionRole - CREATE_IN_PROGRESS AWS::IAM::Role HelloWorldFunctionRole Resource creation ... --------------------------------------------------------------------------------------------------------- CloudFormation outputs from deployed stack --------------------------------------------------------------------------------------------------------- Outputs --------------------------------------------------------------------------------------------------------- Key HelloWorldFunctionIamRole Description Implicit IAM Role created for Hello World function Value arn:aws:iam::012345678910:role/hello-rust-HelloWorldFunctionRole-10II2P13AUDUY Key HelloWorldApi Description API Gateway endpoint URL for Prod stage for Hello World function Value https://ggdxec9le9.execute-api.us-west-2.amazonaws.com/Prod/hello/ Key HelloWorldFunction Description Hello World Lambda Function ARN Value arn:aws:lambda:us-west-2:012345678910:function:hello-rust-HelloWorldFunction- yk4HzGzYeZBj --------------------------------------------------------------------------------------------------------- Successfully created/updated stack - hello-rust in us-west-2

為了進行測試,我們可以使用API端點調用我們的 Lambda 函數。

$ curl https://ggdxec9le9.execute-api.us-west-2.amazonaws.com/Prod/hello/ Hello World!%

為了在本地測試我們的功能,首先我們確保功能的Architectures屬性與我們的本地計算機匹配。

... Resources: HelloWorldFunction: Type: AWS::Serverless::Function # More info about Function Resource: https://github.com/awslabs/serverless-application-model/blob/master/versions/2016-10-31.md#awsserverlessfunction Metadata: BuildMethod: rust-cargolambda # More info about Cargo Lambda: https://github.com/cargo-lambda/cargo-lambda Properties: CodeUri: ./rust_app # Points to dir of Cargo.toml Handler: bootstrap # Do not change, as this is the default executable name produced by Cargo Lambda Runtime: provided.al2 Architectures: - arm64 ...

由於我們arm64在此示例中x86_64將架構從修改為,因此我們運行sam build以更新構建工件。然後我們運行sam local invoke到本地調用我們的函數。

hello-rust$ sam local invoke Invoking bootstrap (provided.al2) Local image was not found. Removing rapid images for repo public.ecr.aws/sam/emulation-provided.al2 Building image..................................................................................................................................... Using local image: public.ecr.aws/lambda/provided:al2-rapid-arm64. Mounting /Users/.../hello-rust/.aws-sam/build/HelloWorldFunction as /var/task:ro,delegated, inside runtime container START RequestId: fbc55e6e-0068-45f9-9f01-8e2276597fc6 Version: $LATEST {"statusCode":200,"body":"Hello World!"}END RequestId: fbc55e6e-0068-45f9-9f01-8e2276597fc6 REPORT RequestId: fbc55e6e-0068-45f9-9f01-8e2276597fc6 Init Duration: 0.68 ms Duration: 130.63 ms Billed Duration: 131 ms Memory Size: 128 MB Max Memory Used: 128 MB

單一 Lambda 函數專案

以下是包含一個 Rust Lambda 函數的無伺服器應用程式範例。

項目目錄結構:

.
├── Cargo.lock
├── Cargo.toml
├── src
│   └── main.rs
└── template.yaml

AWS SAM 模板:

AWSTemplateFormatVersion: '2010-09-09' Transform: AWS::Serverless-2016-10-31 ... Resources: MyFunction: Type: AWS::Serverless::Function Metadata: BuildMethod: rust-cargolambda Properties: CodeUri: ./ Handler: bootstrap Runtime: provided.al2 ...

多個 Lambda 函數專案

以下是一個包含多個 Rust Lambda 函數的無伺服器應用程式範例。

項目目錄結構:

.
├── Cargo.lock
├── Cargo.toml
├── src
│   ├── function_a.rs
│   └── function_b.rs
└── template.yaml

AWS SAM 模板:

AWSTemplateFormatVersion: '2010-09-09' Transform: AWS::Serverless-2016-10-31 ... Resources: FunctionA: Type: AWS::Serverless::Function Metadata: BuildMethod: rust-cargolambda BuildProperties: Binary: function_a Properties: CodeUri: ./ Handler: bootstrap Runtime: provided.al2 FunctionB: Type: AWS::Serverless::Function Metadata: BuildMethod: rust-cargolambda BuildProperties: Binary: function_b Properties: CodeUri: ./ Handler: bootstrap Runtime: provided.al2

Cargo.toml 檔案:

[package] name = "test-handler" version = "0.1.0" edition = "2021" [dependencies] lambda_runtime = "0.6.0" serde = "1.0.136" tokio = { version = "1", features = ["macros"] } tracing = { version = "0.1", features = ["log"] } tracing-subscriber = { version = "0.3", default-features = false, features = ["fmt"] } [[bin]] name = "function_a" path = "src/function_a.rs" [[bin]] name = "function_b" path = "src/function_b.rs"