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

Pulumi AWS Lambda单元测试报错:Could not find property info for real property on object: sdk

Pulumi + Vitest 测试异常:测试通过但非零状态退出

我用Pulumi创建了一个由API Gateway HTTP请求触发、可操作DynamoDB表的AWS Lambda。pulumi up执行完全正常,但跑Vitest测试时,明明测试通过了,进程却以非零状态退出,报错如下:

⎯⎯⎯ Unhandled Rejection ⎯⎯⎯
Error: Could not find property info for real property on object: sdk

我已经定位到错误来自Pulumi的createClosure.ts文件第1103行,但搞不清原因。想问下这是我操作有误,还是Pulumi的Bug?如果是Bug我就去提交Issue。

下面是相关代码摘要,我也做了一个最小复现仓库,GitHub Actions运行会出现这个问题。

基础设施定义文件 index.ts

import * as aws from '@pulumi/aws'
import * as apigateway from '@pulumi/aws-apigateway'
import handler from './handler'

const table = new aws.dynamodb.Table('Table', {...})

const tableAccessPolicy = new aws.iam.Policy('DbAccessPolicy', {
    // 为简洁起见已省略,允许put、get、delete操作
})

const lambdaRole = new aws.iam.Role('lambdaRole', {...})

new aws.iam.RolePolicyAttachment('RolePolicyAttachment', {...})

const callbackFunction = new aws.lambda.CallbackFunction(
  'callbackFunction',
  {
    role: lambdaRole,
    callback: handler(table.name),
  }
)

const api = new apigateway.RestAPI('api', {
  routes: [{
    method: 'GET',
    path: '/',
    eventHandler: callbackFunction,
  }]
})

export const dbTable = table
export const url = api.url

Lambda 处理函数 handler.ts

import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
import * as pulumi from '@pulumi/pulumi';
import * as aws from '@pulumi/aws';

export default function (tableName: pulumi.Output<string>) {
  return async function handleDocument(
    event: APIGatewayProxyEvent
  ): Promise<APIGatewayProxyResult> {
    try {
      const client = new aws.sdk.DynamoDB.DocumentClient();
      await client
        .put({
          TableName: tableName.get(),
          Item: { PK: 'hello', roomId: '12345' },
        })
        .promise();

      const result = await client
        .get({
          TableName: tableName.get(),
          Key: { PK: 'hello' },
        })
        .promise();

      await client
        .delete({
          TableName: tableName.get(),
          Key: { PK: 'hello' },
        })
        .promise();
      return {
        statusCode: 200,
        body: JSON.stringify({
          item: result.Item,
        }),
      };
    } catch (err) {
      return {
        statusCode: 200,
        body: JSON.stringify({
          error: err,
        }),
      };
    }
  };
}

Vitest 测试文件

import * as pulumi from '@pulumi/pulumi';
import { describe, it, expect, beforeAll } from 'vitest';

pulumi.runtime.setMocks(
  {
    newResource: function (args: pulumi.runtime.MockResourceArgs): {
      id: string;
      state: Record<string, any>;
    } {
      return {
        id: `${args.name}_id`,
        state: args.inputs,
      };
    },
    call: function (args: pulumi.runtime.MockCallArgs) {
      return args.inputs;
    },
  },
  'project',
  'stack',
  false
);

describe('infrastructure', () => {
  let infra: typeof import('./index');

  beforeAll(async function () {
    // 必须在定义mock后再导入程序
    infra = await import('./index');
  });

  it('Creates a DynamoDB table', async () => {
    const tableId = await new Promise((resolve) => {
      infra?.dbTable?.id.apply((id) => resolve(id));
    });
    expect(tableId).toBe('Table_id');
  });
});

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.22 10:27:46