hono 0.2.0 → 0.2.4
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/README.md +25 -20
- package/dist/context.d.ts +3 -2
- package/dist/context.js +32 -21
- package/dist/hono.d.ts +0 -1
- package/dist/hono.js +16 -3
- package/dist/middleware/body-parse/body-parse.d.ts +5 -0
- package/dist/middleware/cookie/cookie.d.ts +3 -1
- package/dist/middleware/cookie/cookie.js +27 -7
- package/dist/middleware/cors/cors.js +2 -0
- package/dist/middleware/default.js +0 -11
- package/dist/middleware/mustache/mustache.d.ts +2 -0
- package/dist/middleware/mustache/mustache.js +48 -0
- package/dist/middleware/serve-static/serve-static.d.ts +6 -0
- package/dist/middleware/serve-static/serve-static.js +44 -0
- package/dist/middleware.d.ts +5 -0
- package/dist/middleware.js +6 -0
- package/dist/utils/cloudflare.d.ts +1 -0
- package/dist/utils/cloudflare.js +23 -0
- package/dist/utils/mime.d.ts +1 -0
- package/dist/utils/mime.js +92 -0
- package/package.json +3 -1
package/README.md
CHANGED
|
@@ -23,12 +23,12 @@ app.fire()
|
|
|
23
23
|
**Hono is fastest** compared to other routers for Cloudflare Workers.
|
|
24
24
|
|
|
25
25
|
```plain
|
|
26
|
-
hono x
|
|
27
|
-
itty-router x
|
|
28
|
-
sunder x
|
|
29
|
-
worktop x
|
|
26
|
+
hono x 708,671 ops/sec ±2.58% (58 runs sampled)
|
|
27
|
+
itty-router x 159,610 ops/sec ±2.86% (87 runs sampled)
|
|
28
|
+
sunder x 322,846 ops/sec ±2.24% (86 runs sampled)
|
|
29
|
+
worktop x 223,625 ops/sec ±2.01% (95 runs sampled)
|
|
30
30
|
Fastest is hono
|
|
31
|
-
✨ Done in
|
|
31
|
+
✨ Done in 57.83s.
|
|
32
32
|
```
|
|
33
33
|
|
|
34
34
|
## Hono in 1 minute
|
|
@@ -114,6 +114,16 @@ app
|
|
|
114
114
|
.put(() => {...})
|
|
115
115
|
```
|
|
116
116
|
|
|
117
|
+
### Custom 404 Response
|
|
118
|
+
|
|
119
|
+
You can customize 404 Not Found response:
|
|
120
|
+
|
|
121
|
+
```js
|
|
122
|
+
app.get('*', (c) => {
|
|
123
|
+
return c.text('Custom 404 Error', 404)
|
|
124
|
+
})
|
|
125
|
+
```
|
|
126
|
+
|
|
117
127
|
## async/await
|
|
118
128
|
|
|
119
129
|
```js
|
|
@@ -165,19 +175,6 @@ app.use('/message/*', async (c, next) => {
|
|
|
165
175
|
app.get('/message/hello', (c) => c.text('Hello Middleware!'))
|
|
166
176
|
```
|
|
167
177
|
|
|
168
|
-
### Custom 404 Response
|
|
169
|
-
|
|
170
|
-
You can customize 404 Not Found response:
|
|
171
|
-
|
|
172
|
-
```js
|
|
173
|
-
app.use('*', async (c, next) => {
|
|
174
|
-
await next()
|
|
175
|
-
if (c.res.status === 404) {
|
|
176
|
-
c.res = new Response('Custom 404 Not Found', { status: 404 })
|
|
177
|
-
}
|
|
178
|
-
})
|
|
179
|
-
```
|
|
180
|
-
|
|
181
178
|
### Handling Error
|
|
182
179
|
|
|
183
180
|
```js
|
|
@@ -186,7 +183,7 @@ app.use('*', async (c, next) => {
|
|
|
186
183
|
await next()
|
|
187
184
|
} catch (err) {
|
|
188
185
|
console.error(`${err}`)
|
|
189
|
-
c.res =
|
|
186
|
+
c.res = c.text('Custom Error Message', { status: 500 })
|
|
190
187
|
}
|
|
191
188
|
})
|
|
192
189
|
```
|
|
@@ -252,7 +249,9 @@ app.get('/welcome', (c) => {
|
|
|
252
249
|
c.header('Content-Type', 'text/plain')
|
|
253
250
|
c.status(201)
|
|
254
251
|
c.statusText('201 Content Created')
|
|
252
|
+
|
|
255
253
|
return c.body('Thank you for comming')
|
|
254
|
+
|
|
256
255
|
/*
|
|
257
256
|
Same as:
|
|
258
257
|
return new Response('Thank you for comming', {
|
|
@@ -260,7 +259,8 @@ app.get('/welcome', (c) => {
|
|
|
260
259
|
statusText: '201 Content Created',
|
|
261
260
|
headers: {
|
|
262
261
|
'X-Message': 'Hello',
|
|
263
|
-
'Content-Type': 'text/plain'
|
|
262
|
+
'Content-Type': 'text/plain',
|
|
263
|
+
'Content-Length: '22'
|
|
264
264
|
}
|
|
265
265
|
})
|
|
266
266
|
*/
|
|
@@ -358,6 +358,11 @@ export default {
|
|
|
358
358
|
return app.fetch(request, env, event)
|
|
359
359
|
},
|
|
360
360
|
}
|
|
361
|
+
|
|
362
|
+
/*
|
|
363
|
+
or just do this:
|
|
364
|
+
export default app
|
|
365
|
+
*/
|
|
361
366
|
```
|
|
362
367
|
|
|
363
368
|
## Cloudflare Workers with Hono
|
package/dist/context.d.ts
CHANGED
|
@@ -12,7 +12,7 @@ export declare class Context {
|
|
|
12
12
|
private _headers;
|
|
13
13
|
private _status;
|
|
14
14
|
private _statusText;
|
|
15
|
-
|
|
15
|
+
render: (template: string, params?: object, options?: object) => Promise<Response>;
|
|
16
16
|
constructor(req: Request, opts?: {
|
|
17
17
|
res: Response;
|
|
18
18
|
env: Env;
|
|
@@ -21,7 +21,8 @@ export declare class Context {
|
|
|
21
21
|
header(name: string, value: string): void;
|
|
22
22
|
status(number: number): void;
|
|
23
23
|
statusText(text: string): void;
|
|
24
|
-
newResponse(
|
|
24
|
+
newResponse(data: any, init?: ResponseInit): Response;
|
|
25
|
+
body(data: any, status?: number, headers?: Headers): Response;
|
|
25
26
|
text(text: string, status?: number, headers?: Headers): Response;
|
|
26
27
|
json(object: object, status?: number, headers?: Headers): Response;
|
|
27
28
|
html(html: string, status?: number, headers?: Headers): Response;
|
package/dist/context.js
CHANGED
|
@@ -11,7 +11,6 @@ class Context {
|
|
|
11
11
|
this.event = opts.event;
|
|
12
12
|
}
|
|
13
13
|
this._headers = {};
|
|
14
|
-
this.body = this.newResponse;
|
|
15
14
|
}
|
|
16
15
|
header(name, value) {
|
|
17
16
|
this._headers[name] = value;
|
|
@@ -22,42 +21,54 @@ class Context {
|
|
|
22
21
|
statusText(text) {
|
|
23
22
|
this._statusText = text;
|
|
24
23
|
}
|
|
25
|
-
newResponse(
|
|
26
|
-
init.status =
|
|
27
|
-
init.statusText =
|
|
28
|
-
init.headers = Object.assign(Object.assign({},
|
|
29
|
-
|
|
24
|
+
newResponse(data, init = {}) {
|
|
25
|
+
init.status = init.status || this._status;
|
|
26
|
+
init.statusText = init.statusText || this._statusText;
|
|
27
|
+
init.headers = Object.assign(Object.assign({}, this._headers), init.headers);
|
|
28
|
+
// Content-Length
|
|
29
|
+
let length = 0;
|
|
30
|
+
if (data) {
|
|
31
|
+
if (data instanceof ArrayBuffer) {
|
|
32
|
+
length = data.byteLength;
|
|
33
|
+
}
|
|
34
|
+
else if (typeof data == 'string') {
|
|
35
|
+
const Encoder = new TextEncoder();
|
|
36
|
+
length = Encoder.encode(data).byteLength || 0;
|
|
37
|
+
}
|
|
38
|
+
else {
|
|
39
|
+
length = data.bytelength;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
init.headers = Object.assign(Object.assign({}, init.headers), { 'Content-Length': length.toString() });
|
|
43
|
+
return new Response(data, init);
|
|
30
44
|
}
|
|
31
|
-
|
|
45
|
+
body(data, status = this._status, headers = this._headers) {
|
|
46
|
+
return this.newResponse(data, {
|
|
47
|
+
status: status,
|
|
48
|
+
headers: headers,
|
|
49
|
+
});
|
|
50
|
+
}
|
|
51
|
+
text(text, status = this._status, headers = {}) {
|
|
32
52
|
if (typeof text !== 'string') {
|
|
33
53
|
throw new TypeError('text method arg must be a string!');
|
|
34
54
|
}
|
|
35
55
|
headers['Content-Type'] = 'text/plain';
|
|
36
|
-
return this.
|
|
37
|
-
status: status,
|
|
38
|
-
headers: headers,
|
|
39
|
-
});
|
|
56
|
+
return this.body(text, status, headers);
|
|
40
57
|
}
|
|
41
|
-
json(object, status =
|
|
58
|
+
json(object, status = this._status, headers = {}) {
|
|
42
59
|
if (typeof object !== 'object') {
|
|
43
60
|
throw new TypeError('json method arg must be a object!');
|
|
44
61
|
}
|
|
45
62
|
const body = JSON.stringify(object);
|
|
46
63
|
headers['Content-Type'] = 'application/json; charset=UTF-8';
|
|
47
|
-
return this.
|
|
48
|
-
status: status,
|
|
49
|
-
headers: headers,
|
|
50
|
-
});
|
|
64
|
+
return this.body(body, status, headers);
|
|
51
65
|
}
|
|
52
|
-
html(html, status =
|
|
66
|
+
html(html, status = this._status, headers = {}) {
|
|
53
67
|
if (typeof html !== 'string') {
|
|
54
68
|
throw new TypeError('html method arg must be a string!');
|
|
55
69
|
}
|
|
56
70
|
headers['Content-Type'] = 'text/html; charset=UTF-8';
|
|
57
|
-
return this.
|
|
58
|
-
status: status,
|
|
59
|
-
headers: headers,
|
|
60
|
-
});
|
|
71
|
+
return this.body(html, status, headers);
|
|
61
72
|
}
|
|
62
73
|
redirect(location, status = 302) {
|
|
63
74
|
if (typeof location !== 'string') {
|
package/dist/hono.d.ts
CHANGED
package/dist/hono.js
CHANGED
|
@@ -48,6 +48,7 @@ class Hono {
|
|
|
48
48
|
return this.addRoute('patch', arg, ...args);
|
|
49
49
|
}
|
|
50
50
|
/*
|
|
51
|
+
We may implement these HTTP methods:
|
|
51
52
|
trace
|
|
52
53
|
copy
|
|
53
54
|
lock
|
|
@@ -137,11 +138,23 @@ class Hono {
|
|
|
137
138
|
});
|
|
138
139
|
}
|
|
139
140
|
onError(err) {
|
|
140
|
-
console.error(err);
|
|
141
|
-
|
|
141
|
+
console.error(`${err}`);
|
|
142
|
+
const message = 'Internal Server Error';
|
|
143
|
+
return new Response(message, {
|
|
144
|
+
status: 500,
|
|
145
|
+
headers: {
|
|
146
|
+
'Content-Length': message.length.toString(),
|
|
147
|
+
},
|
|
148
|
+
});
|
|
142
149
|
}
|
|
143
150
|
notFound() {
|
|
144
|
-
|
|
151
|
+
const message = 'Not Found';
|
|
152
|
+
return new Response('Not Found', {
|
|
153
|
+
status: 404,
|
|
154
|
+
headers: {
|
|
155
|
+
'Content-Length': message.length.toString(),
|
|
156
|
+
},
|
|
157
|
+
});
|
|
145
158
|
}
|
|
146
159
|
}
|
|
147
160
|
exports.Hono = Hono;
|
|
@@ -9,12 +9,11 @@ const cookie = () => {
|
|
|
9
9
|
const value = obj[name];
|
|
10
10
|
return value;
|
|
11
11
|
};
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
const cookie = serialize(name, value);
|
|
16
|
-
c.res.headers.set('Set-Cookie', cookie);
|
|
12
|
+
c.cookie = (name, value, opt) => {
|
|
13
|
+
const cookie = serialize(name, value, opt);
|
|
14
|
+
c.header('Set-Cookie', cookie);
|
|
17
15
|
};
|
|
16
|
+
await next();
|
|
18
17
|
};
|
|
19
18
|
};
|
|
20
19
|
exports.cookie = cookie;
|
|
@@ -27,8 +26,29 @@ const parse = (cookie) => {
|
|
|
27
26
|
}
|
|
28
27
|
return parsedCookie;
|
|
29
28
|
};
|
|
30
|
-
const serialize = (name, value,
|
|
29
|
+
const serialize = (name, value, opt = {}) => {
|
|
31
30
|
value = encodeURIComponent(value);
|
|
32
|
-
|
|
31
|
+
let cookie = `${name}=${value}`;
|
|
32
|
+
if (opt.maxAge) {
|
|
33
|
+
cookie += `; Max-Age=${Math.floor(opt.maxAge)}`;
|
|
34
|
+
}
|
|
35
|
+
if (opt.domain) {
|
|
36
|
+
cookie += '; Domain=' + opt.domain;
|
|
37
|
+
}
|
|
38
|
+
if (opt.path) {
|
|
39
|
+
cookie += '; Path=' + opt.path;
|
|
40
|
+
}
|
|
41
|
+
if (opt.expires) {
|
|
42
|
+
cookie += '; Expires=' + opt.expires.toUTCString();
|
|
43
|
+
}
|
|
44
|
+
if (opt.httpOnly) {
|
|
45
|
+
cookie += '; HttpOnly';
|
|
46
|
+
}
|
|
47
|
+
if (opt.secure) {
|
|
48
|
+
cookie += '; Secure';
|
|
49
|
+
}
|
|
50
|
+
if (opt.sameSite) {
|
|
51
|
+
cookie += `; SameSaite=${opt.sameSite}`;
|
|
52
|
+
}
|
|
33
53
|
return cookie;
|
|
34
54
|
};
|
|
@@ -45,6 +45,8 @@ const cors = (options) => {
|
|
|
45
45
|
set('Access-Control-Allow-Headers', headers.join(','));
|
|
46
46
|
set('Vary', 'Access-Control-Request-Headers');
|
|
47
47
|
}
|
|
48
|
+
c.res.headers.delete('Content-Length');
|
|
49
|
+
c.res.headers.delete('Content-Type');
|
|
48
50
|
c.res = new Response(null, {
|
|
49
51
|
headers: c.res.headers,
|
|
50
52
|
status: 204,
|
|
@@ -11,16 +11,5 @@ const defaultMiddleware = async (c, next) => {
|
|
|
11
11
|
return c.req.headers.get(name);
|
|
12
12
|
};
|
|
13
13
|
await next();
|
|
14
|
-
if (c.res.body) {
|
|
15
|
-
// Do not clone Response, ex: c.res.clone().arrayBuffer()
|
|
16
|
-
const buffer = await c.res.arrayBuffer();
|
|
17
|
-
const res = new Response(buffer, {
|
|
18
|
-
status: c.res.status,
|
|
19
|
-
statusText: c.res.statusText,
|
|
20
|
-
headers: c.res.headers,
|
|
21
|
-
});
|
|
22
|
-
res.headers.append('Content-Length', buffer.byteLength.toString());
|
|
23
|
-
c.res = res;
|
|
24
|
-
}
|
|
25
14
|
};
|
|
26
15
|
exports.defaultMiddleware = defaultMiddleware;
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.mustache = void 0;
|
|
4
|
+
const cloudflare_1 = require("../../utils/cloudflare");
|
|
5
|
+
const EXTENSION = '.mustache';
|
|
6
|
+
const mustache = () => {
|
|
7
|
+
let Mustache;
|
|
8
|
+
try {
|
|
9
|
+
Mustache = require('mustache');
|
|
10
|
+
}
|
|
11
|
+
catch (_a) {
|
|
12
|
+
// Do nothing.
|
|
13
|
+
}
|
|
14
|
+
return async (c, next) => {
|
|
15
|
+
if (!Mustache) {
|
|
16
|
+
throw new Error('If you want to use Mustache Middleware, install mustache module.');
|
|
17
|
+
}
|
|
18
|
+
c.render = async (filename, view = {}, options) => {
|
|
19
|
+
const buffer = await (0, cloudflare_1.getContentFromKVAsset)(`${filename}${EXTENSION}`);
|
|
20
|
+
if (!buffer) {
|
|
21
|
+
throw new Error(`Template "${filename}${EXTENSION}" is not found or blank.`);
|
|
22
|
+
}
|
|
23
|
+
const content = bufferToString(buffer);
|
|
24
|
+
const partialArgs = {};
|
|
25
|
+
if (options) {
|
|
26
|
+
const partials = options;
|
|
27
|
+
for (const key of Object.keys(partials)) {
|
|
28
|
+
const partialBuffer = await (0, cloudflare_1.getContentFromKVAsset)(`${partials[key]}${EXTENSION}`);
|
|
29
|
+
if (!partialBuffer) {
|
|
30
|
+
throw new Error(`Partial Template "${partials[key]}${EXTENSION}" is not found or blank.`);
|
|
31
|
+
}
|
|
32
|
+
partialArgs[key] = bufferToString(partialBuffer);
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
const output = Mustache.render(content, view, partialArgs);
|
|
36
|
+
return c.html(output);
|
|
37
|
+
};
|
|
38
|
+
await next();
|
|
39
|
+
};
|
|
40
|
+
};
|
|
41
|
+
exports.mustache = mustache;
|
|
42
|
+
const bufferToString = (buffer) => {
|
|
43
|
+
if (buffer instanceof ArrayBuffer) {
|
|
44
|
+
const enc = new TextDecoder('utf-8');
|
|
45
|
+
return enc.decode(buffer);
|
|
46
|
+
}
|
|
47
|
+
return buffer;
|
|
48
|
+
};
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.serveStatic = void 0;
|
|
4
|
+
const cloudflare_1 = require("../../utils/cloudflare");
|
|
5
|
+
const mime_1 = require("../../utils/mime");
|
|
6
|
+
const DEFAULT_DOCUMENT = 'index.html';
|
|
7
|
+
// This middleware is available only on Cloudflare Workers.
|
|
8
|
+
const serveStatic = (opt = { root: '' }) => {
|
|
9
|
+
return async (c, next) => {
|
|
10
|
+
await next();
|
|
11
|
+
const url = new URL(c.req.url);
|
|
12
|
+
const path = getKVPath(url.pathname, opt.root);
|
|
13
|
+
const content = await (0, cloudflare_1.getContentFromKVAsset)(path);
|
|
14
|
+
if (content) {
|
|
15
|
+
const mimeType = (0, mime_1.getMimeType)(path);
|
|
16
|
+
if (mimeType) {
|
|
17
|
+
c.header('Content-Type', mimeType);
|
|
18
|
+
}
|
|
19
|
+
c.res = c.body(content);
|
|
20
|
+
}
|
|
21
|
+
else {
|
|
22
|
+
// console.debug(`Static file: ${path} is not found`)
|
|
23
|
+
}
|
|
24
|
+
};
|
|
25
|
+
};
|
|
26
|
+
exports.serveStatic = serveStatic;
|
|
27
|
+
const getKVPath = (filename, root) => {
|
|
28
|
+
if (filename.endsWith('/')) {
|
|
29
|
+
// /top/ => /top/index.html
|
|
30
|
+
filename = filename.concat(DEFAULT_DOCUMENT);
|
|
31
|
+
}
|
|
32
|
+
else if (!(0, mime_1.getMimeType)(filename)) {
|
|
33
|
+
// /top => /top/index.html
|
|
34
|
+
filename = filename.concat('/' + DEFAULT_DOCUMENT);
|
|
35
|
+
}
|
|
36
|
+
// /foo.html => foo.html
|
|
37
|
+
filename = filename.replace(/^\//, '');
|
|
38
|
+
// assets/ => assets
|
|
39
|
+
root = root.replace(/\/$/, '');
|
|
40
|
+
// ./assets/foo.html => assets/foo.html
|
|
41
|
+
let path = root + '/' + filename;
|
|
42
|
+
path = path.replace(/^\.?\//, '');
|
|
43
|
+
return path;
|
|
44
|
+
};
|
package/dist/middleware.d.ts
CHANGED
|
@@ -20,4 +20,9 @@ export declare class Middleware {
|
|
|
20
20
|
credentials?: boolean;
|
|
21
21
|
exposeHeaders?: string[];
|
|
22
22
|
}) => (c: import("./context").Context, next: Function) => Promise<void>;
|
|
23
|
+
static cookie: () => (c: import("./context").Context, next: Function) => Promise<void>;
|
|
24
|
+
static mustache: () => (c: import("./context").Context, next: Function) => Promise<void>;
|
|
25
|
+
static serveStatic: (opt?: {
|
|
26
|
+
root: string;
|
|
27
|
+
}) => (c: import("./context").Context, next: Function) => Promise<void>;
|
|
23
28
|
}
|
package/dist/middleware.js
CHANGED
|
@@ -7,6 +7,9 @@ const logger_1 = require("./middleware/logger/logger");
|
|
|
7
7
|
const basic_auth_1 = require("./middleware/basic-auth/basic-auth");
|
|
8
8
|
const body_parse_1 = require("./middleware/body-parse/body-parse");
|
|
9
9
|
const cors_1 = require("./middleware/cors/cors");
|
|
10
|
+
const cookie_1 = require("./middleware/cookie/cookie");
|
|
11
|
+
const mustache_1 = require("./middleware/mustache/mustache");
|
|
12
|
+
const serve_static_1 = require("./middleware/serve-static/serve-static");
|
|
10
13
|
class Middleware {
|
|
11
14
|
}
|
|
12
15
|
exports.Middleware = Middleware;
|
|
@@ -16,3 +19,6 @@ Middleware.logger = logger_1.logger;
|
|
|
16
19
|
Middleware.basicAuth = basic_auth_1.basicAuth;
|
|
17
20
|
Middleware.bodyParse = body_parse_1.bodyParse;
|
|
18
21
|
Middleware.cors = cors_1.cors;
|
|
22
|
+
Middleware.cookie = cookie_1.cookie;
|
|
23
|
+
Middleware.mustache = mustache_1.mustache;
|
|
24
|
+
Middleware.serveStatic = serve_static_1.serveStatic;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const getContentFromKVAsset: (path: string) => Promise<ArrayBuffer>;
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getContentFromKVAsset = void 0;
|
|
4
|
+
const getContentFromKVAsset = async (path) => {
|
|
5
|
+
let ASSET_MANIFEST;
|
|
6
|
+
if (typeof __STATIC_CONTENT_MANIFEST === 'string') {
|
|
7
|
+
ASSET_MANIFEST = JSON.parse(__STATIC_CONTENT_MANIFEST);
|
|
8
|
+
}
|
|
9
|
+
else {
|
|
10
|
+
ASSET_MANIFEST = __STATIC_CONTENT_MANIFEST;
|
|
11
|
+
}
|
|
12
|
+
const ASSET_NAMESPACE = __STATIC_CONTENT;
|
|
13
|
+
const key = ASSET_MANIFEST[path] || path;
|
|
14
|
+
if (!key) {
|
|
15
|
+
return;
|
|
16
|
+
}
|
|
17
|
+
let content = await ASSET_NAMESPACE.get(key, { type: 'arrayBuffer' });
|
|
18
|
+
if (content) {
|
|
19
|
+
content = content;
|
|
20
|
+
}
|
|
21
|
+
return content;
|
|
22
|
+
};
|
|
23
|
+
exports.getContentFromKVAsset = getContentFromKVAsset;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const getMimeType: (filename: string) => string;
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getMimeType = void 0;
|
|
4
|
+
const getMimeType = (filename) => {
|
|
5
|
+
const regexp = /\.([a-zA-Z0-9]+?)$/;
|
|
6
|
+
const match = filename.match(regexp);
|
|
7
|
+
if (!match) {
|
|
8
|
+
return;
|
|
9
|
+
}
|
|
10
|
+
let mimeType = mimes[match[1]];
|
|
11
|
+
if (mimeType.startsWith('text') || mimeType === 'application/json') {
|
|
12
|
+
mimeType += '; charset=utf-8';
|
|
13
|
+
}
|
|
14
|
+
return mimeType;
|
|
15
|
+
};
|
|
16
|
+
exports.getMimeType = getMimeType;
|
|
17
|
+
const mimes = {
|
|
18
|
+
aac: 'audio/aac',
|
|
19
|
+
abw: 'application/x-abiword',
|
|
20
|
+
arc: 'application/x-freearc',
|
|
21
|
+
avi: 'video/x-msvideo',
|
|
22
|
+
azw: 'application/vnd.amazon.ebook',
|
|
23
|
+
bin: 'application/octet-stream',
|
|
24
|
+
bmp: 'image/bmp',
|
|
25
|
+
bz: 'application/x-bzip',
|
|
26
|
+
bz2: 'application/x-bzip2',
|
|
27
|
+
csh: 'application/x-csh',
|
|
28
|
+
css: 'text/css',
|
|
29
|
+
csv: 'text/csv',
|
|
30
|
+
doc: 'application/msword',
|
|
31
|
+
docx: 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
|
|
32
|
+
eot: 'application/vnd.ms-fontobject',
|
|
33
|
+
epub: 'application/epub+zip',
|
|
34
|
+
gz: 'application/gzip',
|
|
35
|
+
gif: 'image/gif',
|
|
36
|
+
htm: 'text/html',
|
|
37
|
+
html: 'text/html',
|
|
38
|
+
ico: 'image/vnd.microsoft.icon',
|
|
39
|
+
ics: 'text/calendar',
|
|
40
|
+
jar: 'application/java-archive',
|
|
41
|
+
jpeg: 'image/jpeg',
|
|
42
|
+
jpg: 'image/jpeg',
|
|
43
|
+
js: 'text/javascript',
|
|
44
|
+
json: 'application/json',
|
|
45
|
+
jsonld: 'application/ld+json',
|
|
46
|
+
mid: 'audio/x-midi',
|
|
47
|
+
midi: 'audio/x-midi',
|
|
48
|
+
mjs: 'text/javascript',
|
|
49
|
+
mp3: 'audio/mpeg',
|
|
50
|
+
mpeg: 'video/mpeg',
|
|
51
|
+
mpkg: 'application/vnd.apple.installer+xml',
|
|
52
|
+
odp: 'application/vnd.oasis.opendocument.presentation',
|
|
53
|
+
ods: 'application/vnd.oasis.opendocument.spreadsheet',
|
|
54
|
+
odt: 'application/vnd.oasis.opendocument.text',
|
|
55
|
+
oga: 'audio/ogg',
|
|
56
|
+
ogv: 'video/ogg',
|
|
57
|
+
ogx: 'application/ogg',
|
|
58
|
+
opus: 'audio/opus',
|
|
59
|
+
otf: 'font/otf',
|
|
60
|
+
png: 'image/png',
|
|
61
|
+
pdf: 'application/pdf',
|
|
62
|
+
php: 'application/php',
|
|
63
|
+
ppt: 'application/vnd.ms-powerpoint',
|
|
64
|
+
pptx: 'application/vnd.openxmlformats-officedocument.presentationml.presentation',
|
|
65
|
+
rar: 'application/vnd.rar',
|
|
66
|
+
rtf: 'application/rtf',
|
|
67
|
+
sh: 'application/x-sh',
|
|
68
|
+
svg: 'image/svg+xml',
|
|
69
|
+
swf: 'application/x-shockwave-flash',
|
|
70
|
+
tar: 'application/x-tar',
|
|
71
|
+
tif: 'image/tiff',
|
|
72
|
+
tiff: 'image/tiff',
|
|
73
|
+
ts: 'video/mp2t',
|
|
74
|
+
ttf: 'font/ttf',
|
|
75
|
+
txt: 'text/plain',
|
|
76
|
+
vsd: 'application/vnd.visio',
|
|
77
|
+
wav: 'audio/wav',
|
|
78
|
+
weba: 'audio/webm',
|
|
79
|
+
webm: 'video/webm',
|
|
80
|
+
webp: 'image/webp',
|
|
81
|
+
woff: 'font/woff',
|
|
82
|
+
woff2: 'font/woff2',
|
|
83
|
+
xhtml: 'application/xhtml+xml',
|
|
84
|
+
xls: 'application/vnd.ms-excel',
|
|
85
|
+
xlsx: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
|
|
86
|
+
xml: 'application/xml',
|
|
87
|
+
xul: 'application/vnd.mozilla.xul+xml',
|
|
88
|
+
zip: 'application/zip',
|
|
89
|
+
'3gp': 'video/3gpp',
|
|
90
|
+
'3g2': 'video/3gpp2',
|
|
91
|
+
'7z': 'application/x-7z-compressed',
|
|
92
|
+
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "hono",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.4",
|
|
4
4
|
"description": "[炎] Ultrafast web framework for Cloudflare Workers.",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -36,6 +36,7 @@
|
|
|
36
36
|
"devDependencies": {
|
|
37
37
|
"@cloudflare/workers-types": "^3.3.0",
|
|
38
38
|
"@types/jest": "^27.4.0",
|
|
39
|
+
"@types/mustache": "^4.1.2",
|
|
39
40
|
"@types/node": "^17.0.8",
|
|
40
41
|
"@typescript-eslint/eslint-plugin": "^5.9.0",
|
|
41
42
|
"@typescript-eslint/parser": "^5.9.0",
|
|
@@ -51,6 +52,7 @@
|
|
|
51
52
|
"form-data": "^4.0.0",
|
|
52
53
|
"jest": "^27.4.5",
|
|
53
54
|
"jest-environment-miniflare": "^2.0.0",
|
|
55
|
+
"mustache": "^4.2.0",
|
|
54
56
|
"rimraf": "^3.0.2",
|
|
55
57
|
"ts-jest": "^27.1.2",
|
|
56
58
|
"typescript": "^4.5.4"
|