Overcoming Same-Origin with AWS Lambda

Posted on

AWS Lambda just makes it sooo easy to do miniscule bits of server-side lifting that cannot be avoided.

Here’s my situation: I’ve deployed a one-page JS/HTML website on an S3 bucket. The site requires a “live” feed to Instagram, which we can satisfy by using this Instagram hidden-in-plain-sight JSON endpoint (actual account redacted from link).

However… it’s not surprising that Instagram doesn’t set an Access-Control-Allow-Origin=* header on this resource. Therefore I can’t pull it using AJAX from the webpage, at least in modern browsers like Chrome.

We need a server-side solution to retrieve this, and it clearly isn’t efficient to spin up a new EC2 instance, etc, just to provide this capability. Nor did I want to re-use an existing instance to perform this (I want minimum coupling between my projects).

Enter AWS Lambda; tightly coupled dead-simple backend for minimal cost. Beyond writing the code to retrieve the Instagram endpoint JSON content, there were two ways we could integrate:

  1. Connect Lambda to API Gateway and turn it into a web service, or
  2. Write the file to an S3 bucket (then set relevant S3 ACL or IAM permissions)

Bearing in mind our one-page site is hosted in an S3 bucket anyway, option #2 is a cheaper and more appropriate choice. Here’s what the Lambda function looks like (Node.js 4.3):

You’ll want to create a new IAM role to execute this function with. That role would need to have S3 write permissions to the bucket of your choosing. Additionally, if creating your own role via the IAM console, ensure that you’ve added “lambda.amazonaws.com” as a trusted entity.


Coupled with a custom Lambda event, you could turn this function into a generic workhorse by parameterising the Instagram endpoint, bucket name, key, etc.