Amazon web services 通过AWS API网关和Lambda函数返回动态内容类型

Amazon web services 通过AWS API网关和Lambda函数返回动态内容类型,amazon-web-services,lambda,aws-lambda,content-type,aws-api-gateway,Amazon Web Services,Lambda,Aws Lambda,Content Type,Aws Api Gateway,我想使用AWSAPI网关作为代理,从S3存储桶获取文件并将其返回给客户端。我使用Lambda函数与S3通信,并通过awsapi网关将文件发送到客户端。我认为最好的方法是使用“Lambda代理集成”,这样整个请求就可以通过管道传输到Lambda,而无需任何修改。但是如果我这样做了,那么我就不能为Lambda函数产生的响应设置集成响应。因此,客户端得到的只是JSON API网关似乎应该有一种方法来获取JSON并将请求转换为客户端的正确响应,但我似乎不知道如何实现这一点。有很多例子都指向手动设置API

我想使用AWSAPI网关作为代理,从S3存储桶获取文件并将其返回给客户端。我使用Lambda函数与S3通信,并通过awsapi网关将文件发送到客户端。我认为最好的方法是使用“Lambda代理集成”,这样整个请求就可以通过管道传输到Lambda,而无需任何修改。但是如果我这样做了,那么我就不能为Lambda函数产生的响应设置集成响应。因此,客户端得到的只是JSON

API网关似乎应该有一种方法来获取JSON并将请求转换为客户端的正确响应,但我似乎不知道如何实现这一点。有很多例子都指向手动设置API网关响应的内容类型,但是我需要将内容类型头设置为任何文件类型

同样对于图像和二进制格式,我的Lambda函数返回base64编码字符串,属性
isBase64Encoded
设置为
true
。当我转到“二进制支持”部分并指定类似于
image/*
的内容类型作为应以二进制形式返回时,它不起作用。我只成功地将二进制支持内容类型设置为
*/*
(也称为“一切”),这对非二进制内容类型不起作用


我错过了什么?为什么这看起来如此困难

原来API网关不是问题所在。我的Lambda函数没有返回正确的头

为了处理二进制响应,我发现您需要将二进制支持内容类型设置为
*/*
(也称为一切),然后让Lambda函数将属性
isBase64Encoded
设置为
true
。base64编码和指示的响应将被解码并作为二进制文件提供,而其他请求将按原样返回

以下是Lambda函数的简单要点,该函数采用给定路径,从S3读取文件并通过API网关返回:

/**
 * This is a simple AWS Lambda function that will look for a given file on S3 and return it
 * passing along all of the headers of the S3 file. To make this available via a URL use
 * API Gateway with an AWS Lambda Proxy Integration.
 * 
 * Set the S3_REGION and S3_BUCKET global parameters in AWS Lambda
 * Make sure the Lambda function is passed an object with `{ pathParameters : { proxy: 'path/to/file.jpg' } }` set
 */

var AWS = require('aws-sdk');

exports.handler = function( event, context, callback ) {
    var region = process.env.S3_REGION;
    var bucket = process.env.S3_BUCKET;
    var key = decodeURI( event.pathParameters.proxy );

    // Basic server response
    /*
    var response = {
        statusCode: 200,
        headers: {
            'Content-Type': 'text/plain',
        },
        body: "Hello world!",
    };
    callback( null, response );
    */

    // Fetch from S3
    var s3 = new AWS.S3( Object.assign({ region: region }) );
    return s3.makeUnauthenticatedRequest(
        'getObject',
        { Bucket: bucket, Key: key },
        function(err, data) {
            if (err) {
                return err;
            }

            var isBase64Encoded = false;
            if ( data.ContentType.indexOf('image/') > -1 ) {
                isBase64Encoded = true;
            }

            var encoding = '';
            if ( isBase64Encoded ) {
                encoding = 'base64'
            }
            var resp = {
                statusCode: 200,
                headers: {
                    'Content-Type': data.ContentType,
                },
                body: new Buffer(data.Body).toString(encoding),
                isBase64Encoded: isBase64Encoded
            };

            callback(null, resp);
        }
    );
};
通过