无服务器框架 Lambda AppSync 错误

Serverless framework Lambda AppSync error

我正在使用无服务器框架上传 AWS Lambda 函数以用作 AppSync 中的数据源。我拥有的 serverless.yml 非常基础:

service: mongoose-lambda-srvrls
provider:
  name: aws
  runtime: nodejs6.10
  region: us-west-2
functions:
  mongoose: 
    handler: index.handler 

当我 运行 AppSync GraphQL 查询时出现错误:

{
  "data": {
    "getPost": null
  },
  "errors": [
    {
      "path": [
        "getPost"
      ],
      "data": null,
      "errorType": "Lambda:AWSLambdaException",
      "errorInfo": null,
      "locations": [
        {
          "line": 43,
          "column": 2
        }
      ],
      "message": "User: arn:aws:sts::433333333335:assumed-role/appsync-datasource-lam-kkzuep-mongoose-lambda-srvr/APPSYNC_ASSUME_ROLE is not authorized to perform: lambda:InvokeFunction on resource: arn:aws:lambda:us-west-2:43333333333335:function:mongoose-lambda-srvrls-dev-mongoose (Service: AWSLambda; Status Code: 403; Error Code: AccessDeniedException; Request ID: 9fa82eb9-3a64-11e8-88a1-09c4e639fc45)"
    }
  ]
}

我很确定我需要充实我的 YML,以便此 lambda 堆栈可以很好地与 AppSync 配合使用,但我不太确定该怎么做。


多一点信息。在查看 Lambda 的 CloudFormation 中的资源时,我看到:

IamRoleLambdaExecution  mongoose-lambda-srvrls-dev-us-west-2-lambdaRole AWS::IAM::Role
MongooseLambdaFunction  mongoose-lambda-srvrls-dev-mongoose AWS::Lambda::Function   
MongooseLambdaVersionwCQ1...    arn:aws:lambda:us-west-2:4542242445:function:mongoose-lambda-srvrls-dev-mongoose:4  AWS::Lambda::Version    
MongooseLogGroup    /aws/lambda/mongoose-lambda-srvrls-dev-mongoose AWS::Logs::LogGroup 
ServerlessDeploymentBucket  mongoose-lambda-srvrls-d-serverlessdeploymentbuck-qwp8sdfgjr    AWS::S3::Bucket

而在我使用 AppSync 文档 (AWS CLI) 创建的 Lambda 中具有以下 CloudFormation 资源:

AppSyncLambdaInvokePolicy   Fulls-AppS-15SHASDFSADZ03N  AWS::IAM::Policy
AppSyncServiceRole  Fullstack-Lamba-AppSyncServiceRole-DK8QHASDFE5R AWS::IAM::Role
LambdaExecutionRole Fullstack-Lamba-LambdaExecutionRole-OJHASDF3AHG1    AWS::IAM::Role  
LambdaFunction  fullstack-lambda    AWS::Lambda::Function

看起来您赋予 AppSync 的角色 运行 lambda 函数没有调用该特定 lambda 的权限。

您需要创建或修改一个角色,使其具有以下权限。

IAM 角色应该有一个策略,使承担它的任何人都能够 run/invoke 您的 lambda 函数:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "lambda:Invoke"
            ],
            "Resource": "arn:aws:lambda:REGION:ACCOUNTNUMBER:function/LAMBDA_FUNCTION"
        }
    ]
}

该角色还应具有信任策略。此信任策略将允许 AppSync 代表您承担该角色。这就是每当 graphQL 请求传入时 AppSync 调用您的 lambda 的方式。

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": {
                "Service": "appsync.amazonaws.com"
            },
            "Action": "sts:AssumeRole"
        }
    ]
}

一旦您拥有具有必要权限的 IAM 角色,您将需要确保它与 AppSync 中的 lambda 数据源相关联。您可以 select AppSync 控制台 Data Sources 部分中的角色,或使用 AppSync CLI 更新 lambda 数据源并使其使用您的角色。

有关创建与 AppSync 配合良好的 lambda 函数的更多信息,请参阅文档:https://docs.aws.amazon.com/appsync/latest/devguide/tutorial-lambda-resolvers.html#configure-data-source-for-aws-lambda

我认为他们在 https://docs.aws.amazon.com/appsync/latest/devguide/tutorial-lambda-resolvers.html#configure-data-source-for-aws-lambda 文档中犯了一个错误。

允许的操作应该是 lambda:InvokeFunction 而不是 lambda:Invoke

这是有效的:

{
  "Version"   : "2012-10-17",
  "Statement" : [{
    "Effect"    : "Allow",
    "Action"    : "lambda:InvokeFunction",
    "Resource"  : "arn:aws:lambda:REGION:ACCOUNTNUMBER:function/LAMBDA_FUNCTION"
  }]
}