Currently the Serverless framework does not support Lambda@Edge and it might never. The reason is that Lambda@Edge is designed to fit a very unique use case that only interacts with a very limited set of event triggers as well having limited function size and instance size (only 128MB memory instances). It would be cool if the framework could find a way to do it but it’s probably not likely.
Thank you for the reply, I hope it will be supported as I see it as a great possibility, if you are in need of running some simple logic as close to the user as possible it would seem a great fit. I guess I see it more as a contender to scripting in Nginx (but with automatic CDN distribution), than for full fledged business logic, and in that case the current limitations should not be too troubling.
Would it maybe be possible to manually configure CloudFront and Lambda@Edge and use Serverless for controlling API Gateway and other Lambda logic? Or would I need to drop Serverless altogether if using Lambda@Edge?
(For some context, I’m looking into rendering webpages using Lambda, and having CloudFront as cache in front, and would like to use Lambda@Edge for some manipulation of the incoming requests, like country or device detection to serve different results depending on these.)
To be honest, Lambda would be a bad way to run a site from. What is probably a better method is to use S3 to store your HTML, CSS and JS and the JS on that frontend communicates to a Lambda backend via HTTP. S3 buckets can be fed through Cloudfront as well allowing for any manual setting-up of Lambda@Edge if you really need to.
That is pretty much how our current stack works (except our data producing API is not in Lambda). What I’m trying to add in between there is server-side rendering of the HTML. For that part I’m hoping Lambda + Lambda@Edge could be a viable solution
Amazon have said Lambda@Edge is not meant for large workload which is why there are restrictions. At best it is meant to drop in a header into a request and/or response.
@osmestad What client-side rendering can you not do that requires server-side rendering? The solution for us was to invest in use of a client-side framework such as Vue to help “componentise” the different portions of our pages, and each component is now a seperate private node module that then goes through the webpack “compile” process to optimise everything. So far there has been zero need for us to have server-side rendering and we just allow JS on the client-side to request data it needs to finish rendering a page.
@garethmcc An example would be sharing a link from your site on social media sites like Facebook. FB, for instance, looks for the Open Graph meta tags when converting the link to an embedded card (with a photo and all that). I use the Vue Head library to change the meta tags based on which component is loaded, but unfortunately FB’s Open Graph parser doesn’t wait for the page’s JS to complete execution before rendering the embedded card.
@osmestad This is a problem I’m facing now and I am looking into attaching a L@E function to Cloud Front to check the User Agent in the request header and take appropriate action if the request originated from FB (e.g. return tags with appropriate meta data). I haven’t figured how to instruct the L@E function to “continue as normal” (e.g. Cloud Front responds to the request) if the User Agent isn’t FB.
Timely question. Thanks for asking. If I get any further I’ll post it here.
We currently use Cloudformation to deploy our Cloudfront distributions that sit in front of S3. Bundling our lambda@edge functions into a serverless app that includes the Cloudfront distribution would allow us to test & promote our CDN the same way we develop our applications. I would say that is a very valid use case and something relatively simple to implement once Cloudformation supports lambda function associations.
Of course, one could write a plugin that uses the API/SDK for Create/UpdateDistribution to shoehorn the event association in there instead.
My usecase is that I need to secure my S3 bucket and only allow access to it via CloudFormation. To do this, you need your CloudFormation template to reference the bucket’s REST endpoint (rather than the website endpoint). The REST endpoint does not support default documents (e.g. index.html) on subdirectories (e.g. example.com/foo/ will not show the /foo/index.html file from your bucket via the REST endpoint - only via the website endpoint). So, I wrote a Lambda@Edge function attached to the origin request, and if the requested URI ends with / it will append index.html to the request before sending it on to S3.