diff --git a/lib/index.js b/lib/index.js
index 5279ff3..326a298 100644
--- a/lib/index.js
+++ b/lib/index.js
@@ -23,9 +23,11 @@ function connect_dev() {
heartbeat: 10 * 1000
}),
- async (req, res, next) => {
- asset_cache = await watcher.ready;
- next();
+ (req, res, next) => {
+ watcher.ready.then(cache => {
+ asset_cache = cache;
+ next();
+ });
},
set_req_pathname,
@@ -126,7 +128,7 @@ function get_asset_handler(opts) {
}
function get_route_handler(fn) {
- return async function handle_route(req, res, next) {
+ return function handle_route(req, res, next) {
const url = req.pathname;
const { client, server } = fn();
@@ -136,57 +138,66 @@ function get_route_handler(fn) {
'Content-Type': 'text/html'
});
- try {
- for (const route of route_manager.routes) {
- if (route.test(url)) {
- req.params = route.exec(url);
-
- const mod = require(server.entry)[route.id];
-
- if (route.type === 'page') {
- // preload main.js and current route
- // TODO detect other stuff we can preload? images, CSS, fonts?
- res.set('Link', `<${client.main_file}>;rel="preload";as="script", <${client.routes[route.id]}>;rel="preload";as="script"`);
-
- const data = { params: req.params, query: req.query };
-
- if (mod.preload) {
- const promise = Promise.resolve(mod.preload(req)).then(preloaded => {
- Object.assign(data, preloaded);
- return mod.render(data);
- });
-
- await templates.stream(res, 200, {
- main: client.main_file,
- html: promise.then(rendered => rendered.html),
- head: promise.then(({ head }) => `${head}`),
- styles: promise.then(({ css }) => (css && css.code ? `` : ''))
- });
- } else {
- const { html, head, css } = mod.render(data);
-
- const page = templates.render(200, {
- main: client.main_file,
- html,
- head: `${head}`,
- styles: (css && css.code ? `` : '')
- });
-
- res.end(page);
- }
- }
-
- else {
- const handler = mod[req.method.toLowerCase()];
- if (handler) handler(req, res, next);
- }
-
- return;
- }
+ let i = 0;
+ function handle_route_inner() {
+ if (i === route_manager.routes.length) {
+ next();
+ return;
}
- next();
- } catch(err) {
+ const route = route_manager.routes[i];
+
+ if (route.test(url)) {
+ req.params = route.exec(url);
+
+ const mod = require(server.entry)[route.id];
+
+ if (route.type === 'page') {
+ // preload main.js and current route
+ // TODO detect other stuff we can preload? images, CSS, fonts?
+ res.set('Link', `<${client.main_file}>;rel="preload";as="script", <${client.routes[route.id]}>;rel="preload";as="script"`);
+
+ const data = { params: req.params, query: req.query };
+
+ if (mod.preload) {
+ const promise = Promise.resolve(mod.preload(req)).then(preloaded => {
+ Object.assign(data, preloaded);
+ return mod.render(data);
+ });
+
+ return templates.stream(res, 200, {
+ main: client.main_file,
+ html: promise.then(rendered => rendered.html),
+ head: promise.then(({ head }) => `${head}`),
+ styles: promise.then(({ css }) => (css && css.code ? `` : ''))
+ });
+ } else {
+ const { html, head, css } = mod.render(data);
+
+ const page = templates.render(200, {
+ main: client.main_file,
+ html,
+ head: `${head}`,
+ styles: (css && css.code ? `` : '')
+ });
+
+ res.end(page);
+ }
+ }
+
+ else {
+ const handler = mod[req.method.toLowerCase()];
+ if (handler) handler(req, res, next);
+ }
+
+ return;
+ }
+
+ ++i;
+ return handle_route_inner();
+ }
+
+ return Promise.resolve().then(handle_route_inner).catch(err => {
res.status(500);
res.end(templates.render(500, {
title: (err && err.name) || 'Internal server error',
@@ -194,7 +205,7 @@ function get_route_handler(fn) {
error: escape_html(err && (err.details || err.message || err) || 'Unknown error'),
stack: err && err.stack.split('\n').slice(1).join('\n')
}));
- }
+ });
};
}
diff --git a/lib/templates.js b/lib/templates.js
index 34360d1..8260aa8 100644
--- a/lib/templates.js
+++ b/lib/templates.js
@@ -31,10 +31,14 @@ function create_templates() {
return key in data ? data[key] : '';
});
},
- stream: async (res, data) => {
+ stream: (res, data) => {
let i = 0;
- do {
+ function stream_inner() {
+ if (i >= template.length) {
+ return;
+ }
+
const start = template.indexOf('%sapper', i);
if (start === -1) {
@@ -53,9 +57,14 @@ function create_templates() {
const match = /sapper\.(\w+)/.exec(tag);
if (!match || !(match[1] in data)) throw new Error(`Bad template`); // TODO ditto
- res.write(await data[match[1]]);
- i = end + 1;
- } while (i < template.length);
+ return Promise.resolve(data[match[1]]).then(datamatch => {
+ res.write(datamatch);
+ i = end + 1;
+ return stream_inner();
+ });
+ }
+
+ return Promise.resolve().then(stream_inner);
}
};
})