yarbsemaj / sveltekit-adapter-lambda

An adapter to build a SvelteKit app into a lambda ready for deployment with lambda proxy via the Serverless Framework or CDK.
https://www.npmjs.com/package/@yarbsemaj/adapter-lambda
MIT License
77 stars 16 forks source link

Implementing a serverless solution in AWS: Static S3, CloudFront & Lambda #4

Closed Lottike closed 2 years ago

Lottike commented 2 years ago

Hi!

I already have an app that is distributed via CloudFront (from a static S3 bucket). I mostly get data from an API Gateway / Lambda + DynamoDB backend and I format the responses with some javascript on the client side.

But it turns out I'll need some extra server-side rendering functionality. I'm looking if I could use your project in my solution. I already have a set up CI/CD environment, so I'm basically asking how can I figure out which files should go into an S3 bucket and if you have any idea how to set up the SSR via Lambda or Lambda@Edge?

Or is there another solution you'd recommend?

Thanks.

yarbsemaj commented 2 years ago

Hi @Lottike, Thanks for your interest! You could certainly integrate this repo into your existing solution, in fact, I use a setup very similar to yours to host a very simple blog. I'm not sure of your particular circumstance, but here are a few things I would consider;

If neither of these things concern you then I can highly recommend Svelte, it's a really clean, efficient framework.

As for static assets, these really fall into three categories, public files (like any images, fonts, etc), pre-rendered pages (these are static pages that you designate that are rendered as compile-time), and files generated by SvelteKit at build time, these are used to make your site isomorphic, basically, the server renders the first page you visit, but then when a user clicks around your site all subsequent pages are client-side rendered. As for what files specifically, after the build process any files in ./build/assets/ or ./build/prerendered/ should be hosted in S3.

You also mentioned doing the SSR in a lambda@edge, you certainly could as this will improve response time and I thought about this but decided against this for this adapter because;

  1. You can only return response body's up to 1MB (this may be an issue with larger pages)
  2. It's also more costly to run a lambda@edge, about 3x more expensive compared with us-east-1 per GBs
Lottike commented 2 years ago

@yarbsemaj, Thank you for your detailed reply and advice! I really appreciate it.

I've already chosen SvelteKit for my project. The concerns you mentioned are valid, but they don't really worry me. You are also right about lambda@edge. I should reconsider it's role in my project.

I'm really new to the dev world so I'm basically trying to figure out how things work. Here is a test I ran with your adapter:

Firstly, I cloned the example SvelteKit app, by selecting "No" to all the options. Then I followed your instructions to set up your adapter, but some things came up:

  1. Cloning the adapter worked fine, but my config file was named svelte.config.js and your instructions refer to a svelte.config.cjs file. Don't know why the difference is, but thought I should let you know
  2. I also had to do a npm audit -fix --force because some warnings were coming up
  3. Inside the svelte.config.js file I copied the snippet you've provided, but I had to take the following actions:
    • Delete target: '#svelte',
    • Add export default config; at the end of the file
    • Do a npm i svelte-preprocess as it was not pre-installed
  4. After that I did a npm run build and it seems to have worked, but the following warning popped up:

> build/app.js:657:14: warning: This dynamic import will not be bundled because the argument is not a string literal (use "import().catch()" to silence this warning) 657 │ csp_ready = import(name).then((crypto2) => {

The build created the following folders and files in the root directory: assets, chunks, entries, nodes, server, manifest.js, manifest.json

I followed your advice and uploaded the static files from assets to an S3 bucket. Then I hosted it as a static website to test what works, and as expected, the static pages show up, but the todos functionality doesn't work, but the page layout loads.

Also, I checked out the serverless.yml file you've provided, to get a better understanding of the infrastructure, but there are a few things that I don't seem to be able to figure out.

As far as I can see it creates and the following resources:

This gives me a better understanding of the general infrastructure, but leaves me with a couple of important questions:

  1. What do I do with the remaining directories and files from the build: chunks, entries, nodes, manifest.js, manifest.json ?
  2. If I wanted, for example, to have some sort of an application that required a simple login, how would you advise me to protect the routes? Will I be able to use the SvelteKit context=module load() functions to verify an JWT for example before allowing the user to see the page and redirecting them to a login page if the token has expired (or if it isn't present in a cookie)?

Any input would be highly appreciated.

Sorry if some of the details were trivial or useless, but I'm really new and learning, and I thought it might be useful to someone if they were addressed, as there is not much information on the web for this kind of thing atm.

Thank you.

yarbsemaj commented 2 years ago

@Lottike Thank You for spotting my typo on svelte.config.cjs will publish a fix for that now. :) I think the issue around the npm audit are to do with outdated packages that come as part of serverless plugins, as your running this build process away from users that shouldn't be an issue. svelte-preprocess i believe is added to your config is you choose to enable typescript buts it's handy to have for other bits as well.

Your dissection of the serverless.yml file is correct. As for the edge function, the way serverless packages up your app is it makes a zip of all your function code, limited by your package config, it then uses that zip as the basis for all functions, with only the entry point been different.

As for your questions;

  1. those directories are generated by sveltekit as part of building your application, not sure what they do specifically but might be fun to try and reverse engineer.
  2. As for login, i can see some blog posts that looks like good starting places, this one looks to be just what you're after