You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用@aws-sdk/client-lambda调用Lambda返回空响应排查

问题:Angular调用Lambda返回空Payload但CloudWatch显示执行成功

现象

  • 在AWS控制台使用相同负载测试Lambda函数,可成功执行并返回有效结果
  • 通过Angular调用时,CloudWatch日志明确显示Lambda运行成功,且输出了有效返回数据:
73ec2dbb-a647-43ea-82c6-a30407001d65    INFO    event received:  {
  body: "MATCH (n %7Bname:'Israel'%7D) RETURN n",
  headers: { SignatureHeader: '******' }
}

73ec2dbb-a647-43ea-82c6-a30407001d65    INFO    requestPayload:  MATCH (n %7Bname:'Israel'%7D) RETURN n

73ec2dbb-a647-43ea-82c6-a30407001d65    INFO    Successfully received result:  
{
    "results": [
        {
            "n": {
                "~id": "1d68ae59-deef-4dd7-b97d-d2771f7dd793",
                "~entityType": "node",
                "~labels": [
                    "Country"
                ],
                "~properties": {
                    "keyID": 972,
                    "language": "Hebrew",
                    "codeText": "IL",
                    "image": "flags/il.png",
                    "enabled": true,
                    "name": "Israel"
                }
            }
        }
    ]
}
  • 但浏览器控制台显示Angular应用收到空结果集:
Lambda payload:  {body: "MATCH (n %7Bname:'Israel'%7D) RETURN n", headers: {…}}
Creating LambdaClient:  {body: "MATCH (n %7Bname:'Israel'%7D) RETURN n", headers: {…}}
SENDING LambdaClient. command:  {FunctionName: 'simplify-mvp-neptune-query:dev', InvocationType: 'Event', Payload: Uint8Array(102)}
Returned from LAmbda call. resp:  
Uint8Array [buffer: ArrayBuffer(0), byteLength: 0, byteOffset: 0, length: 0, Symbol(Symbol.toStringTag): 'Uint8Array']

Angular客户端调用代码

import { Lambda } from "@aws-sdk/client-lambda";

...

async queryLambda(data: any) {
    console.log('Creating LambdaClient: ', data);
    const lambdaClient = new Lambda({ 
      region: environment.awsRegion,
      credentials: {        
        accessKeyId: environment.awsAccessKeyLambda,
        secretAccessKey: environment.awsSecretLambda,
      }
    });

    console.log('Creating InvokeCommand');
    const command = {
      FunctionName: environment.awsLambdaDBFunction,
      InvocationType: 'Event',
      //Payload: Buffer.from(JSON.stringify(data)),
      Payload: new TextEncoder().encode(JSON.stringify(data))
    };
  
    
    try {
      console.log('SENDING LambdaClient. command: ', command);      
      const resp  = await lambdaClient.invoke(command);
      console.log('Returned from LAmbda call. resp: ', resp.Payload);
      //const result = Buffer.from(resp.Payload).toString();
      const result = (new TextDecoder('utf-8').decode(resp.Payload));
      console.log('Converted result from buffer: ', result);            
      return result;
    } catch (err) {
      console.log('There was an error invoking Lambda DB function: ', err);
        return false;
    }
   }

也曾尝试另一种调用方式,结果一致:

import { LambdaClient, InvokeCommand } from "@aws-sdk/client-lambda"; 
...
const client = new LambdaClient(config);
const command = new InvokeCommand(input);
const response = await client.send(command);

Lambda(NodeJS 18.x)代码

import axios from 'axios';
import { SignatureV4 } from '@aws-sdk/signature-v4';
import { Sha256 } from '@aws-crypto/sha256-js';

const {
  AWS_ACCESS_KEY_ID,
  AWS_SECRET_ACCESS_KEY,
  AWS_SESSION_TOKEN,
  CALL_SIGNATURE
} = process.env;

const sigv4 = new SignatureV4({
  service: 'neptune-db',
  region: 'us-east-1',
  credentials: {
    accessKeyId: AWS_ACCESS_KEY_ID,
    secretAccessKey: AWS_SECRET_ACCESS_KEY,
    sessionToken: AWS_SESSION_TOKEN,
  },
  sha256: Sha256,
});


const validateSignature = async (requestSignature) => {
  //Lambda call permission validator
  if (requestSignature!=CALL_SIGNATURE) {
    throw new Error('Function call signature does not match');
  }
};


const decodeQuery = async (queryText) => {
    //Decodes some chars in the raw query text for Lambda to process properly
    let result = queryText.replace(/%7B/g, "{");
    result = result.replace(/%7D/g, "}");
    return result;
  };


export const handler = async (event) => {
  
  // retrieve signature and payload
  const requestSignature = event.headers.SignatureHeader;
  //const requestSignature = event.body.SignatureHeader;
  console.log('event received: ', event);
  
  try {
        await validateSignature(requestSignature); // throws if invalid signature
    } catch (error) {
        console.error(error);
        return {
            statusCode: 400,
            body: `Function permission error: ${error}`,
        };
    }
  
  const requestPayload = event.body; //Passed openCypher query string
  console.log('requestPayload: ', requestPayload);
  const signatureQuery = await decodeQuery(requestPayload);
  
  const ocQuery = requestPayload;
  const API_URL = "https://****.****.us-east-1.neptune.amazonaws.com:8182/openCypher?query=" + ocQuery;
  const apiUrl = new URL(API_URL);

  const signed = await sigv4.sign({
    method: 'GET',
    hostname: apiUrl.host,
    path: apiUrl.pathname,
    protocol: apiUrl.protocol,
    query: {
      query: signatureQuery
      },
    headers: {
      'Content-Type': 'application/json',
      host: apiUrl.hostname, 
    }
  });

  try {
    const result = await axios({
      ...signed,
      url: API_URL,
    });

    console.log('Successfully received result: ', JSON.stringify(result.data));
    return {
      statusCode: 200,
      body: result.data
    };
  } catch (error) {
    console.log('An error occurred', error);

    throw error;
  }
};

解决方案

问题出在**InvocationType: 'Event'**这个参数上:

  • 当设置为Event时,Lambda会以异步方式执行,调用方(Angular)会立即收到空响应,不会等待Lambda执行完成并返回结果,这就是你看到空Payload的原因
  • 若需要同步获取Lambda执行结果,需将InvocationType改为RequestResponse(这也是默认值)

修改后的Angular调用代码片段:

const command = {
  FunctionName: environment.awsLambdaDBFunction,
  InvocationType: 'RequestResponse', // 改为同步调用模式
  Payload: new TextEncoder().encode(JSON.stringify(data))
};

另外建议调整Lambda返回逻辑,将结果序列化为JSON字符串,避免前端解析异常:

return {
  statusCode: 200,
  body: JSON.stringify(result.data) // 将对象转为JSON字符串
};

前端解码Payload后,可直接用JSON.parse(result)解析出结果对象。

内容的提问来源于stack exchange,提问作者Mor Sagmon

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.30 06:12:43