在带有Python的CDK中使用CfnFunction引用SAM中的本地代码

2024-09-27 21:31:41 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在使用AWS CDK创建SAMCfnFunction

对于codeUri属性,它需要引用一个^{}

使用SAM CLI时,我可以执行以下操作

Resources:
  HelloWorldFunction:
    Type: AWS::Serverless::Function
    Properties:
      CodeUri: hello_world/

其中hello_world有我函数的代码

运行sam buildsam deploy将代码打包并上载到S3,并在S3中使用正确的CodeUri路径部署Cloudformation模板

我尝试使用CDK(Python)做类似的事情,但是samcli在幕后完成的工作没有发生

from aws_cdk import (
    core,
    aws_sam as sam
)

class SamStack(core.Stack):
    
    def __init__(self, id, scope: core.Construct, **kwargs) -> None:
        super().__init__(id, scope, **kwargs)

        sam_stack = sam.CfnFunction(
            self, "MySamFunction",
            code_uri="lambda",  # Directory with my code
            runtime="python3.8",
            handler="MyFunction.handler",
            # other properties removed
        )

使用创建堆栈时运行cdk deploy错误

Transform AWS::Serverless-2016-10-31 failed with: Invalid Serverless Application Specification document. Number of errors found: 1. Resource with id [InferenceSam] is invalid. 'CodeUri' is not a valid S3 Uri of the form 's3://bucket/key' with optional versionId query parameter.

有没有一种方法可以使用CDK自动打包和上传python代码到S3


Tags: 代码coreawsidhelloworlds3sam
2条回答

这个线程有点旧,但我遇到了这个问题,它是令人费解的,所以我想分享我的解决方案。通过使用aws_s3_assets库并将local标志传递到无服务器堆栈中,以决定是否在synth上上载资产,或使用本地exec的路径,我能够解决部署中的这个问题

例如:

import aws_cdk.core as cdk
from aws_cdk import aws_sam as sam
from aws_cdk import aws_s3_assets as s3_assets


class ServerlessStack(cdk.Stack):

    def __init__(
        self, scope: cdk.Construct, id: str, local: bool = False, **kwargs
    ) -> None:

    # function_kwargs is a dict containing specific function params
    # see: https://docs.aws.amazon.com/cdk/api/latest/python/aws_cdk.aws_sam/CfnFunction.html

    if not local:
        function_kwargs['code_uri'] = s3_assets.Asset(
            scope=self,
            id=f"{function}asset",
            path=function_kwargs.pop('code_uri')
        ).s3_object_url

    # Create the function resource
    sam.CfnFunction(
        scope=self,
        id=function,
        runtime="python3.8",
        **function_kwargs
    )

我做了类似的事情,下面是我使用的方法

cdk-project
 | package.json
 | cdk.json
 | stack.ts
 |- lambda (sam application directory)
    | template.yaml
    |- solution
       | requirements.txt
       |- app       
          | index.py 

在template.yaml中

Resources:
  SolutionAPIFunction:
    Type: AWS::Serverless::Function 
    Properties:
      CodeUri: solution/
      Handler: app.index.lambda_handler

在package.json中

 "scripts": {
    "build": "cd lambda && sam build && cd .. && tsc",
    "watch": "tsc -w",
    "test": "jest",
    "cdk": "cdk"
  },

因此,当运行“npm run build”时,它将运行sam构建,并在cdk project/lambda/.aws sam下创建一个文件夹

在堆栈内部

    const aFunction = new Function(this, "aFunction", {
      runtime: Runtime.PYTHON_3_8,
      handler: "app.index.lambda_handler",
      code: Code.asset('./lambda/.aws-sam/build/SolutionAPIFunction')
      timeout: cdk.Duration.minutes(3),
      logRetention: logs.RetentionDays.THREE_MONTHS      
    })

相关问题 更多 >

    热门问题