Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to perform 302 Redirect in AWS Lambda python integrated with API Gateway?

I am trying to build a very light weight static website with a form using a serverless architecture:

  1. User populates the form with login info
  2. Submit action routes to AWS API Gateway which then triggers AWS Lambda Python function which logs the user in to 3rd party site, gets some data and saves it to s3
  3. Once the data is saved, I would like to provide a download button for the data back to the user at the client

I've tried to do this using a 302 redirect in API Gateway both with and without lambda proxy integration so that I could redirect the user to a different webpage that pulls their data from s3.

Using proxy integration I get an Internal Server Error every time.

Without it I just get the json response back to the user instead of an actual redirect.

Here is the python code for the response in my lambda function (this json is what comes back to the user currently instead of taking them to the url https://example.com):

return {
        "isBase64Encoded": False,
        "statusCode": 302,
        "headers": {
            "Location": "https://example.com"
        },
        "multiValueHeaders": {},
        "body": "Success!!!"
    }

I added the "Location" header to the Method Response in API Gateway and mapped it to integration.response.headers.location in the Integration Response (when I tried without lambda proxy).

No success with any of this though.

With proxy its an internal server error that only happens from the html form (doesn't happen when testing in api gateway console or lambda console), and without proxy it doesn't redirect to the value in the Location header, just prints the json to the url of the api.

Any help, guidance or suggestions is much appreciated!

Thanks for your time.

like image 487
libertydawg18 Avatar asked May 03 '26 22:05

libertydawg18


1 Answers

Sharing how I figured this out in case someone else ever runs into a similar issue.

I was getting an Internal Server error when using Lambda Proxy Integration because of the way I was parsing my event variable from API Gateway.

Assuming your API Gateway is configured to Lambda Proxy Integration and that your Lambda function is written in python, the below code should result in a successful 302 Redirect when triggered from a static s3 http form:

import urllib.parse
from furl import furl

def lambda_handler(event, context):

     body = urllib.parse.unquote(event["body"])
     furledBody = furl("/abc?" + body)
     
     parameter1 = furledBody.args["parameter1"]
     parameter2 = furledBody.args["parameter2"]
     parameter3 = furledBody.args["parameter3"]

     #Do stuff with body parameters

     return {
          "isBase64Encoded": False,
          "statusCode": 302,
          "headers": {
               "Location": "https://example.com"
          }
          "multiValueHeaders": {},
          "body": ""
     }

This however is not the design I went with for my use case of providing the data my lambda function downloaded back to the client for the user to download.

Instead I configured my lambda response to contain html that automatically rendered at the client as a response to the http form request. Within the html I include S3 pre-signed URLs that were generated earlier in the lambda:

import boto3
s3 = boto3.client('s3')

presignedURL = s3.generate_presigned_url('get_object',{'Bucket': '[insert bucket name]', 'Key': '[insert key aka file name including the full path]'}, 500, 'GET'}

responseBody = (
    "<html>"
        "<head></head>"
        "<body>"
            "<a href=\"" + presignedURL + "\"download><button>Download</button></a>"
        "</body>"
    "</html>")
    
return {
     "isBase64Encoded": False,
     "statusCode": 200,
     "headers": {
         "Content-Type": "text/html"
     }
     "multiValueHeaders": {},
     "body": responseBody
}
like image 147
libertydawg18 Avatar answered May 06 '26 10:05

libertydawg18



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!