

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

# 使用 .NET Lambda Global CLI
<a name="csharp-package-cli"></a>

透過 .NET CLI 和 .NET Lambda Global Tools 延伸模組 (`Amazon.Lambda.Tools`)，可以跨平台建立 .NET 式 Lambda 應用程式、封裝這些應用程式，然後部署到 Lambda。在本節中，您將學習如何使用 .NET CLI 和 Amazon Lambda 範本建立新的 Lambda .NET 專案，以及如何使用 `Amazon.Lambda.Tools` 封裝和部署這些專案。

**Topics**
+ [

## 必要條件
](#csharp-package-cli-prerequisites)
+ [

## 使用 .NET CLI 建立 .NET 專案
](#csharp-package-cli-create)
+ [

## 使用 .NET CLI 部署 .NET 專案
](#csharp-package-cli-deploy)
+ [

## 透過 .NET CLI 使用 Lambda 層
](#csharp-layers)

## 必要條件
<a name="csharp-package-cli-prerequisites"></a>

**.NET 8 SDK**  
如果尚未安裝，請安裝 [.NET 8](https://dotnet.microsoft.com/en-us/download/dotnet/8.0) SDK 和執行時期。

**AWS Amazon.Lambda.Templates .NET 專案範本**  
若要產生 Lambda 函數程式碼，請使用 [https://www.nuget.org/packages/Amazon.Lambda.Templates](https://www.nuget.org/packages/Amazon.Lambda.Templates) NuGet 套件。若要安裝此範本套件，請執行下列命令：  

```
dotnet new install Amazon.Lambda.Templates
```

**AWS Amazon.Lambda.Tools .NET Global CLI 工具**  
若要建立 Lambda 函數，請使用 [https://www.nuget.org/packages/Amazon.Lambda.Tools](https://www.nuget.org/packages/Amazon.Lambda.Tools) [.NET Core Global Tools 延伸模組](https://aws.amazon.com/blogs/developer/net-core-global-tools-for-aws/)。若要安裝 Amazon.Lambda.Tools，請執行下列命令：  

```
dotnet tool install -g Amazon.Lambda.Tools
```
如需有關 Amazon.Lambda.Tools .NET CLI 延伸模組的詳細資訊，請參閱 GitHub 上的[適用於 .NET CLI 的 AWS 延伸模組](https://github.com/aws/aws-extensions-for-dotnet-cli)儲存庫。

## 使用 .NET CLI 建立 .NET 專案
<a name="csharp-package-cli-create"></a>

在 .NET CLI 中，在命令列中使用 `dotnet new` 命令建立 .NET 專案。Lambda 提供使用 [https://www.nuget.org/packages/Amazon.Lambda.Templates](https://www.nuget.org/packages/Amazon.Lambda.Templates) NuGet 套件的其他範本。

安裝此套件後，執行以下命令即可查看可用範本的清單。

```
dotnet new list
```

若要檢查範本的詳細資訊，請使用 `help` 選項。例如，若要查看有關 `lambda.EmptyFunction` 範本的詳細資訊，請執行以下命令。

```
dotnet new lambda.EmptyFunction --help
```

若要建立 .NET Lambda 函數的基本範本，請使用 `lambda.EmptyFunction` 範本。這會建立一個簡單的函數，此函數會接受字串作為輸入，並使用 `ToUpper` 方法轉換為大寫。此範本支援以下選項︰ 
+ `--name` - 函數的名稱。
+ `--region`：要建立函數的 AWS 區域。
+ `--profile`：您的 適用於 .NET 的 AWS SDK 憑證檔中的設定檔名稱。若要深入了解 .NET 中的憑證設定檔，請參閱**《適用於 .NET 的 AWS SDK 開發人員指南》中的[設定 AWS 憑證](https://docs.aws.amazon.com/sdk-for-net/v3/developer-guide/net-dg-config-creds.html)。

在此範例中，我們使用預設設定檔和 AWS 區域 設定建立了新的空函數 `myDotnetFunction`：

```
dotnet new lambda.EmptyFunction --name myDotnetFunction
```

此命令會在您的專案目錄中建立以下檔案和目錄。

```
└── myDotnetFunction
    ├── src
    │   └── myDotnetFunction
    │       ├── Function.cs
    │       ├── Readme.md
    │       ├── aws-lambda-tools-defaults.json
    │       └── myDotnetFunction.csproj
    └── test
        └── myDotnetFunction.Tests
            ├── FunctionTest.cs
            └── myDotnetFunction.Tests.csproj
```

在 `src/myDotnetFunction` 目錄下，檢查下列檔案：
+ **aws-lambda-tools-defaults.json**：您在部署 Lambda 函數時，在此檔案中指定命令列選項。例如：

  ```
    "profile" : "default",
    "region" : "us-east-2",
    "configuration" : "Release",
    "function-architecture": "x86_64",
    "function-runtime":"dotnet8",
    "function-memory-size" : 256,
    "function-timeout" : 30,
    "function-handler" : "myDotnetFunction::myDotnetFunction.Function::FunctionHandler"
  ```
+ **Function.cs**：您的 Lambda 處理常式函數程式碼。它是 C\$1 範本，包含了預設的 `Amazon.Lambda.Core` 程式庫和預設的 `LambdaSerializer` 屬性。如需關於序列化需求及選項的詳細資訊，請參閱[C\$1 Lambda 函式中的序列化](csharp-handler.md#csharp-handler-serializer)。它也包含可編輯以套用 Lambda 函數程式碼的範例函數。

  ```
  using Amazon.Lambda.Core;
  
  // Assembly attribute to enable the Lambda function's JSON input to be converted into a .NET class.
  [assembly: LambdaSerializer(typeof(Amazon.Lambda.Serialization.SystemTextJson.DefaultLambdaJsonSerializer))]
  
  namespace myDotnetFunction;
  
  public class Function
  {
  
      /// <summary>
      /// A simple function that takes a string and does a ToUpper
      /// </summary≫
      /// <param name="input"></param>
      /// <param name="context"></param>
      /// <returns></returns>
      public string FunctionHandler(string input, ILambdaContext context)
      {
          return input.ToUpper();
      }
  }
  ```
+ **myDotnetFunction.csproj**：[MSBuild](https://msdn.microsoft.com/en-us/library/dd393574.aspx) 檔案，列出構成應用程式的檔案和組件。

  ```
  <Project Sdk="Microsoft.NET.Sdk">
    <PropertyGroup>
      <TargetFramework>net8.0</TargetFramework>
      <ImplicitUsings>enable</ImplicitUsings>
      <Nullable>enable</Nullable>
      <GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
      <AWSProjectType>Lambda</AWSProjectType>
      <!-- This property makes the build directory similar to a publish directory and helps the AWS .NET Lambda Mock Test Tool find project dependencies. -->
      <CopyLocalLockFileAssemblies>true</CopyLocalLockFileAssemblies>
      <!-- Generate ready to run images during publishing to improve cold start time. -->
      <PublishReadyToRun>true</PublishReadyToRun>
    </PropertyGroup>
    <ItemGroup>
      <PackageReference Include="Amazon.Lambda.Core" Version="2.2.0" />
      <PackageReference Include="Amazon.Lambda.Serialization.SystemTextJson" Version="2.4.0" />
    </ItemGroup>
  </Project>
  ```
+ **Readme**：使用此檔案來記錄您的 Lambda 函數。

在 `myfunction/test` 目錄下，檢查下列檔案：
+ **myDotnetFunction.Tests.csproj**：如上所述，這是 [MSBuild](https://msdn.microsoft.com/en-us/library/dd393574.aspx) 檔案，其列出了構成您的測試專案的檔案和組件。也請注意，它包含 `Amazon.Lambda.Core` 程式庫，以便您順利整合測試函數時所需要的任何 Lambda 範本。

  ```
  <Project Sdk="Microsoft.NET.Sdk">
     ... 
  
      <PackageReference Include="Amazon.Lambda.Core" Version="2.2.0 " />
     ...
  ```
+ **FunctionTest.cs**：包含在 `src` 目錄中的相同的 C\$1 程式碼範本檔案。編輯此檔案以鏡像您的函數的生產程式碼，並在上傳 Lambda 函數至生產環境之前進行測試。

  ```
  using Xunit;
  using Amazon.Lambda.Core;
  using Amazon.Lambda.TestUtilities;
  
  using MyFunction;
  
  namespace MyFunction.Tests
  {
      public class FunctionTest
      {
          [Fact]
          public void TestToUpperFunction()
          {
  
              // Invoke the lambda function and confirm the string was upper cased.
              var function = new Function();
              var context = new TestLambdaContext();
              var upperCase = function.FunctionHandler("hello world", context);
  
              Assert.Equal("HELLO WORLD", upperCase);
          }
      }
  }
  ```

## 使用 .NET CLI 部署 .NET 專案
<a name="csharp-package-cli-deploy"></a>

若要建置部署套件並部署到 Lambda，請使用 `Amazon.Lambda.Tools` CLI 工具。若要從先前步驟中建立的檔案部署函數，請先瀏覽至包含函數 `.csproj` 檔案的資料夾。

```
cd myDotnetFunction/src/myDotnetFunction
```

若要將程式碼以 .zip 部署套件形式部署至 Lambda，請執行下列命令。選擇您的函數名稱。

```
dotnet lambda deploy-function myDotnetFunction
```

在部署期間，精靈會要求您選取 [使用執行角色定義 Lambda 函數許可](lambda-intro-execution-role.md)。在此範例中，請選取 `lambda_basic_role`。

部署函數後，您可以使用 `dotnet lambda invoke-function` 命令在雲端進行測試。在 `lambda.EmptyFunction` 範本的程式碼範例中，您可以使用 `--payload` 選項傳入字串來測試函數。

```
dotnet lambda invoke-function myDotnetFunction --payload "Just checking if everything is OK"
```

如果函數部署成功，您應該會看到類似以下內容的輸出。

```
dotnet lambda invoke-function myDotnetFunction --payload "Just checking if everything is OK"
Amazon Lambda Tools for .NET Core applications (5.8.0)
Project Home: https://github.com/aws/aws-extensions-for-dotnet-cli, https://github.com/aws/aws-lambda-dotnet

Payload:
"JUST CHECKING IF EVERYTHING IS OK"

Log Tail:
START RequestId: id Version: $LATEST
END RequestId: id
REPORT RequestId: id  Duration: 0.99 ms       Billed Duration: 1 ms         Memory Size: 256 MB     Max Memory Used: 12 MB
```

## 透過 .NET CLI 使用 Lambda 層
<a name="csharp-layers"></a>

**注意**  
雖然在 .NET 中可以將[層](chapter-layers.md)與函式搭配使用，但建議不要這麼做。.NET 中使用層的函式會在 `Init` 階段手動將共用組件載入到記憶體中，這可能會增加冷啟動時間。請改在編譯時加入所有共用程式碼，利用 .NET 編譯器的內建最佳化功能。

.NET CLI 支援命令，協助您發布層及部署使用層的 C\$1 函數。若要將層發布至指定的 Amazon S3 儲存貯體，請在與 `.csproj` 檔案相同的目錄中執行以下命令：

```
dotnet lambda publish-layer <layer_name> --layer-type runtime-package-store --s3-bucket <s3_bucket_name>
```

接著使用 .NET CLI 部署函數時，請在以下命令中指定要使用的層 ARN：

```
dotnet lambda deploy-function <function_name> --function-layers arn:aws:lambda:us-east-1:123456789012:layer:layer-name:1
```

如需 Hello World 函數的完整範例，請參閱 [blank-csharp-with-layer](https://github.com/awsdocs/aws-lambda-developer-guide/tree/main/sample-apps/blank-csharp-with-layer) 範例。