deno.land / std@0.173.0 / http / http_errors.ts

http_errors.ts
نووسراو ببینە
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
// Copyright 2018-2023 the Deno authors. All rights reserved. MIT license.
/** A collection of HTTP errors and utilities. * * The export {@linkcode errors} contains an individual class that extends * {@linkcode HttpError} which makes handling HTTP errors in a structured way. * * The function {@linkcode createHttpError} provides a way to create instances * of errors in a factory pattern. * * The function {@linkcode isHttpError} is a type guard that will narrow a value * to an `HttpError` instance. * * @example * ```ts * import { errors, isHttpError } from "https://deno.land/std@$STD_VERSION/http/http_errors.ts"; * * try { * throw new errors.NotFound(); * } catch (e) { * if (isHttpError(e)) { * const response = new Response(e.message, { status: e.status }); * } else { * throw e; * } * } * ``` * * @example * ```ts * import { createHttpError } from "https://deno.land/std@$STD_VERSION/http/http_errors.ts"; * import { Status } from "https://deno.land/std@$STD_VERSION/http/http_status.ts"; * * try { * throw createHttpError( * Status.BadRequest, * "The request was bad.", * { expose: false } * ); * } catch (e) { * // handle errors * } * ``` * * @module */
import { type ErrorStatus, isClientErrorStatus, Status, STATUS_TEXT,} from "./http_status.ts";
const ERROR_STATUS_MAP = { "BadRequest": 400, "Unauthorized": 401, "PaymentRequired": 402, "Forbidden": 403, "NotFound": 404, "MethodNotAllowed": 405, "NotAcceptable": 406, "ProxyAuthRequired": 407, "RequestTimeout": 408, "Conflict": 409, "Gone": 410, "LengthRequired": 411, "PreconditionFailed": 412, "RequestEntityTooLarge": 413, "RequestURITooLong": 414, "UnsupportedMediaType": 415, "RequestedRangeNotSatisfiable": 416, "ExpectationFailed": 417, "Teapot": 418, "MisdirectedRequest": 421, "UnprocessableEntity": 422, "Locked": 423, "FailedDependency": 424, "UpgradeRequired": 426, "PreconditionRequired": 428, "TooManyRequests": 429, "RequestHeaderFieldsTooLarge": 431, "UnavailableForLegalReasons": 451, "InternalServerError": 500, "NotImplemented": 501, "BadGateway": 502, "ServiceUnavailable": 503, "GatewayTimeout": 504, "HTTPVersionNotSupported": 505, "VariantAlsoNegotiates": 506, "InsufficientStorage": 507, "LoopDetected": 508, "NotExtended": 510, "NetworkAuthenticationRequired": 511,} as const;
export type ErrorStatusKeys = keyof typeof ERROR_STATUS_MAP;
export interface HttpErrorOptions extends ErrorOptions { expose?: boolean; headers?: HeadersInit;}
/** The base class that all derivative HTTP extend, providing a `status` and an * `expose` property. */export class HttpError extends Error { #status: ErrorStatus = Status.InternalServerError; #expose: boolean; #headers?: Headers; constructor( message = "Http Error", options?: HttpErrorOptions, ) { super(message, options); this.#expose = options?.expose === undefined ? isClientErrorStatus(this.status) : options.expose; if (options?.headers) { this.#headers = new Headers(options.headers); } } /** A flag to indicate if the internals of the error, like the stack, should * be exposed to a client, or if they are "private" and should not be leaked. * By default, all client errors are `true` and all server errors are * `false`. */ get expose(): boolean { return this.#expose; } /** The optional headers object that is set on the error. */ get headers(): Headers | undefined { return this.#headers; } /** The error status that is set on the error. */ get status(): ErrorStatus { return this.#status; }}
function createHttpErrorConstructor(status: ErrorStatus): typeof HttpError { const name = `${Status[status]}Error`; const ErrorCtor = class extends HttpError { constructor( message = STATUS_TEXT[status], options?: HttpErrorOptions, ) { super(message, options); Object.defineProperty(this, "name", { configurable: true, enumerable: false, value: name, writable: true, }); }
override get status() { return status; } }; return ErrorCtor;}
/** * A namespace that contains each error constructor. Each error extends * `HTTPError` and provides `.status` and `.expose` properties, where the * `.status` will be an error `Status` value and `.expose` indicates if * information, like a stack trace, should be shared in the response. * * By default, `.expose` is set to false in server errors, and true for client * errors. * * @example * ```ts * import { errors } from "https://deno.land/std@$STD_VERSION/http/http_errors.ts"; * * throw new errors.InternalServerError("Ooops!"); * ``` */export const errors: Record<ErrorStatusKeys, typeof HttpError> = {} as Record< ErrorStatusKeys, typeof HttpError>;
for (const [key, value] of Object.entries(ERROR_STATUS_MAP)) { errors[key as ErrorStatusKeys] = createHttpErrorConstructor(value);}
/** * A factory function which provides a way to create errors. It takes up to 3 * arguments, the error `Status`, an message, which defaults to the status text * and error options, which incudes the `expose` property to set the `.expose` * value on the error. */export function createHttpError( status: ErrorStatus = Status.InternalServerError, message?: string, options?: HttpErrorOptions,): HttpError { return new errors[Status[status] as ErrorStatusKeys](message, options);}
/** A type guard that determines if the value is an HttpError or not. */export function isHttpError(value: unknown): value is HttpError { return value instanceof HttpError;}
std

Version Info

Tagged at
a year ago