Aktueller Stand
This commit is contained in:
411
backend/node_modules/hono/dist/context.js
generated
vendored
Normal file
411
backend/node_modules/hono/dist/context.js
generated
vendored
Normal file
@@ -0,0 +1,411 @@
|
||||
// src/context.ts
|
||||
import { HonoRequest } from "./request.js";
|
||||
import { HtmlEscapedCallbackPhase, resolveCallback } from "./utils/html.js";
|
||||
var TEXT_PLAIN = "text/plain; charset=UTF-8";
|
||||
var setDefaultContentType = (contentType, headers) => {
|
||||
return {
|
||||
"Content-Type": contentType,
|
||||
...headers
|
||||
};
|
||||
};
|
||||
var Context = class {
|
||||
#rawRequest;
|
||||
#req;
|
||||
/**
|
||||
* `.env` can get bindings (environment variables, secrets, KV namespaces, D1 database, R2 bucket etc.) in Cloudflare Workers.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#env}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* // Environment object for Cloudflare Workers
|
||||
* app.get('*', async c => {
|
||||
* const counter = c.env.COUNTER
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
env = {};
|
||||
#var;
|
||||
finalized = false;
|
||||
/**
|
||||
* `.error` can get the error object from the middleware if the Handler throws an error.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#error}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.use('*', async (c, next) => {
|
||||
* await next()
|
||||
* if (c.error) {
|
||||
* // do something...
|
||||
* }
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
error;
|
||||
#status;
|
||||
#executionCtx;
|
||||
#res;
|
||||
#layout;
|
||||
#renderer;
|
||||
#notFoundHandler;
|
||||
#preparedHeaders;
|
||||
#matchResult;
|
||||
#path;
|
||||
/**
|
||||
* Creates an instance of the Context class.
|
||||
*
|
||||
* @param req - The Request object.
|
||||
* @param options - Optional configuration options for the context.
|
||||
*/
|
||||
constructor(req, options) {
|
||||
this.#rawRequest = req;
|
||||
if (options) {
|
||||
this.#executionCtx = options.executionCtx;
|
||||
this.env = options.env;
|
||||
this.#notFoundHandler = options.notFoundHandler;
|
||||
this.#path = options.path;
|
||||
this.#matchResult = options.matchResult;
|
||||
}
|
||||
}
|
||||
/**
|
||||
* `.req` is the instance of {@link HonoRequest}.
|
||||
*/
|
||||
get req() {
|
||||
this.#req ??= new HonoRequest(this.#rawRequest, this.#path, this.#matchResult);
|
||||
return this.#req;
|
||||
}
|
||||
/**
|
||||
* @see {@link https://hono.dev/docs/api/context#event}
|
||||
* The FetchEvent associated with the current request.
|
||||
*
|
||||
* @throws Will throw an error if the context does not have a FetchEvent.
|
||||
*/
|
||||
get event() {
|
||||
if (this.#executionCtx && "respondWith" in this.#executionCtx) {
|
||||
return this.#executionCtx;
|
||||
} else {
|
||||
throw Error("This context has no FetchEvent");
|
||||
}
|
||||
}
|
||||
/**
|
||||
* @see {@link https://hono.dev/docs/api/context#executionctx}
|
||||
* The ExecutionContext associated with the current request.
|
||||
*
|
||||
* @throws Will throw an error if the context does not have an ExecutionContext.
|
||||
*/
|
||||
get executionCtx() {
|
||||
if (this.#executionCtx) {
|
||||
return this.#executionCtx;
|
||||
} else {
|
||||
throw Error("This context has no ExecutionContext");
|
||||
}
|
||||
}
|
||||
/**
|
||||
* @see {@link https://hono.dev/docs/api/context#res}
|
||||
* The Response object for the current request.
|
||||
*/
|
||||
get res() {
|
||||
return this.#res ||= new Response(null, {
|
||||
headers: this.#preparedHeaders ??= new Headers()
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Sets the Response object for the current request.
|
||||
*
|
||||
* @param _res - The Response object to set.
|
||||
*/
|
||||
set res(_res) {
|
||||
if (this.#res && _res) {
|
||||
_res = new Response(_res.body, _res);
|
||||
for (const [k, v] of this.#res.headers.entries()) {
|
||||
if (k === "content-type") {
|
||||
continue;
|
||||
}
|
||||
if (k === "set-cookie") {
|
||||
const cookies = this.#res.headers.getSetCookie();
|
||||
_res.headers.delete("set-cookie");
|
||||
for (const cookie of cookies) {
|
||||
_res.headers.append("set-cookie", cookie);
|
||||
}
|
||||
} else {
|
||||
_res.headers.set(k, v);
|
||||
}
|
||||
}
|
||||
}
|
||||
this.#res = _res;
|
||||
this.finalized = true;
|
||||
}
|
||||
/**
|
||||
* `.render()` can create a response within a layout.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#render-setrenderer}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/', (c) => {
|
||||
* return c.render('Hello!')
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
render = (...args) => {
|
||||
this.#renderer ??= (content) => this.html(content);
|
||||
return this.#renderer(...args);
|
||||
};
|
||||
/**
|
||||
* Sets the layout for the response.
|
||||
*
|
||||
* @param layout - The layout to set.
|
||||
* @returns The layout function.
|
||||
*/
|
||||
setLayout = (layout) => this.#layout = layout;
|
||||
/**
|
||||
* Gets the current layout for the response.
|
||||
*
|
||||
* @returns The current layout function.
|
||||
*/
|
||||
getLayout = () => this.#layout;
|
||||
/**
|
||||
* `.setRenderer()` can set the layout in the custom middleware.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#render-setrenderer}
|
||||
*
|
||||
* @example
|
||||
* ```tsx
|
||||
* app.use('*', async (c, next) => {
|
||||
* c.setRenderer((content) => {
|
||||
* return c.html(
|
||||
* <html>
|
||||
* <body>
|
||||
* <p>{content}</p>
|
||||
* </body>
|
||||
* </html>
|
||||
* )
|
||||
* })
|
||||
* await next()
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
setRenderer = (renderer) => {
|
||||
this.#renderer = renderer;
|
||||
};
|
||||
/**
|
||||
* `.header()` can set headers.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#header}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/welcome', (c) => {
|
||||
* // Set headers
|
||||
* c.header('X-Message', 'Hello!')
|
||||
* c.header('Content-Type', 'text/plain')
|
||||
*
|
||||
* return c.body('Thank you for coming')
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
header = (name, value, options) => {
|
||||
if (this.finalized) {
|
||||
this.#res = new Response(this.#res.body, this.#res);
|
||||
}
|
||||
const headers = this.#res ? this.#res.headers : this.#preparedHeaders ??= new Headers();
|
||||
if (value === void 0) {
|
||||
headers.delete(name);
|
||||
} else if (options?.append) {
|
||||
headers.append(name, value);
|
||||
} else {
|
||||
headers.set(name, value);
|
||||
}
|
||||
};
|
||||
status = (status) => {
|
||||
this.#status = status;
|
||||
};
|
||||
/**
|
||||
* `.set()` can set the value specified by the key.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#set-get}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.use('*', async (c, next) => {
|
||||
* c.set('message', 'Hono is hot!!')
|
||||
* await next()
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
set = (key, value) => {
|
||||
this.#var ??= /* @__PURE__ */ new Map();
|
||||
this.#var.set(key, value);
|
||||
};
|
||||
/**
|
||||
* `.get()` can use the value specified by the key.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#set-get}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/', (c) => {
|
||||
* const message = c.get('message')
|
||||
* return c.text(`The message is "${message}"`)
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
get = (key) => {
|
||||
return this.#var ? this.#var.get(key) : void 0;
|
||||
};
|
||||
/**
|
||||
* `.var` can access the value of a variable.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#var}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* const result = c.var.client.oneMethod()
|
||||
* ```
|
||||
*/
|
||||
// c.var.propName is a read-only
|
||||
get var() {
|
||||
if (!this.#var) {
|
||||
return {};
|
||||
}
|
||||
return Object.fromEntries(this.#var);
|
||||
}
|
||||
#newResponse(data, arg, headers) {
|
||||
const responseHeaders = this.#res ? new Headers(this.#res.headers) : this.#preparedHeaders ?? new Headers();
|
||||
if (typeof arg === "object" && "headers" in arg) {
|
||||
const argHeaders = arg.headers instanceof Headers ? arg.headers : new Headers(arg.headers);
|
||||
for (const [key, value] of argHeaders) {
|
||||
if (key.toLowerCase() === "set-cookie") {
|
||||
responseHeaders.append(key, value);
|
||||
} else {
|
||||
responseHeaders.set(key, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (headers) {
|
||||
for (const [k, v] of Object.entries(headers)) {
|
||||
if (typeof v === "string") {
|
||||
responseHeaders.set(k, v);
|
||||
} else {
|
||||
responseHeaders.delete(k);
|
||||
for (const v2 of v) {
|
||||
responseHeaders.append(k, v2);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
const status = typeof arg === "number" ? arg : arg?.status ?? this.#status;
|
||||
return new Response(data, { status, headers: responseHeaders });
|
||||
}
|
||||
newResponse = (...args) => this.#newResponse(...args);
|
||||
/**
|
||||
* `.body()` can return the HTTP response.
|
||||
* You can set headers with `.header()` and set HTTP status code with `.status`.
|
||||
* This can also be set in `.text()`, `.json()` and so on.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#body}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/welcome', (c) => {
|
||||
* // Set headers
|
||||
* c.header('X-Message', 'Hello!')
|
||||
* c.header('Content-Type', 'text/plain')
|
||||
* // Set HTTP status code
|
||||
* c.status(201)
|
||||
*
|
||||
* // Return the response body
|
||||
* return c.body('Thank you for coming')
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
body = (data, arg, headers) => this.#newResponse(data, arg, headers);
|
||||
/**
|
||||
* `.text()` can render text as `Content-Type:text/plain`.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#text}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/say', (c) => {
|
||||
* return c.text('Hello!')
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
text = (text, arg, headers) => {
|
||||
return !this.#preparedHeaders && !this.#status && !arg && !headers && !this.finalized ? new Response(text) : this.#newResponse(
|
||||
text,
|
||||
arg,
|
||||
setDefaultContentType(TEXT_PLAIN, headers)
|
||||
);
|
||||
};
|
||||
/**
|
||||
* `.json()` can render JSON as `Content-Type:application/json`.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#json}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/api', (c) => {
|
||||
* return c.json({ message: 'Hello!' })
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
json = (object, arg, headers) => {
|
||||
return this.#newResponse(
|
||||
JSON.stringify(object),
|
||||
arg,
|
||||
setDefaultContentType("application/json", headers)
|
||||
);
|
||||
};
|
||||
html = (html, arg, headers) => {
|
||||
const res = (html2) => this.#newResponse(html2, arg, setDefaultContentType("text/html; charset=UTF-8", headers));
|
||||
return typeof html === "object" ? resolveCallback(html, HtmlEscapedCallbackPhase.Stringify, false, {}).then(res) : res(html);
|
||||
};
|
||||
/**
|
||||
* `.redirect()` can Redirect, default status code is 302.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#redirect}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/redirect', (c) => {
|
||||
* return c.redirect('/')
|
||||
* })
|
||||
* app.get('/redirect-permanently', (c) => {
|
||||
* return c.redirect('/', 301)
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
redirect = (location, status) => {
|
||||
const locationString = String(location);
|
||||
this.header(
|
||||
"Location",
|
||||
// Multibyes should be encoded
|
||||
// eslint-disable-next-line no-control-regex
|
||||
!/[^\x00-\xFF]/.test(locationString) ? locationString : encodeURI(locationString)
|
||||
);
|
||||
return this.newResponse(null, status ?? 302);
|
||||
};
|
||||
/**
|
||||
* `.notFound()` can return the Not Found Response.
|
||||
*
|
||||
* @see {@link https://hono.dev/docs/api/context#notfound}
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* app.get('/notfound', (c) => {
|
||||
* return c.notFound()
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
notFound = () => {
|
||||
this.#notFoundHandler ??= () => new Response();
|
||||
return this.#notFoundHandler(this);
|
||||
};
|
||||
};
|
||||
export {
|
||||
Context,
|
||||
TEXT_PLAIN
|
||||
};
|
||||
Reference in New Issue
Block a user