Java AWS Lambda函数调用出现NoClassDefFoundError的解决求助
我开发了一个Java Lambda函数,用于调用另一个Lambda函数,代码如下:
package com.example; import com.amazonaws.services.lambda.AWSLambda; import com.amazonaws.services.lambda.AWSLambdaClientBuilder; import com.amazonaws.services.lambda.model.InvokeRequest; import com.amazonaws.services.lambda.model.InvokeResult; public class InvokeLambda { public String myHandler(String input){ AWSLambda lambdaClient = AWSLambdaClientBuilder.defaultClient(); InvokeRequest invokeRequest = new InvokeRequest() .withFunctionName("testLambdaFunction") .withPayload("{ \"key1\": \"value1\", \"key2\": \"value2\" }"); InvokeResult invokeResult = lambdaClient.invoke(invokeRequest); String functionOutput = new String(invokeResult.getPayload().array()); System.out.println(functionOutput); return input; } }
对应的pom.xml配置如下:
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.example</groupId> <artifactId>invokelambda</artifactId> <version>1.0-SNAPSHOT</version> <name>invokelambda</name> <!-- FIXME change it to the project's website --> <url>http://www.example.com</url> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <maven.compiler.source>1.7</maven.compiler.source> <maven.compiler.target>1.7</maven.compiler.target> </properties> <dependencyManagement> <dependencies> <dependency> <groupId>software.amazon.awssdk</groupId> <artifactId>bom</artifactId> <version>2.20.66</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.11</version> <scope>test</scope> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-lambda-java-core</artifactId> <version>1.2.2</version> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-lambda-java-events</artifactId> <version>3.11.1</version> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-lambda-java-log4j2</artifactId> <version>1.5.1</version> </dependency> <dependency> <groupId>com.amazonaws</groupId> <artifactId>aws-java-sdk-lambda</artifactId> <version>1.11.76</version> </dependency> </dependencies> <build> <pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) --> <plugins> <!-- clean lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#clean_Lifecycle --> <plugin> <artifactId>maven-clean-plugin</artifactId> <version>3.1.0</version> </plugin> <!-- default lifecycle, jar packaging: see https://maven.apache.org/ref/current/maven-core/default-bindings.html#Plugin_bindings_for_jar_packaging --> <plugin> <artifactId>maven-resources-plugin</artifactId> <version>3.0.2</version> </plugin> <plugin> <artifactId>maven-compiler-plugin</artifactId> <version>3.8.0</version> </plugin> <plugin> <artifactId>maven-surefire-plugin</artifactId> <version>2.22.1</version> </plugin> <plugin> <artifactId>maven-jar-plugin</artifactId> <version>3.0.2</version> </plugin> <plugin> <artifactId>maven-install-plugin</artifactId> <version>2.5.2</version> </plugin> <plugin> <artifactId>maven-deploy-plugin</artifactId> <version>2.8.2</version> </plugin> <!-- site lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#site_Lifecycle --> <plugin> <artifactId>maven-site-plugin</artifactId> <version>3.7.1</version> </plugin> <plugin> <artifactId>maven-project-info-reports-plugin</artifactId> <version>3.0.0</version> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-shade-plugin</artifactId> <version>3.2.2</version> <configuration> <createDependencyReducedPom>false</createDependencyReducedPom> </configuration> <executions> <execution> <phase>package</phase> <goals> <goal>shade</goal> </goals> </execution> </executions> </plugin> </plugins> </pluginManagement> </build> </project>
通过mvn package命令本地构建Jar包并上传至AWS Lambda后,出现如下错误:
"errorMessage": "com/amazonaws/services/lambda/AWSLambdaClientBuilder", "errorType": "java.lang.NoClassDefFoundError", "stackTrace": [ "com.example.InvokeLambda.myHandler(InvokeLambda.java:10)", "java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)", "java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)", "java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)", "java.base/java.lang.reflect.Method.invoke(Unknown Source)" ],
尝试移除并重新安装依赖包后问题仍未解决,该如何处理?
这个错误核心是运行时找不到AWSLambdaClientBuilder类,原因集中在依赖打包不完整、SDK版本冲突或构建配置问题,以下是针对性解决步骤:
1. 修复Maven Shade插件配置
你的pom.xml中maven-shade-plugin放在了<pluginManagement>节点下,该节点仅用于管理插件版本,不会实际执行打包逻辑。需要将插件移到<build>下的独立<plugins>节点,确保打包时能把所有依赖合并到Jar中:
<build> <!-- 保留原pluginManagement节点内容不变 --> <pluginManagement> <!-- 原配置内容 --> </pluginManagement> <!-- 新增独立plugins节点放置shade插件 --> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-shade-plugin</artifactId> <version>3.2.2</version> <configuration> <createDependencyReducedPom>false</createDependencyReducedPom> </configuration> <executions> <execution> <phase>package</phase> <goals> <goal>shade</goal> </goals> </execution> </executions> </plugin> </plugins> </build>
2. 解决AWS SDK版本冲突
pom中同时引入了AWS SDK v1(com.amazonaws:aws-java-sdk-lambda)和SDK v2的BOM(software.amazon.awssdk:bom),会导致依赖版本混乱,建议统一使用一个版本的SDK:
选项A:继续使用SDK v1
移除<dependencyManagement>中的SDK v2 BOM依赖,同时升级aws-java-sdk-lambda到较新的v1版本(如1.12.500),避免老旧版本兼容性问题:
<!-- 删除这部分依赖管理配置 --> <dependencyManagement> <dependencies> <dependency> <groupId>software.amazon.awssdk</groupId> <artifactId>bom</artifactId> <version>2.20.66</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement>
选项B:迁移到SDK v2(官方推荐)
AWS SDK v2性能更优,是官方主推版本,修改代码和依赖如下:
- 替换依赖:
<!-- 删除aws-java-sdk-lambda,添加v2的lambda依赖 --> <dependency> <groupId>software.amazon.awssdk</groupId> <artifactId>lambda</artifactId> </dependency>
- 修改Java代码:
package com.example; import software.amazon.awssdk.services.lambda.LambdaClient; import software.amazon.awssdk.services.lambda.model.InvokeRequest; import software.amazon.awssdk.services.lambda.model.InvokeResponse; public class InvokeLambda { public String myHandler(String input){ try (LambdaClient lambdaClient = LambdaClient.create()) { InvokeRequest invokeRequest = InvokeRequest.builder() .functionName("testLambdaFunction") .payload("{ \"key1\": \"value1\", \"key2\": \"value2\" }") .build(); InvokeResponse invokeResult = lambdaClient.invoke(invokeRequest); String functionOutput = new String(invokeResult.payload().asByteArray()); System.out.println(functionOutput); } catch (Exception e) { e.printStackTrace(); } return input; } }
3. 验证打包结果
执行mvn clean package后,打开target目录下生成的Jar包,检查是否包含com/amazonaws/services/lambda/AWSLambdaClientBuilder.class(v1)或software/amazonawssdk/services/lambda/LambdaClient.class(v2)。如果没有,说明打包配置仍有问题,需重新检查插件配置。
4. 匹配Lambda运行时环境
确保Lambda函数选择的运行时与pom中指定的Java版本一致(pom中为1.7,对应Lambda的Java 8运行时)。若升级了Java版本,需同步修改Lambda的运行时配置。
内容的提问来源于stack exchange,提问作者shamila

