hono 4.0.3 → 4.0.5

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.
@@ -32,14 +32,21 @@ const html = (strings, ...values) => {
32
32
  const child = children[i2];
33
33
  if (typeof child === "string") {
34
34
  (0, import_html.escapeToBuffer)(child, buffer);
35
+ } else if (typeof child === "number") {
36
+ ;
37
+ buffer[0] += child;
35
38
  } else if (typeof child === "boolean" || child === null || child === void 0) {
36
39
  continue;
37
- } else if (typeof child === "object" && child.isEscaped || typeof child === "number") {
38
- const tmp = child.toString();
39
- if (tmp instanceof Promise) {
40
- buffer.unshift("", tmp);
40
+ } else if (typeof child === "object" && child.isEscaped) {
41
+ if (child.callbacks) {
42
+ buffer.unshift("", child);
41
43
  } else {
42
- buffer[0] += tmp;
44
+ const tmp = child.toString();
45
+ if (tmp instanceof Promise) {
46
+ buffer.unshift("", tmp);
47
+ } else {
48
+ buffer[0] += tmp;
49
+ }
43
50
  }
44
51
  } else if (child instanceof Promise) {
45
52
  buffer.unshift("", child);
@@ -36,6 +36,9 @@ const SSG_CONTEXT = "HONO_SSG_CONTEXT";
36
36
  const SSG_DISABLED_RESPONSE = new Response("SSG is disabled", { status: 404 });
37
37
  const generateFilePath = (routePath, outDir, mimeType) => {
38
38
  const extension = determineExtension(mimeType);
39
+ if (routePath.endsWith(`.${extension}`)) {
40
+ return (0, import_utils2.joinPaths)(outDir, routePath);
41
+ }
39
42
  if (routePath === "/") {
40
43
  return (0, import_utils2.joinPaths)(outDir, `index.${extension}`);
41
44
  }
@@ -27,11 +27,17 @@ module.exports = __toCommonJS(render_exports);
27
27
  var import_constants = require("../constants");
28
28
  var import_context = require("../context");
29
29
  var import_hooks = require("../hooks");
30
+ var import__ = require(".");
30
31
  const eventAliasMap = {
31
32
  Change: "Input",
32
33
  DoubleClick: "DblClick"
33
34
  };
35
+ const nameSpaceMap = {
36
+ svg: "http://www.w3.org/2000/svg",
37
+ math: "http://www.w3.org/1998/Math/MathML"
38
+ };
34
39
  const buildDataStack = [];
40
+ let nameSpaceContext = void 0;
35
41
  const isNodeString = (node) => Array.isArray(node);
36
42
  const getEventSpec = (key) => {
37
43
  const match = key.match(/^on([A-Z][a-zA-Z]+?)((?<!Pointer)Capture)?$/);
@@ -178,22 +184,24 @@ const applyNode = (node, container) => {
178
184
  applyNodeObject(node, container);
179
185
  }
180
186
  };
187
+ const findChildNodeIndex = (childNodes, child) => {
188
+ if (!child) {
189
+ return;
190
+ }
191
+ for (let i = 0, len = childNodes.length; i < len; i++) {
192
+ if (childNodes[i] === child) {
193
+ return i;
194
+ }
195
+ }
196
+ return;
197
+ };
181
198
  const applyNodeObject = (node, container) => {
182
199
  const next = [];
183
200
  const remove = [];
184
201
  const callbacks = [];
185
202
  getNextChildren(node, container, next, remove, callbacks);
186
- let offset = container.childNodes.length;
187
- const insertBefore = findInsertBefore(node.nN) || next.find((n) => n.e)?.e;
188
- if (insertBefore) {
189
- for (let i = 0; i < offset; i++) {
190
- if (container.childNodes[i] === insertBefore) {
191
- offset = i;
192
- break;
193
- }
194
- }
195
- }
196
203
  const childNodes = container.childNodes;
204
+ let offset = findChildNodeIndex(childNodes, findInsertBefore(node.nN)) ?? findChildNodeIndex(childNodes, next.find((n) => n.e)?.e) ?? childNodes.length;
197
205
  for (let i = 0, len = next.length; i < len; i++, offset++) {
198
206
  const child = next[i];
199
207
  let el;
@@ -203,7 +211,7 @@ const applyNodeObject = (node, container) => {
203
211
  }
204
212
  el = child.e || (child.e = document.createTextNode(child[0]));
205
213
  } else {
206
- el = child.e || (child.e = document.createElement(child.tag));
214
+ el = child.e || (child.e = child.n ? document.createElementNS(child.n, child.tag) : document.createElement(child.tag));
207
215
  applyProps(el, child.props, child.pP);
208
216
  applyNode(child, el);
209
217
  }
@@ -264,6 +272,11 @@ const build = (context, node, topLevelErrorHandlerNode, children) => {
264
272
  oldChild.children = child.children;
265
273
  child = oldChild;
266
274
  }
275
+ } else if (!isNodeString(child) && nameSpaceContext) {
276
+ const ns = (0, import__.useContext)(nameSpaceContext);
277
+ if (ns) {
278
+ child.n = ns;
279
+ }
267
280
  }
268
281
  if (!isNodeString(child)) {
269
282
  build(context, child, topLevelErrorHandlerNode);
@@ -301,6 +314,22 @@ const buildNode = (node) => {
301
314
  if (typeof node.tag === "function") {
302
315
  ;
303
316
  node[import_constants.DOM_STASH] = [0, []];
317
+ } else {
318
+ const ns = nameSpaceMap[node.tag];
319
+ if (ns) {
320
+ ;
321
+ node.n = ns;
322
+ nameSpaceContext || (nameSpaceContext = (0, import__.createContext)(""));
323
+ node.children = [
324
+ {
325
+ tag: nameSpaceContext.Provider,
326
+ props: {
327
+ value: ns
328
+ },
329
+ children: node.children
330
+ }
331
+ ];
332
+ }
304
333
  }
305
334
  return node;
306
335
  }
@@ -237,7 +237,10 @@ const use = (promise) => {
237
237
  }
238
238
  return cachedRes[0];
239
239
  }
240
- promise.then((res2) => resolvedPromiseValueMap.set(promise, [res2])).catch((e) => resolvedPromiseValueMap.set(promise, [void 0, e]));
240
+ promise.then(
241
+ (res2) => resolvedPromiseValueMap.set(promise, [res2]),
242
+ (e) => resolvedPromiseValueMap.set(promise, [void 0, e])
243
+ );
241
244
  const buildData = import_render.buildDataStack.at(-1);
242
245
  if (!buildData) {
243
246
  throw promise;
@@ -245,11 +248,14 @@ const use = (promise) => {
245
248
  const [, node] = buildData;
246
249
  const promiseArray = (_a = node[import_constants.DOM_STASH][1])[STASH_USE] || (_a[STASH_USE] = []);
247
250
  const hookIndex = node[import_constants.DOM_STASH][0]++;
248
- promise.then((res2) => {
249
- promiseArray[hookIndex] = [res2];
250
- }).catch((e) => {
251
- promiseArray[hookIndex] = [void 0, e];
252
- });
251
+ promise.then(
252
+ (res2) => {
253
+ promiseArray[hookIndex] = [res2];
254
+ },
255
+ (e) => {
256
+ promiseArray[hookIndex] = [void 0, e];
257
+ }
258
+ );
253
259
  const res = promiseArray[hookIndex];
254
260
  if (res) {
255
261
  if (res.length === 2) {
@@ -24,7 +24,7 @@ __export(jwt_exports, {
24
24
  verify: () => verify
25
25
  });
26
26
  module.exports = __toCommonJS(jwt_exports);
27
- var import_helper = require("../../helper");
27
+ var import_cookie = require("../../helper/cookie");
28
28
  var import_http_exception = require("../../http-exception");
29
29
  var import_jwt = require("../../utils/jwt");
30
30
  var import_context = require("../../context");
@@ -52,7 +52,7 @@ const jwt = (options) => {
52
52
  token = parts[1];
53
53
  }
54
54
  } else if (options.cookie) {
55
- token = (0, import_helper.getCookie)(ctx)[options.cookie];
55
+ token = (0, import_cookie.getCookie)(ctx)[options.cookie];
56
56
  }
57
57
  if (!token) {
58
58
  throw new import_http_exception.HTTPException(401, {
@@ -34,6 +34,10 @@ const validator = (target, validationFunc) => {
34
34
  const message = `Invalid HTTP header: Content-Type=${contentType}`;
35
35
  throw new import_http_exception.HTTPException(400, { message });
36
36
  }
37
+ if (c.req.bodyCache.json) {
38
+ value = await c.req.bodyCache.json;
39
+ break;
40
+ }
37
41
  try {
38
42
  const arrayBuffer = c.req.bodyCache.arrayBuffer ?? await c.req.raw.arrayBuffer();
39
43
  value = await new Response(arrayBuffer).json();
@@ -45,6 +49,10 @@ const validator = (target, validationFunc) => {
45
49
  }
46
50
  break;
47
51
  case "form": {
52
+ if (c.req.bodyCache.formData) {
53
+ value = c.req.bodyCache.formData;
54
+ break;
55
+ }
48
56
  try {
49
57
  const contentType2 = c.req.header("Content-Type");
50
58
  if (contentType2) {
@@ -9,14 +9,21 @@ var html = (strings, ...values) => {
9
9
  const child = children[i2];
10
10
  if (typeof child === "string") {
11
11
  escapeToBuffer(child, buffer);
12
+ } else if (typeof child === "number") {
13
+ ;
14
+ buffer[0] += child;
12
15
  } else if (typeof child === "boolean" || child === null || child === void 0) {
13
16
  continue;
14
- } else if (typeof child === "object" && child.isEscaped || typeof child === "number") {
15
- const tmp = child.toString();
16
- if (tmp instanceof Promise) {
17
- buffer.unshift("", tmp);
17
+ } else if (typeof child === "object" && child.isEscaped) {
18
+ if (child.callbacks) {
19
+ buffer.unshift("", child);
18
20
  } else {
19
- buffer[0] += tmp;
21
+ const tmp = child.toString();
22
+ if (tmp instanceof Promise) {
23
+ buffer.unshift("", tmp);
24
+ } else {
25
+ buffer[0] += tmp;
26
+ }
20
27
  }
21
28
  } else if (child instanceof Promise) {
22
29
  buffer.unshift("", child);
@@ -7,6 +7,9 @@ var SSG_CONTEXT = "HONO_SSG_CONTEXT";
7
7
  var SSG_DISABLED_RESPONSE = new Response("SSG is disabled", { status: 404 });
8
8
  var generateFilePath = (routePath, outDir, mimeType) => {
9
9
  const extension = determineExtension(mimeType);
10
+ if (routePath.endsWith(`.${extension}`)) {
11
+ return joinPaths(outDir, routePath);
12
+ }
10
13
  if (routePath === "/") {
11
14
  return joinPaths(outDir, `index.${extension}`);
12
15
  }
@@ -2,11 +2,17 @@
2
2
  import { DOM_RENDERER, DOM_ERROR_HANDLER, DOM_STASH } from "../constants.js";
3
3
  import { globalContexts as globalJSXContexts } from "../context.js";
4
4
  import { STASH_EFFECT } from "../hooks/index.js";
5
+ import { useContext, createContext } from "./index.js";
5
6
  var eventAliasMap = {
6
7
  Change: "Input",
7
8
  DoubleClick: "DblClick"
8
9
  };
10
+ var nameSpaceMap = {
11
+ svg: "http://www.w3.org/2000/svg",
12
+ math: "http://www.w3.org/1998/Math/MathML"
13
+ };
9
14
  var buildDataStack = [];
15
+ var nameSpaceContext = void 0;
10
16
  var isNodeString = (node) => Array.isArray(node);
11
17
  var getEventSpec = (key) => {
12
18
  const match = key.match(/^on([A-Z][a-zA-Z]+?)((?<!Pointer)Capture)?$/);
@@ -153,22 +159,24 @@ var applyNode = (node, container) => {
153
159
  applyNodeObject(node, container);
154
160
  }
155
161
  };
162
+ var findChildNodeIndex = (childNodes, child) => {
163
+ if (!child) {
164
+ return;
165
+ }
166
+ for (let i = 0, len = childNodes.length; i < len; i++) {
167
+ if (childNodes[i] === child) {
168
+ return i;
169
+ }
170
+ }
171
+ return;
172
+ };
156
173
  var applyNodeObject = (node, container) => {
157
174
  const next = [];
158
175
  const remove = [];
159
176
  const callbacks = [];
160
177
  getNextChildren(node, container, next, remove, callbacks);
161
- let offset = container.childNodes.length;
162
- const insertBefore = findInsertBefore(node.nN) || next.find((n) => n.e)?.e;
163
- if (insertBefore) {
164
- for (let i = 0; i < offset; i++) {
165
- if (container.childNodes[i] === insertBefore) {
166
- offset = i;
167
- break;
168
- }
169
- }
170
- }
171
178
  const childNodes = container.childNodes;
179
+ let offset = findChildNodeIndex(childNodes, findInsertBefore(node.nN)) ?? findChildNodeIndex(childNodes, next.find((n) => n.e)?.e) ?? childNodes.length;
172
180
  for (let i = 0, len = next.length; i < len; i++, offset++) {
173
181
  const child = next[i];
174
182
  let el;
@@ -178,7 +186,7 @@ var applyNodeObject = (node, container) => {
178
186
  }
179
187
  el = child.e || (child.e = document.createTextNode(child[0]));
180
188
  } else {
181
- el = child.e || (child.e = document.createElement(child.tag));
189
+ el = child.e || (child.e = child.n ? document.createElementNS(child.n, child.tag) : document.createElement(child.tag));
182
190
  applyProps(el, child.props, child.pP);
183
191
  applyNode(child, el);
184
192
  }
@@ -239,6 +247,11 @@ var build = (context, node, topLevelErrorHandlerNode, children) => {
239
247
  oldChild.children = child.children;
240
248
  child = oldChild;
241
249
  }
250
+ } else if (!isNodeString(child) && nameSpaceContext) {
251
+ const ns = useContext(nameSpaceContext);
252
+ if (ns) {
253
+ child.n = ns;
254
+ }
242
255
  }
243
256
  if (!isNodeString(child)) {
244
257
  build(context, child, topLevelErrorHandlerNode);
@@ -276,6 +289,22 @@ var buildNode = (node) => {
276
289
  if (typeof node.tag === "function") {
277
290
  ;
278
291
  node[DOM_STASH] = [0, []];
292
+ } else {
293
+ const ns = nameSpaceMap[node.tag];
294
+ if (ns) {
295
+ ;
296
+ node.n = ns;
297
+ nameSpaceContext || (nameSpaceContext = createContext(""));
298
+ node.children = [
299
+ {
300
+ tag: nameSpaceContext.Provider,
301
+ props: {
302
+ value: ns
303
+ },
304
+ children: node.children
305
+ }
306
+ ];
307
+ }
279
308
  }
280
309
  return node;
281
310
  }
@@ -203,7 +203,10 @@ var use = (promise) => {
203
203
  }
204
204
  return cachedRes[0];
205
205
  }
206
- promise.then((res2) => resolvedPromiseValueMap.set(promise, [res2])).catch((e) => resolvedPromiseValueMap.set(promise, [void 0, e]));
206
+ promise.then(
207
+ (res2) => resolvedPromiseValueMap.set(promise, [res2]),
208
+ (e) => resolvedPromiseValueMap.set(promise, [void 0, e])
209
+ );
207
210
  const buildData = buildDataStack.at(-1);
208
211
  if (!buildData) {
209
212
  throw promise;
@@ -211,11 +214,14 @@ var use = (promise) => {
211
214
  const [, node] = buildData;
212
215
  const promiseArray = (_a = node[DOM_STASH][1])[STASH_USE] || (_a[STASH_USE] = []);
213
216
  const hookIndex = node[DOM_STASH][0]++;
214
- promise.then((res2) => {
215
- promiseArray[hookIndex] = [res2];
216
- }).catch((e) => {
217
- promiseArray[hookIndex] = [void 0, e];
218
- });
217
+ promise.then(
218
+ (res2) => {
219
+ promiseArray[hookIndex] = [res2];
220
+ },
221
+ (e) => {
222
+ promiseArray[hookIndex] = [void 0, e];
223
+ }
224
+ );
219
225
  const res = promiseArray[hookIndex];
220
226
  if (res) {
221
227
  if (res.length === 2) {
@@ -1,5 +1,5 @@
1
1
  // src/middleware/jwt/index.ts
2
- import { getCookie } from "../../helper.js";
2
+ import { getCookie } from "../../helper/cookie/index.js";
3
3
  import { HTTPException } from "../../http-exception.js";
4
4
  import { Jwt } from "../../utils/jwt/index.js";
5
5
  import "../../context.js";
@@ -1,5 +1,3 @@
1
- import type { FC } from './jsx';
2
- import type { PropsForRenderer } from './middleware/jsx-renderer';
3
1
  import type { HonoRequest } from './request';
4
2
  import type { Env, FetchEventLike, NotFoundHandler, Input, TypedResponse } from './types';
5
3
  import type { RedirectStatusCode, StatusCode } from './utils/http-status';
@@ -18,6 +16,8 @@ interface DefaultRenderer {
18
16
  (content: string | Promise<string>): Response | Promise<Response>;
19
17
  }
20
18
  export type Renderer = ContextRenderer extends Function ? ContextRenderer : DefaultRenderer;
19
+ export type PropsForRenderer = [...Required<Parameters<Renderer>>] extends [unknown, infer Props] ? Props : unknown;
20
+ export type Layout<T = Record<string, any>> = (props: T) => any;
21
21
  interface Get<E extends Env> {
22
22
  <Key extends keyof ContextVariableMap>(key: Key): ContextVariableMap[Key];
23
23
  <Key extends keyof E['Variables']>(key: Key): E['Variables'][Key];
@@ -112,13 +112,13 @@ export declare class Context<E extends Env = any, P extends string = any, I exte
112
112
  * @see https://hono.dev/api/context#render-setrenderer
113
113
  */
114
114
  render: Renderer;
115
- setLayout: (layout: FC<PropsForRenderer & {
116
- Layout: FC;
117
- }>) => FC<{
118
- Layout: FC;
115
+ setLayout: (layout: Layout<PropsForRenderer & {
116
+ Layout: Layout;
117
+ }>) => Layout<{
118
+ Layout: Layout;
119
119
  }>;
120
- getLayout: () => FC<{
121
- Layout: FC;
120
+ getLayout: () => Layout<{
121
+ Layout: Layout;
122
122
  }> | undefined;
123
123
  /**
124
124
  * `.setRenderer()` can set the layout in the custom middleware.
@@ -8,14 +8,16 @@ export type HasRenderToDom = FC<any> & {
8
8
  export type ErrorHandler = (error: any, retry: () => void) => Child | undefined;
9
9
  type Container = HTMLElement | DocumentFragment;
10
10
  type LocalJSXContexts = [JSXContext<unknown>, unknown][] | undefined;
11
+ type SupportedElement = HTMLElement | SVGElement | MathMLElement;
11
12
  export type NodeObject = {
12
13
  pP: Props | undefined;
13
14
  nN: Node | undefined;
14
15
  vC: Node[];
15
16
  vR: Node[];
16
17
  s?: Node[];
18
+ n?: string;
17
19
  c: Container | undefined;
18
- e: HTMLElement | Text | undefined;
20
+ e: SupportedElement | Text | undefined;
19
21
  [DOM_STASH]: [
20
22
  number,
21
23
  any[][],
@@ -1,8 +1,7 @@
1
- import type { Context, Renderer } from '../../context';
1
+ import type { Context, PropsForRenderer } from '../../context';
2
2
  import type { FC, PropsWithChildren } from '../../jsx';
3
3
  import type { Env, Input, MiddlewareHandler } from '../../types';
4
4
  export declare const RequestContext: import("../../jsx").Context<Context<any, any, {}> | null>;
5
- export type PropsForRenderer = [...Required<Parameters<Renderer>>] extends [unknown, infer Props] ? Props : unknown;
6
5
  type RendererOptions = {
7
6
  docType?: boolean | string;
8
7
  stream?: boolean | Record<string, string>;
@@ -12,6 +12,10 @@ var validator = (target, validationFunc) => {
12
12
  const message = `Invalid HTTP header: Content-Type=${contentType}`;
13
13
  throw new HTTPException(400, { message });
14
14
  }
15
+ if (c.req.bodyCache.json) {
16
+ value = await c.req.bodyCache.json;
17
+ break;
18
+ }
15
19
  try {
16
20
  const arrayBuffer = c.req.bodyCache.arrayBuffer ?? await c.req.raw.arrayBuffer();
17
21
  value = await new Response(arrayBuffer).json();
@@ -23,6 +27,10 @@ var validator = (target, validationFunc) => {
23
27
  }
24
28
  break;
25
29
  case "form": {
30
+ if (c.req.bodyCache.formData) {
31
+ value = c.req.bodyCache.formData;
32
+ break;
33
+ }
26
34
  try {
27
35
  const contentType2 = c.req.header("Content-Type");
28
36
  if (contentType2) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "hono",
3
- "version": "4.0.3",
3
+ "version": "4.0.5",
4
4
  "description": "Ultrafast web framework for the Edges",
5
5
  "main": "dist/cjs/index.js",
6
6
  "type": "module",
@@ -499,7 +499,7 @@
499
499
  "cloudflare",
500
500
  "workers",
501
501
  "fastly",
502
- "compute@edge",
502
+ "compute",
503
503
  "deno",
504
504
  "bun",
505
505
  "lambda",
@@ -1,10 +0,0 @@
1
- export * from './helper/accepts';
2
- export * from './helper/adapter';
3
- export * from './helper/cookie';
4
- export * from './helper/css';
5
- export * from './helper/factory';
6
- export * from './helper/html';
7
- export * from './helper/streaming';
8
- export * from './helper/testing';
9
- export * from './helper/dev';
10
- export * from './adapter/deno/ssg';