How to return a CSV file using power tools #1780
-
From what I saw, by default power tools returns base64 in a call to get a .csv file, in the documentation it was not clear to me if I should send the accept header or if I have to configure binaryMediaTypes in my gateway or if I have to do both, none both ways worked for me, is there any documentation or example to solve this difficulty example: |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment
-
Hei @mrsants, tudo bom?! 😄 Thanks for opening this thread. Powertools automatically encodes the binary content to base64 to avoid any decoding errors in the Lambda response to ApiGateway according AWS documentation. In your case you need to configure binary media types in APIGateway and also specify the header Accept in Response object. I'm not sure what headers you're passing because I can't see all that code, but I've prepared some code here to help you out. Lambda Code import os
from pathlib import Path
import requests
from aws_lambda_powertools import Logger
from aws_lambda_powertools.event_handler.api_gateway import (
APIGatewayRestResolver,
Response,
)
from aws_lambda_powertools.logging import correlation_paths
from aws_lambda_powertools.utilities.typing import LambdaContext
logger = Logger()
app = APIGatewayRestResolver()
@app.get("/hello")
def get_logo():
todos = requests.get("https://www.sample-videos.com/csv/Sample-Spreadsheet-10-rows.csv")
return Response(status_code=200, content_type="application/csv", body=todos.content, headers={"Content-Disposition": "attachment; filename=filename_download.csv", "Accept": "application/csv"})
@logger.inject_lambda_context(correlation_id_path=correlation_paths.API_GATEWAY_REST)
def lambda_handler(event: dict, context: LambdaContext) -> dict:
return app.resolve(event, context) SAM Template AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: >
download-csv
Sample SAM Template for download-csv
# More info about Globals: https://github.com/awslabs/serverless-application-model/blob/master/docs/globals.rst
Globals:
Api:
BinaryMediaTypes:
- "application/csv"
Function:
Timeout: 3
Resources:
HelloWorldFunction:
Type: AWS::Serverless::Function # More info about Function Resource: https://github.com/awslabs/serverless-application-model/blob/master/versions/2016-10-31.md#awsserverlessfunction
Properties:
CodeUri: hello_world/
Handler: app.lambda_handler
Runtime: python3.9
Architectures:
- x86_64
Events:
HelloWorld:
Type: Api # More info about API Event Source: https://github.com/awslabs/serverless-application-model/blob/master/versions/2016-10-31.md#api
Properties:
Path: /hello
Method: get
Outputs:
# ServerlessRestApi is an implicit API created out of Events key under Serverless::Function
# Find out more about other implicit resources you can reference within SAM
# https://github.com/awslabs/serverless-application-model/blob/master/docs/internals/generated_resources.rst#api
HelloWorldApi:
Description: "API Gateway endpoint URL for Prod stage for Hello World function"
Value: !Sub "https://${ServerlessRestApi}.execute-api.${AWS::Region}.amazonaws.com/Prod/hello/"
HelloWorldFunction:
Description: "Hello World Lambda Function ARN"
Value: !GetAtt HelloWorldFunction.Arn
HelloWorldFunctionIamRole:
Description: "Implicit IAM Role created for Hello World function"
Value: !GetAtt HelloWorldFunctionRole.Arn If you still have trouble getting this to work, you can ping me on the Twitter (@LecoDamascena)/Discord and we see together. Thank you! |
Beta Was this translation helpful? Give feedback.
Hei @mrsants, tudo bom?! 😄
Thanks for opening this thread. Powertools automatically encodes the binary content to base64 to avoid any decoding errors in the Lambda response to ApiGateway according AWS documentation.
In your case you need to configure binary media types in APIGateway and also specify the header Accept in Response object. I'm not sure what headers you're passing because I can't see all that code, but I've prepared some code here to help you out.
Lambda Code