-
Notifications
You must be signed in to change notification settings - Fork 81
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
RFC for builders #25
RFC for builders #25
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,101 @@ | ||
- Start Date: 2020-06-25 | ||
- RFC PR: | ||
- Svelte Issue: ] | ||
|
||
# Sapper Builders | ||
|
||
## Summary | ||
|
||
This RFC proposes a method of modularising build output from Sapper for ease of deployment across a variety of targets. | ||
|
||
## Motivation | ||
|
||
Sapper's current build output comprises of a series of files: | ||
|
||
1. A build manifest | ||
1. A client bundle | ||
1. A server bundle (in non-exported mode) | ||
1. An (optional) legacy client bundle | ||
1. Static files | ||
|
||
Deploying this is relatively simple, but certainly not optimised for certain deployment strategies such as serverless (lambda), and often relies on third-party, platform-specific builders. | ||
|
||
If Sapper were to produce its output in a more modular fashion, it would facilitate the creation of a number of officially supported "builders" for major platforms, as well as opening the doors for third parties to easily produce builders which targetted other platforms. | ||
|
||
Additionally, it would ease the creation of some desirable features: | ||
|
||
1. Per-route bundle splitting | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @pngwn pointed out that you might want the splitting to happen for both the server-side and client-side code: sveltejs/sapper#1346 (comment) |
||
1. [Differential rendering on a per-route basis](https://github.com/sveltejs/sapper/issues/1324) - Allowing SSR, SSG, SPA, [JAM](https://github.com/sveltejs/sapper/issues/1093), on a per-route basis. | ||
1. [Faster cold-boot time for serverless functions](https://github.com/sveltejs/sapper/issues/356) | ||
1. [SPA Mode](https://github.com/sveltejs/sapper/issues/383) | ||
|
||
It would facilitate easier deployment on some new platforms: | ||
|
||
1. [Azure Functions](https://azure.microsoft.com/en-gb/services/functions) | ||
1. [AWS Lambda](https://aws.amazon.com/lambda/) | ||
1. [Google Cloud Functions](https://cloud.google.com/functions) | ||
1. [IBM Cloud Functions](https://www.ibm.com/uk-en/cloud/functions) | ||
1. [IPFS](https://ipfs.io/) | ||
1. [Begin.com](https://begin.com/) | ||
1. [Netlify](https://www.netlify.com/) | ||
1. [Cloudflare Workers](https://blog.cloudflare.com/introducing-cloudflare-workers/) | ||
1. [Fastly Edge](https://www.fastly.com/products/edge-compute) | ||
|
||
## Detailed design | ||
|
||
> This is the bulk of the RFC. | ||
|
||
> Explain the design in enough detail for somebody | ||
familiar with the framework to understand, and for somebody familiar with the | ||
implementation to implement. This should get into specifics and corner-cases, | ||
and include examples of how the feature is used. Any new terminology should be | ||
defined here. | ||
|
||
* Client-side bundle goes into static dir (SPA) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. When you say "static dir" I'm guessing you mean There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. That is my understanding. There is additional complexity here. We obviously need this information in the server builder as well, but if we are moving towards facilitating 'faas' deployment then we might want to consider greater support for plopping your assets on a CDN, there have been some issues about this in the past. I think this is quite difficult right now, if it is possible at all. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The main difficulty right now that I'm aware of is that the images don't have hashes in their names, so they're not cacheable. I sent a PR to the template to address this: sveltejs/sapper-template#248 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Re "if it is possible at all": Right now I'm deploying my sapper app to a CDN by parsing the routes directly out of manifest source code and generating CDN configuration for it. |
||
* Individual modules built for each route | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. What do you mean by "modules" here? An npm module? Or just a file or collection of files? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think this is the per route code-splitting part, essentially having distinct individually deployable pieces of code for each route. There are benefits to this approach but it might also not be necessary, we'd need to validate. It could be that it becomes more significant over a certain size. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. My instinct here is that there are at least 2 reasons to put things into the same function bundle:
Along these lines, there are at least 2 reasons to put things in different bundles:
|
||
* entrypoint imports individual route modules (for local development + simple `node` deployment) | ||
* `@sapper/[architecture]-builder` packages | ||
* Removing export (an application which has no dynamic routes is automatically SSG) | ||
|
||
Discuss: | ||
|
||
1. How do we determine which routes are: | ||
* SPA (No preload) | ||
* SSG (?) | ||
* Hybrid / SSR (Preload function exists) - current behaviour | ||
|
||
2. Questions around treatment of server routes | ||
|
||
## How we teach this | ||
|
||
> What names and terminology work best for these concepts and why? How is this | ||
idea best presented? As a continuation of existing Svelte patterns, or as a | ||
wholly new one? | ||
|
||
> Would the acceptance of this proposal mean the Svelte guides must be | ||
re-organized or altered? Does it change how Svelte is taught to new users | ||
at any level? | ||
|
||
> How should this feature be introduced and taught to existing Svelte | ||
users? | ||
|
||
To define: | ||
|
||
SSG: Server-side generated pages | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Should this be statically generated? (i.e. at compile time) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Is this leaning towards https://nextjs.org/blog/next-9-5#stable-incremental-static-regeneration ? |
||
SPA: Single-page App | ||
SSR: Server-side Rendering | ||
|
||
## Drawbacks | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. One of the major questions this might raise is whether to keep support Webpack. Depending on the implementation, we may decide it's not worth implementing for Webpack (at least until someone from the community contributes a new Webpack implemention) I think about 2/3 of our users use Rollup based on the numbers from the plugins: There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I would ditch webpack entirely. We don't have the resource to support multiple bundlers, and 5 is probably different enough to require a re-implementation anyway. Rollup is fast becoming the preferred choice for other projects anyway, and we have a distinct advantage in having a certain project author on our team. I am very much in favour of abstracting the build, I wouldn't build it for any specific bundler, but I also wouldn't go too deep in abstracting it. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I am in favor of only focusing on rollup in the near-term, although I don't think we should allow any rollup-specific abstractions into the core algorithms of this stuff. This will: reduce the total amount of knowledge someone will need to understand the core algorithms, insulate us from changes to rollup, and make it easier to support other bundlers |
||
|
||
This approach provides many benefits, however one potential drawback is the additional complexity of moving from a two-bundle, encapsulated deployment, served up by a single javascript file `node /__sapper__/build/index.js` into a collection of files relating to routes. It's important that a builder exists (and is possibly the default) for running the simplest possible instance of the app, with just node and a http server installed. | ||
|
||
## Alternatives | ||
|
||
NextJS [already has a solution for this](https://github.com/vercel/next.js/issues/9524), borne of a constraint in the architecture, however it has proven itself as a highly desirable feature. We can draw inspiration from the way they have addressed this problem. It's also worth noting that their problem is understandably very targetted to users hosting on their own Vercel platform, whereas the Sapper solution should consider a range of platforms. | ||
|
||
Builders are a feature that Vercel uses quite heavily. However they can be quite complicated due to the abstraction they work over (such as serving serverless GO, PHP, etc). Since we control the input, Sapper builders should be a simple mapping excercise in most cases. | ||
|
||
## Unresolved questions | ||
|
||
> Optional, but suggested for first drafts. What parts of the design are still | ||
TBD? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
One way to think about this is that there should be no
__sapper__/build/index.js
.Instead, we should emit enough information for someone to run a completely separate tool against the sapper build output. Something like
sapper serve ...
This command would read the routes from the given directory and serve them directly. This would also make it straightforward for others to write deploy commands that can package things up for various hosting providers.