在 Java 中为 AWS Lambda 执行 "Hello World" 时出错
Error executing "Hello World" for AWS Lambda in Java
我写了 Hello World Lambda,我正在通过 AWS 工具包为 Eclipse 上传到 AWS 上执行。
public class HelloWorldLambdaHandler implements RequestHandler<String, String> {
public String handleRequest(String input, Context context) {
System.out.println("Hello World! executed with input: " + input);
return input;
}
}
执行上述代码时出现以下错误。知道我在这里做错了什么吗?顺便说一句,具有此处理程序的 Maven 项目没有任何其他 class,并且唯一的依赖项是 aws-lambda-java-core version 1.1.0.
Skip uploading function code since no local change is found...
Invoking function...
==================== FUNCTION OUTPUT ====================
{"errorMessage":"An error occurred during JSON parsing","errorType":"java.lang.RuntimeException","stackTrace":[],"cause":{"errorMessage":"com.fasterxml.jackson.databind.JsonMappingException: Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: lambdainternal.util.NativeMemoryAsInputStream@2f7c7260; line: 1, column: 1]","errorType":"java.io.UncheckedIOException","stackTrace":[],"cause":{"errorMessage":"Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: lambdainternal.util.NativeMemoryAsInputStream@2f7c7260; line: 1, column: 1]","errorType":"com.fasterxml.jackson.databind.JsonMappingException","stackTrace":["com.fasterxml.jackson.databind.JsonMappingException.from(JsonMappingException.java:148)","com.fasterxml.jackson.databind.DeserializationContext.mappingException(DeserializationContext.java:835)","com.fasterxml.jackson.databind.deser.std.StringDeserializer.deserialize(StringDeserializer.java:59)","com.fasterxml.jackson.databind.deser.std.StringDeserializer.deserialize(StringDeserializer.java:12)","com.fasterxml.jackson.databind.ObjectReader._bindAndClose(ObjectReader.java:1441)","com.fasterxml.jackson.databind.ObjectReader.readValue(ObjectReader.java:1047)"]}}}
出于某种原因,Amazon 无法将 json 反序列化为字符串。您可能会认为 String 与输入参数一样通用,但无论对错,它都不兼容。
要处理 JSON,您可以使用地图或自定义 POJO。
public class HelloWorldLambdaHandler {
public String handleRequest(Map<String,Object> input, Context context) {
System.out.println(input);
return "Hello";
}
}
从堆栈跟踪中读取错误。它说 "Can not deserialize instance of java.lang.String out of START_OBJECT token"。 "START_OBJECT" 标记是“{”。
问题很简单,您需要传递一个实际的字符串作为输入,例如 "A String"。这是您的 json 输入。不是 {}。 {} 不是字符串。您不需要任何大括号,只需要一个字符串(引号)。另一方面,{} 是一个有效的 Person 对象,因此一旦您将其更改为处理 Person 作为输入,它就会起作用。
我在测试中尝试使用以下值:
"TestInput"
而不是:
{ Input : "TestInput"}
它似乎运行良好。
完整的工作解决方案是
public class HelloWorldLambdaHandler implements RequestHandler<String, String> {
public String handleRequest(String input, Context context) {
System.out.println("Hello World! executed with input: " + input);
return input;
}
}
然后输入必须作为字符串用双引号括起来 - "Test Input"
测试配置器的输入 window 采用原始 json 或字符串。
- 如果您传递原始 json,AWS 会将 json 转换为 Map,其中变量名称是映射各个值的键。
- 如果将 json 括在双引号中并分隔内引号,这是 json 对象的可接受的 Java 字符串表示形式,可以照常解析。
解决方法 1:
而不是
{
"key1": "value1",
"key2": "value2",
"key3": "value3"
}
使用一些字符串作为输入,如下所示
"anyString"
它会很好地工作。
解决方法二:请参考@Lionel Port的回答
原因:
正如@Lionel Port 所建议的,您必须在 handleRequest() 方法中将 String 作为 inputType!
public String handleRequest(String input, Context context) {}
你可以在这里看到,输入类型是 String 而你正在传递 Json,这就是为什么会出现这个错误!
我写了 Hello World Lambda,我正在通过 AWS 工具包为 Eclipse 上传到 AWS 上执行。
public class HelloWorldLambdaHandler implements RequestHandler<String, String> {
public String handleRequest(String input, Context context) {
System.out.println("Hello World! executed with input: " + input);
return input;
}
}
执行上述代码时出现以下错误。知道我在这里做错了什么吗?顺便说一句,具有此处理程序的 Maven 项目没有任何其他 class,并且唯一的依赖项是 aws-lambda-java-core version 1.1.0.
Skip uploading function code since no local change is found...
Invoking function...
==================== FUNCTION OUTPUT ====================
{"errorMessage":"An error occurred during JSON parsing","errorType":"java.lang.RuntimeException","stackTrace":[],"cause":{"errorMessage":"com.fasterxml.jackson.databind.JsonMappingException: Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: lambdainternal.util.NativeMemoryAsInputStream@2f7c7260; line: 1, column: 1]","errorType":"java.io.UncheckedIOException","stackTrace":[],"cause":{"errorMessage":"Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: lambdainternal.util.NativeMemoryAsInputStream@2f7c7260; line: 1, column: 1]","errorType":"com.fasterxml.jackson.databind.JsonMappingException","stackTrace":["com.fasterxml.jackson.databind.JsonMappingException.from(JsonMappingException.java:148)","com.fasterxml.jackson.databind.DeserializationContext.mappingException(DeserializationContext.java:835)","com.fasterxml.jackson.databind.deser.std.StringDeserializer.deserialize(StringDeserializer.java:59)","com.fasterxml.jackson.databind.deser.std.StringDeserializer.deserialize(StringDeserializer.java:12)","com.fasterxml.jackson.databind.ObjectReader._bindAndClose(ObjectReader.java:1441)","com.fasterxml.jackson.databind.ObjectReader.readValue(ObjectReader.java:1047)"]}}}
出于某种原因,Amazon 无法将 json 反序列化为字符串。您可能会认为 String 与输入参数一样通用,但无论对错,它都不兼容。
要处理 JSON,您可以使用地图或自定义 POJO。
public class HelloWorldLambdaHandler {
public String handleRequest(Map<String,Object> input, Context context) {
System.out.println(input);
return "Hello";
}
}
从堆栈跟踪中读取错误。它说 "Can not deserialize instance of java.lang.String out of START_OBJECT token"。 "START_OBJECT" 标记是“{”。
问题很简单,您需要传递一个实际的字符串作为输入,例如 "A String"。这是您的 json 输入。不是 {}。 {} 不是字符串。您不需要任何大括号,只需要一个字符串(引号)。另一方面,{} 是一个有效的 Person 对象,因此一旦您将其更改为处理 Person 作为输入,它就会起作用。
我在测试中尝试使用以下值:
"TestInput"
而不是:
{ Input : "TestInput"}
它似乎运行良好。
完整的工作解决方案是
public class HelloWorldLambdaHandler implements RequestHandler<String, String> {
public String handleRequest(String input, Context context) {
System.out.println("Hello World! executed with input: " + input);
return input;
}
}
然后输入必须作为字符串用双引号括起来 - "Test Input"
测试配置器的输入 window 采用原始 json 或字符串。
- 如果您传递原始 json,AWS 会将 json 转换为 Map,其中变量名称是映射各个值的键。
- 如果将 json 括在双引号中并分隔内引号,这是 json 对象的可接受的 Java 字符串表示形式,可以照常解析。
解决方法 1:
而不是
{
"key1": "value1",
"key2": "value2",
"key3": "value3"
}
使用一些字符串作为输入,如下所示
"anyString"
它会很好地工作。
解决方法二:请参考@Lionel Port的回答
原因:
正如@Lionel Port 所建议的,您必须在 handleRequest() 方法中将 String 作为 inputType!
public String handleRequest(String input, Context context) {}
你可以在这里看到,输入类型是 String 而你正在传递 Json,这就是为什么会出现这个错误!