当前位置: 首页 > 知识库问答 >
问题:

AWS Java Lambda压缩JSON响应失败:“由于配置错误,执行失败:Lambda代理响应格式错误”

阎辰钊
2023-03-14

我正在从AWS API网关调用AWS Lambda函数。返回的JSON需要压缩,因为它有时会变得太大(身体大小太大等)。但是,我在通过API网关获取响应时遇到了一些问题。这是我的Java代码

    @Override
    public JSONObject handleRequest(Object input, Context context) {
        String json_string = "";
        try {
            Gson gson = new Gson();
            json_string = gson.toJson(input, LinkedHashMap.class);
        } catch (ClassCastException ex) {
            json_string = (String) input;
        }

        GenerateJson generateJson = new GenerateJson ();
        String body = "";
        try {
            JSONParser parser = new JSONParser();
            Object jsonObj = parser.parse(json_string);
            JSONObject matchesobj = (JSONObject) jsonObj;

            if (matchesobj.containsKey("body")) {
                body = (String) matchesobj.get("body");
            } else {
                JSONObject error = new JSONObject();
                error.put("error", "No body with Base64 data in Request.");
                System.out.println(error.toJSONString());
                return error;
            }

        } catch (ParseException ex) {
            ex.printStackTrace();
        }

        byte[] decodedBytes = Base64.getDecoder().decode(body);
        String decodedString = new String(decodedBytes);
        // System.out.println(decodedString);

        JSONObject json = generateJson .getJson(decodedString, "", 2);

        JSONObject returnObject = new JSONObject();
        JSONObject headers = new JSONObject();
        returnObject.put("statusCode", 205);
        returnObject.put("isBase64Encoded", true);
        // returnObject.put("Content-Encoding", "gzip");

        returnObject.put("headers", headers);
        returnObject.put("body", compressStringAndReturnBase64(json.toString()));

        return (returnObject);
    }

    public static String compressStringAndReturnBase64(String srcTxt) {

        ByteArrayOutputStream rstBao = new ByteArrayOutputStream();
        GZIPOutputStream zos;
        try {
            zos = new GZIPOutputStream(rstBao);
            zos.write(srcTxt.getBytes());
            IOUtils.closeQuietly(zos);
            byte[] bytes = rstBao.toByteArray();
            String base64comp = Base64.getEncoder().encodeToString(bytes);
            System.out.println("Json String is " + srcTxt.toString().getBytes().length + " compressed " + bytes.length + " compressed Base64 " + base64comp.getBytes().length);

            return base64comp;
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return "";
    }

我已经检查了Base64输出,它似乎工作正常(粘贴了它)https://www.base64decode.org/). 此外,当我与Postman核对时,我得到一个二进制blob,如果我将响应保存为以.gz结尾的内容,则可以使用7-zip解包。

在“设置”下,API网关二进制媒体类型已设置为/但我想让客户端“看到”它是gzip并动态解码的。但是,当我添加行时

returnObject.put("Content-Encoding", "gzip");

我得到{“message”:“internalserver error”},在AWS API日志中:由于配置错误,执行失败:Lambda代理响应格式错误

Lambda日志没有问题,因此它确实成功执行了,只是无法返回。

我想我需要在API网关方面做更多的调整,有什么想法吗?

共有2个答案

昝浩阔
2023-03-14

在HTTP请求中,添加带有有效负载内容类型的“Accept”头。

接受:应用/gzip

同样在HTTP响应中,应该有指示响应内容类型的“内容类型”标头。

内容类型:应用程序/gzip

您的lambda将Base64编码的二进制数据返回到API网关。因此,为了解码数据,HTTP请求的Accept头和响应的Content-type头应该在那里。

盖斌
2023-03-14

这听起来像是API网关上的二进制支持设置没有正确配置;API网关试图解析来自lambda的响应,而不是直接将其传递给客户端。

您可以在控制台中更新此设置:

 类似资料:
  • 我有一个API网关设置,它带有一个调用Lambda函数的自定义授权程序。出于测试目的,我从这里复制了以下示例:http://docs.aws.amazon.com/apigateway/latest/developerguide/api-gateway-create-api-as-simple-proxy-for-lambda.html#api-gateway-proxy-integration-

  • 我正在尝试使用AWS lambda设置一个hello world示例并通过api网关提供它。我单击了“创建Lambda函数”,它设置了api网关并选择了空白函数选项。我添加了在AWS网关上找到的lambda函数入门指南: 问题是,当我向它发出GET请求时,它会返回502响应{“message”:“Internal server error”}。日志显示“由于配置错误,执行失败:Lambda代理响应

  • 问题内容: 我正在尝试使用AWS Lambda建立一个hello world示例,并通过api网关为其提供服务。我单击了“创建Lambda函数”,这将设置api通道并选择了Blank Function选项。我添加了在AWS网关入门指南中找到的lambda函数: 问题是,当我向它发出GET请求时,它返回了502响应。并且日志显示“由于配置错误,执行失败:Lambda代理响应格式错误”。 问题答案:

  • 我试图用AWS lambda建立一个hello world示例,并通过api网关为其服务。我点击了“创建一个Lambda函数”,它设置了api网关,并选择了空白函数选项。我添加了在AWS网关入门指南上找到的lambda函数: 问题是,当我向它发出GET请求时,它返回502响应。日志上写着“由于配置错误执行失败:Lambda代理响应不正确”。

  • 我运行了一些java代码,它将从示例中上传:storm-starter-topologies-0.9.6.jar,控制台显示: 535[main]INFO backtype.storm.stormsubmitter-上载拓扑jar C:\apachestorm096\examples\storm-starter\storm-starter-topologies-0.9.6.jar到指定位置:–/u

  • 我试图在aws.lamda-service上的node.js中创建函数,并在函数控制台进行测试,效果良好,但当调用api时,它不能导出到外部,api网关错误“malformed Lambda proxy response”状态错误502 有什么想法吗