1 | var Page = require('./Page');
|
2 | var util = require('racer/lib/util');
|
3 | var contexts = require('derby-templates').contexts;
|
4 |
|
5 | Page.prototype.render = function(status, ns) {
|
6 | if (typeof status !== 'number') {
|
7 | ns = status;
|
8 | status = null;
|
9 | }
|
10 | this.app.emit('render', this);
|
11 |
|
12 | if (status) this.res.statusCode = status;
|
13 |
|
14 |
|
15 | this.res.setHeader('Cache-Control', 'no-store');
|
16 |
|
17 | if (!this.res.getHeader('Content-Type')) {
|
18 | this.res.setHeader('Content-Type', 'text/html; charset=utf-8');
|
19 | }
|
20 |
|
21 | this._setRenderParams(ns);
|
22 | var pageHtml = this.get('Page', ns);
|
23 | this.res.write(pageHtml);
|
24 |
|
25 | var bundleScriptTag = '<script async data-derby-app src="' + this.app.scriptUrl + '"';
|
26 | if (this.app.scriptCrossOrigin) {
|
27 |
|
28 |
|
29 |
|
30 |
|
31 |
|
32 |
|
33 |
|
34 |
|
35 | bundleScriptTag += ' crossorigin';
|
36 | }
|
37 | bundleScriptTag += '></script>';
|
38 | this.res.write(bundleScriptTag);
|
39 |
|
40 | this.res.write('<script type="application/json">');
|
41 | var tailHtml = this.get('Tail', ns);
|
42 |
|
43 | this.model.destroy('$components');
|
44 |
|
45 | var page = this;
|
46 | this.model.bundle(function(err, bundle) {
|
47 | if (page.model.hasErrored) return;
|
48 | if (err) return page.emit('error', err);
|
49 | var json = stringifyBundle(bundle);
|
50 | page.res.write(json);
|
51 | page.res.end('</script>' + tailHtml);
|
52 | page.app.emit('routeDone', page, 'render');
|
53 | });
|
54 | };
|
55 |
|
56 | Page.prototype.renderStatic = function(status, ns) {
|
57 | if (typeof status !== 'number') {
|
58 | ns = status;
|
59 | status = null;
|
60 | }
|
61 | this.app.emit('renderStatic', this);
|
62 |
|
63 | if (status) this.res.statusCode = status;
|
64 | this.params = pageParams(this.req);
|
65 | this._setRenderParams(ns);
|
66 | var pageHtml = this.get('Page', ns);
|
67 | var tailHtml = this.get('Tail', ns);
|
68 | this.res.send(pageHtml + tailHtml);
|
69 | this.app.emit('routeDone', this, 'renderStatic');
|
70 | };
|
71 |
|
72 |
|
73 | Page.prototype._addListeners = function() {};
|
74 |
|
75 | function stringifyBundle(bundle) {
|
76 | var json = JSON.stringify(bundle);
|
77 | return json.replace(/<[\/!]/g, function(match) {
|
78 |
|
79 |
|
80 | if (match === '</') return '<\\/';
|
81 |
|
82 |
|
83 | if (match === '<!') return '<\\u0021';
|
84 | throw new Error('Unexpected match when escaping JSON');
|
85 | });
|
86 | }
|
87 |
|
88 |
|
89 | function pageParams(req) {
|
90 | var params = {
|
91 | url: req.url
|
92 | , body: req.body
|
93 | , query: req.query
|
94 | };
|
95 | for (var key in req.params) {
|
96 | params[key] = req.params[key];
|
97 | }
|
98 | return params;
|
99 | }
|