为什么从CodePipeline调用我的Lambda函数不会接收事件数据?

问题描述

我有一个为部署Go应用程序而构建的CodePipeline,现在我正尝试使其使用golang-migrate应用数据库迁移。我有一个用Go语言编写的Lambda函数来应用迁移,但是从CodePipeline调用函数时,它不会接收带有修订位置,用户参数等的事件数据。为简单起见,我删除了迁移代码并替换为将事件数据简单地写入CloudWatch的代码

package main

import (
    "context"
    "fmt"

    "github.com/aws/aws-lambda-go/events"
    "github.com/aws/aws-lambda-go/lambda"
)

func Handler(ctx context.Context,job events.CodePipelineJob) (string,error) {    
    fmt.Printf("%#v",job)    
    return "Success",nil
}

func main() {
    lambda.Start(Handler)
}

当CodePipeline运行时,它会触发该函数,并且我从函数中的fmt.Printf语句在CloudWatch中找到以下日志:

events.CodePipelineJob {ID:“”,AccountID:“”,数据:events.CodePipelineData {ActionConfiguration:events.CodePipelineActionConfiguration {Configuration:events.CodePipelineConfiguration {FunctionName:“”,UserParameters:“”}},InputArtifacts:[ ] events.CodePipelineInputArtifact(nil),OutPutArtifacts:[] events.CodePipelineOutputArtifact(nil),ArtifactCredentials:events.CodePipelineArtifactCredentials {SecretAccessKey:“”,SessionToken:“”,AccessKeyID:“”},ContinuationToken:“} >

job参数是一个空对象,没有像我期望的那样绑定到CodePipeline事件数据。我所做的所有研究都表明它应该收到此处定义的CodePipelineJob事件:

https://github.com/aws/aws-lambda-go/blob/master/events/codepipeline_job.go

如果使用Python Lambda函数,我已经确认收到了预期的JSON事件格式:

import json
import logging

logger = logging.getLogger()
logger.setLevel(logging.INFO)

def main(event,context):    
    logger.info("Event: " + str(event))

    return "Success"

当我更改CodePipeline以改为调用Python函数时,包含正确数据的事件将成功写入CloudWatch。看起来类似于:

{
   "CodePipeline.job":{
      "id":"11111111-abcd-1111-abcd-111111abcdef","accountId":"111111111111","data":{
         "actionConfiguration":{
            "configuration":{
               "FunctionName":"MyLambdaFunctionForAWSCodePipeline","UserParameters":"some-input-such-as-a-URL"
            }
         },"inputArtifacts":[
            {
               "location":{
                  "s3Location":{
                     "bucketName":"the name of the bucket configured as the pipeline artifact store in Amazon S3,for example codepipeline-us-east-2-1234567890","objectKey":"the name of the application,for example CodePipelineDemoApplication.zip"
                  },"type":"S3"
               },"revision":null,"name":"ArtifactName"
            }
         ],"outputArtifacts":[            
         ],"continuationToken":"A continuation token if continuing job","encryptionKey":{
            "id":"arn:aws:kms:us-west-2:111122223333:key/1234abcd-12ab-34cd-56ef-1234567890ab","type":"KMS"
         }
      }
   }
}

所以,我的问题是,为什么我的Python Lambda函数将在Go函数不会编写事件时编写事件?我定义参数的方式有问题吗?

解决方法

我为输入参数使用了错误的事件类型。当我将参数类型更改为events.CodePipelineEvent时,该函数开始正确记录事件详细信息。输入事件中的根JSON元素名为CodePipeline.job。 events.CodePipelineEvent结构的定义如下:

CodePipelineEvent struct {
    CodePipelineJob CodePipelineJob `json:"CodePipeline.job"`
}

一旦我将参数切换为正确的类型,它就开始正确匹配根元素并提取值。这是更新的功能:

package main

import (
    "context"
    "fmt"

    "github.com/aws/aws-lambda-go/events"
    "github.com/aws/aws-lambda-go/lambda"
)

func Handler(ctx context.Context,event events.CodePipelineEvent) (string,error) {
    fmt.Printf("%#v",event)
    return "Success",nil
}

func main() {
    lambda.Start(Handler)
}