Slot-based routing (#573)

This commit is contained in:
Rich Harris
2019-02-21 16:34:07 -05:00
committed by GitHub
parent c637687922
commit e0de230e13
22 changed files with 141 additions and 99 deletions

View File

@@ -3,7 +3,7 @@ import * as path from 'path';
import { posixify, stringify, walk, write_if_changed } from '../utils';
import { Page, PageComponent, ManifestData } from '../interfaces';
export function create_main_manifests({
export function create_app({
bundler,
manifest_data,
dev_port,
@@ -31,8 +31,11 @@ export function create_main_manifests({
const client_manifest = generate_client_manifest(manifest_data, path_to_routes, bundler, dev, dev_port);
const server_manifest = generate_server_manifest(manifest_data, path_to_routes, cwd, src, dest, dev);
const app = generate_app(manifest_data, path_to_routes);
write_if_changed(`${output}/internal/manifest-client.mjs`, client_manifest);
write_if_changed(`${output}/internal/manifest-server.mjs`, server_manifest);
write_if_changed(`${output}/internal/App.svelte`, app);
}
export function create_serviceworker_manifest({ manifest_data, output, client_files, static_files }: {
@@ -230,6 +233,58 @@ function generate_server_manifest(
`.replace(/^\t{2}/gm, '').trim();
}
function generate_app(manifest_data: ManifestData, path_to_routes: string) {
// TODO remove default layout altogether
const max_depth = Math.max(...manifest_data.pages.map(page => page.parts.filter(Boolean).length));
const levels = [];
for (let i = 0; i < max_depth; i += 1) {
levels.push(i + 1);
}
let l = max_depth;
let pyramid = `<svelte:component this={level${l}.component} {...level${l}.props}/>`;
while (l-- > 1) {
pyramid = `
<svelte:component this={level${l}.component} segment={segments[${l}]} {...level${l}.props}>
{#if level${l + 1}}
${pyramid.replace(/\n/g, '\n\t\t\t\t\t')}
{/if}
</svelte:component>
`.replace(/^\t\t\t/gm, '').trim();
}
return `
<!-- This file is generated by Sapper — do not edit it! -->
<script>
import { setContext } from 'svelte';
import { CONTEXT_KEY } from './shared';
import Layout from '${get_file(path_to_routes, manifest_data.root)}';
import Error from '${get_file(path_to_routes, manifest_data.error)}';
export let session;
export let error;
export let status;
export let segments;
export let level0;
${levels.map(l => `export let level${l} = null;`).join('\n\t\t\t')}
setContext(CONTEXT_KEY, session);
</script>
<Layout segment={segments[0]} {...level0.props}>
{#if error}
<Error {error} {status}/>
{:else}
${pyramid.replace(/\n/g, '\n\t\t\t\t')}
{/if}
</Layout>
`.replace(/^\t\t/gm, '').trim();
}
function get_file(path_to_routes: string, component: PageComponent) {
if (component.default) return `./${component.type}.svelte`;
return posixify(`${path_to_routes}/${component.file}`);