slower 2.1.6 → 2.1.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/decorators.js +69 -57
- package/src/slower.js +1 -0
package/package.json
CHANGED
package/src/decorators.js
CHANGED
|
@@ -4,14 +4,14 @@ const utils = require('./utils');
|
|
|
4
4
|
|
|
5
5
|
/**
|
|
6
6
|
* Receives and configures the HTTP Response object
|
|
7
|
-
* @param {http.ServerResponse} response
|
|
8
|
-
* @returns {http.ServerResponse}
|
|
7
|
+
* @param {http.ServerResponse} response
|
|
8
|
+
* @returns {http.ServerResponse}
|
|
9
9
|
* @exposes .status()
|
|
10
10
|
* @exposes .send()
|
|
11
11
|
* @exposes .json()
|
|
12
12
|
* @exposes .file()
|
|
13
13
|
*/
|
|
14
|
-
function setupResponse
|
|
14
|
+
function setupResponse(response) {
|
|
15
15
|
/**
|
|
16
16
|
* Sets the response status code
|
|
17
17
|
* @chainable
|
|
@@ -27,10 +27,10 @@ function setupResponse (response) {
|
|
|
27
27
|
* Sets a response header to a specified value
|
|
28
28
|
* @chainable
|
|
29
29
|
* @overload
|
|
30
|
-
* @param {string} header
|
|
31
|
-
* @param {string} value
|
|
30
|
+
* @param {string} header
|
|
31
|
+
* @param {string} value
|
|
32
32
|
* @returns {http.ServerResponse}
|
|
33
|
-
* @info Pass in an object of "header":"value" entries
|
|
33
|
+
* @info Pass in an object of "header":"value" entries
|
|
34
34
|
* to set multiple headers at once
|
|
35
35
|
* @example
|
|
36
36
|
* res.set('Content-Length', 1000)
|
|
@@ -45,22 +45,19 @@ function setupResponse (response) {
|
|
|
45
45
|
* res.set({ 'Content-Length':1000, 'Content-Type':'text/plain' })
|
|
46
46
|
*/
|
|
47
47
|
response.set = function (header, value) {
|
|
48
|
-
if (typeof header === 'string')
|
|
49
|
-
|
|
50
|
-
else
|
|
51
|
-
for (let prop of header)
|
|
52
|
-
response.setHeader(prop, header[prop]);
|
|
48
|
+
if (typeof header === 'string') response.setHeader(header, value);
|
|
49
|
+
else for (let prop of header) response.setHeader(prop, header[prop]);
|
|
53
50
|
return response;
|
|
54
|
-
}
|
|
51
|
+
};
|
|
55
52
|
|
|
56
53
|
/**
|
|
57
54
|
* An alias for 'res.getHeader()'.
|
|
58
|
-
* @param {string} header
|
|
55
|
+
* @param {string} header
|
|
59
56
|
* @returns {string}
|
|
60
57
|
*/
|
|
61
|
-
response.get = function(header) {
|
|
58
|
+
response.get = function (header) {
|
|
62
59
|
return response.getHeader(header);
|
|
63
|
-
}
|
|
60
|
+
};
|
|
64
61
|
|
|
65
62
|
/**
|
|
66
63
|
* Sets the Content-Type header with a specific MIME type.
|
|
@@ -70,32 +67,36 @@ function setupResponse (response) {
|
|
|
70
67
|
* @info And if no type is specified, binary type is used (application/octet-stream)
|
|
71
68
|
*/
|
|
72
69
|
response.type = function (mime) {
|
|
73
|
-
let mimetype =
|
|
70
|
+
let mimetype =
|
|
71
|
+
MIME_TABLE[mime] ||
|
|
72
|
+
mime ||
|
|
73
|
+
MIME_TABLE[extension] ||
|
|
74
|
+
MIME_TABLE['default'];
|
|
74
75
|
response.setHeader('Content-type', mimetype);
|
|
75
76
|
return response;
|
|
76
|
-
}
|
|
77
|
+
};
|
|
77
78
|
|
|
78
79
|
/**
|
|
79
80
|
* Sends a string or buffer as JSON and ends the response
|
|
80
|
-
* @param {string|Buffer} data
|
|
81
|
+
* @param {string|Buffer} data
|
|
81
82
|
* @returns {undefined}
|
|
82
83
|
*/
|
|
83
|
-
response.json = function json
|
|
84
|
+
response.json = function json(data) {
|
|
84
85
|
if (response.statusCode === undefined) response.status(200);
|
|
85
86
|
response.setHeader('Content-type', 'application/json');
|
|
86
87
|
response.write(JSON.stringify(data));
|
|
87
88
|
response.end();
|
|
88
89
|
return undefined;
|
|
89
|
-
}
|
|
90
|
+
};
|
|
90
91
|
|
|
91
92
|
/**
|
|
92
93
|
* Sends a string or buffer as HTML data and ends the response
|
|
93
|
-
* @param {string|Buffer} data
|
|
94
|
+
* @param {string|Buffer} data
|
|
94
95
|
* @returns {undefined}
|
|
95
96
|
*/
|
|
96
97
|
response.send = function (data) {
|
|
97
98
|
if (response.statusCode === undefined) response.status(200);
|
|
98
|
-
if (!response.getHeader('Content-Type'))
|
|
99
|
+
if (!response.getHeader('Content-Type'))
|
|
99
100
|
response.setHeader('Content-Type', 'text/html');
|
|
100
101
|
response.write(data);
|
|
101
102
|
response.end();
|
|
@@ -110,41 +111,46 @@ function setupResponse (response) {
|
|
|
110
111
|
response.file = function (filename) {
|
|
111
112
|
if (response.statusCode === undefined) response.status(200);
|
|
112
113
|
if (!response.getHeader('Content-Type')) {
|
|
113
|
-
let extension = (filename||'').split('.').slice(-1)[0];
|
|
114
|
-
response.setHeader(
|
|
114
|
+
let extension = (filename || '').split('.').slice(-1)[0];
|
|
115
|
+
response.setHeader(
|
|
116
|
+
'Content-Type',
|
|
117
|
+
MIME_TABLE[extension] || MIME_TABLE['default']
|
|
118
|
+
);
|
|
115
119
|
}
|
|
116
120
|
const stream = fs.createReadStream(filename);
|
|
117
121
|
stream.pipe(response);
|
|
118
122
|
return undefined;
|
|
119
|
-
}
|
|
123
|
+
};
|
|
120
124
|
|
|
121
125
|
/**
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
126
|
+
* Renders an HTML document and sends it to client
|
|
127
|
+
* @param {string} filename The file to use as rendering View
|
|
128
|
+
* @param {object} locals The properties to replace in the View
|
|
129
|
+
* @info The locals object may contain either strings or functions or objects with 'toString' method.
|
|
130
|
+
* @returns {undefined}
|
|
131
|
+
* @example
|
|
132
|
+
* // In 'home.html:
|
|
133
|
+
* <h2>{{user}}</h2> has <h2>{{count}}</h2> items
|
|
134
|
+
* // In server.js: (generates a new random item for each request)
|
|
135
|
+
* res.render('./views/home.html', { user: 'Mike', count: () => randomInt() });
|
|
136
|
+
*/
|
|
133
137
|
response.render = function (filename, locals = {}) {
|
|
134
138
|
let html = fs.readFileSync(filename, 'utf-8');
|
|
135
139
|
for (let item in locals) {
|
|
136
140
|
html = html.replace(
|
|
137
|
-
new RegExp('{{'+item+'}}', 'gim'),
|
|
138
|
-
typeof locals[item] === 'function'
|
|
139
|
-
|
|
141
|
+
new RegExp('{{' + item + '}}', 'gim'),
|
|
142
|
+
typeof locals[item] === 'function'
|
|
143
|
+
? locals[item]()
|
|
144
|
+
: locals[item]?.toString() || ''
|
|
140
145
|
);
|
|
141
146
|
}
|
|
142
|
-
response.
|
|
147
|
+
if (!response.getHeader('Content-Type'))
|
|
148
|
+
response.setHeader('Content-type', 'text/html');
|
|
143
149
|
response.write(html);
|
|
144
150
|
response.end();
|
|
145
151
|
return undefined;
|
|
146
|
-
}
|
|
147
|
-
|
|
152
|
+
};
|
|
153
|
+
|
|
148
154
|
/**
|
|
149
155
|
* Sets the 'Location' header and redirects to a given path, URL, or link.
|
|
150
156
|
* @param {string} location An URL, link, path, or the string 'back' to set the target
|
|
@@ -160,47 +166,53 @@ function setupResponse (response) {
|
|
|
160
166
|
* res.status(300).redirect('http://example.com');
|
|
161
167
|
*/
|
|
162
168
|
response.redirect = function (location) {
|
|
163
|
-
response.setHeader(
|
|
169
|
+
response.setHeader(
|
|
170
|
+
'Location',
|
|
171
|
+
location === 'back'
|
|
172
|
+
? request.getHeader('Referrer')
|
|
173
|
+
: location || '/'
|
|
174
|
+
);
|
|
164
175
|
response.end();
|
|
165
176
|
return undefined;
|
|
166
|
-
}
|
|
167
|
-
|
|
177
|
+
};
|
|
168
178
|
|
|
169
179
|
return response;
|
|
170
180
|
}
|
|
171
181
|
|
|
172
182
|
/**
|
|
173
183
|
* Receives and configures the HTTP Request object
|
|
174
|
-
* @param {http.IncomingMessage} request
|
|
184
|
+
* @param {http.IncomingMessage} request
|
|
175
185
|
* @returns {http.IncomingMessage}
|
|
176
186
|
* @exposes req.body
|
|
177
187
|
* @exposes req.urlParts
|
|
178
188
|
* @exposes req.query
|
|
179
189
|
* @exposes req.session = { port, rport, host, rhost }
|
|
180
190
|
*/
|
|
181
|
-
function setupRequest
|
|
191
|
+
function setupRequest(request) {
|
|
182
192
|
/**
|
|
183
193
|
* @property
|
|
184
194
|
* Holds the request body data as a buffer
|
|
185
195
|
*/
|
|
186
|
-
return new Promise
|
|
196
|
+
return new Promise(resolve => {
|
|
187
197
|
// Set classical socket locals
|
|
188
198
|
request.session = {
|
|
189
199
|
port: request.socket.localPort,
|
|
190
200
|
rport: request.socket.remotePort,
|
|
191
201
|
host: utils.normalizeAddress(request.socket.localAddress),
|
|
192
|
-
rhost: utils.normalizeAddress(request.socket.remoteAddress)
|
|
202
|
+
rhost: utils.normalizeAddress(request.socket.remoteAddress),
|
|
193
203
|
};
|
|
194
204
|
|
|
195
|
-
|
|
205
|
+
// Set express-compatible locals
|
|
206
|
+
request.ip = request.session.rhost;
|
|
207
|
+
|
|
196
208
|
/**
|
|
197
209
|
* An alias for 'req.getHeader()'.
|
|
198
|
-
* @param {string} header
|
|
210
|
+
* @param {string} header
|
|
199
211
|
* @returns {string}
|
|
200
212
|
*/
|
|
201
|
-
request.get = function(header) {
|
|
213
|
+
request.get = function (header) {
|
|
202
214
|
return request.getHeader(header);
|
|
203
|
-
}
|
|
215
|
+
};
|
|
204
216
|
|
|
205
217
|
// Add req.params placeholder, it is added in the main router, not here
|
|
206
218
|
request.params = undefined;
|
|
@@ -212,17 +224,17 @@ function setupRequest (request) {
|
|
|
212
224
|
request.body = [];
|
|
213
225
|
request.on('timeout', () => reject(new Error('Timeout')));
|
|
214
226
|
request.on('data', chunk => request.body.push(chunk));
|
|
215
|
-
request.on('error',
|
|
227
|
+
request.on('error', err => reject(err));
|
|
216
228
|
request.on('end', () => {
|
|
217
229
|
let tmp = Buffer.concat(request.body);
|
|
218
230
|
request.body = {
|
|
219
231
|
buffer: tmp,
|
|
220
232
|
text: () => tmp.toString(),
|
|
221
|
-
json: () => JSON.parse(tmp)
|
|
222
|
-
}
|
|
233
|
+
json: () => JSON.parse(tmp),
|
|
234
|
+
};
|
|
223
235
|
return resolve(request);
|
|
224
236
|
});
|
|
225
237
|
});
|
|
226
238
|
}
|
|
227
239
|
|
|
228
|
-
module.exports = { setupRequest, setupResponse };
|
|
240
|
+
module.exports = { setupRequest, setupResponse };
|