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

Java调用AWS Lambda方法单元测试Mock LambdaClient不生效问题求助

问题原因

你遇到的Mock不生效的核心是依赖没有注入到测试目标类中,具体问题点如下:

  • RoutingService的无参构造函数内部自行初始化了真实的LambdaClient实例,你在测试类中通过@Mock生成的Mock对象完全没有被RoutingService使用,自然不会拦截真实调用
  • 你构造的fakeResponse是空实例,即使Mock生效,调用result.payload().asUtf8String()也会抛出空指针异常
  • 业务代码中存在多处拼写错误,会导致编译/运行异常:比如SDKBytes应为SdkBytes、routingURI后续使用时写成了routingUri、AWSServiceExceptuion拼写错误、方法最后返回的response变量未定义
修复方案

第一步:改造RoutingService支持依赖注入

新增构造函数,允许外部传入LambdaClient、环境、区域参数,原有生产逻辑保持不变:

public class RoutingService {

  private LambdaClient lambdaClient;
  private String env;
  private String region;

  // 新增测试用构造函数
  public RoutingService(LambdaClient lambdaClient, String env, String region){
     this.lambdaClient = lambdaClient;
     this.env = env;
     this.region = region;
  }

  // 原有生产用无参构造保持不变
  public RoutingService(){
     this(LambdaClient.builder().build(), System.getenv(ENVIRONMENT), System.getenv(REGION));
  }

  // 剩余原有代码保持不变,注意修正拼写错误
}

第二步:修改单元测试用例

调整测试代码,将Mock的LambdaClient注入到RoutingService实例中,同时构造合法的返回值:

// 测试类上方新增Mockito扩展注解(JUnit5环境,老版本可以保留initMocks)
@ExtendWith(MockitoExtension.class)
public class RoutingServiceTest {

  @Mock
  private LambdaClient lambdaClient;

  @Test
  void invokeLambda() throws IOException, JSONException {
    // 原有构造fakeRequest的代码保持不变
    Map<String,String> queryStringParameters = new HashMap<>();
    queryStringParameters.put("test","GOOG");

    String[] cookies = {"cookiea", "cookieb"};

    Map<String,String> headers = new HashMap<>();
    headers.put("header1","valuex");
    headers.put("header2","valuey");

    InvokeLambda fakeRequest = new InvokeLambda.InvokeLambdaBuilder()
                               .cdnToken("cdn-token").applicationName("eaf-4137-demo")
                               .service("quote").method("GET")
                               .path("QuoteService/getQuote")
                               .queryString(queryStringParameters)
                               .headers(headers)
                               .cookies(cookies)
                               .body("body")
                               .requestId("request-id")
                               .build();

    // 构造带合法payload的假返回
    RoutingResponse expectedResp = new RoutingResponse();
    expectedResp.setStatusCode(200);
    String respJson = new ObjectMapper().writeValueAsString(expectedResp);
    InvokeResponse fakeResponse = InvokeResponse.builder()
            .payload(SdkBytes.fromUtf8String(respJson))
            .statusCode(200)
            .build();
      
    Mockito.when(lambdaClient.invoke(Mockito.any(InvokeRequest.class))).thenReturn(fakeResponse);

    // 实例化RoutingService时传入Mock的lambdaClient和测试用环境、区域值
    RoutingService routingService = new RoutingService(lambdaClient, "test", "us-east-1");
    RoutingResponse response = routingService.invokeLambda(fakeRequest);

    Assertions.assertEquals(200, response.getStatusCode());
   }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.21 15:54:05