@t402/hono 2.8.0 → 2.8.1
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/dist/cjs/index.js +9 -13
- package/dist/cjs/index.js.map +1 -1
- package/dist/esm/index.mjs +9 -13
- package/dist/esm/index.mjs.map +1 -1
- package/package.json +11 -11
package/dist/cjs/index.js
CHANGED
|
@@ -196,33 +196,30 @@ function paymentMiddleware(routes, server, paywallConfig, paywall, syncFacilitat
|
|
|
196
196
|
}
|
|
197
197
|
case "payment-verified":
|
|
198
198
|
const { paymentPayload, paymentRequirements } = result;
|
|
199
|
-
await next();
|
|
200
|
-
let res = c.res;
|
|
201
|
-
if (res.status >= 400) {
|
|
202
|
-
return;
|
|
203
|
-
}
|
|
204
|
-
c.res = void 0;
|
|
205
199
|
try {
|
|
206
200
|
const settleResult = await httpServer.processSettlement(
|
|
207
201
|
paymentPayload,
|
|
208
202
|
paymentRequirements
|
|
209
203
|
);
|
|
210
204
|
if (!settleResult.success) {
|
|
211
|
-
|
|
205
|
+
return c.json(
|
|
212
206
|
{
|
|
213
207
|
error: "Settlement failed",
|
|
214
208
|
details: settleResult.errorReason
|
|
215
209
|
},
|
|
216
210
|
402
|
|
217
211
|
);
|
|
218
|
-
} else {
|
|
219
|
-
Object.entries(settleResult.headers).forEach(([key, value]) => {
|
|
220
|
-
res.headers.set(key, value);
|
|
221
|
-
});
|
|
222
212
|
}
|
|
213
|
+
await next();
|
|
214
|
+
let res = c.res;
|
|
215
|
+
c.res = void 0;
|
|
216
|
+
Object.entries(settleResult.headers).forEach(([key, value]) => {
|
|
217
|
+
res.headers.set(key, value);
|
|
218
|
+
});
|
|
219
|
+
c.res = res;
|
|
223
220
|
} catch (error) {
|
|
224
221
|
console.error(error);
|
|
225
|
-
|
|
222
|
+
return c.json(
|
|
226
223
|
{
|
|
227
224
|
error: "Settlement failed",
|
|
228
225
|
details: error instanceof Error ? error.message : "Unknown error"
|
|
@@ -230,7 +227,6 @@ function paymentMiddleware(routes, server, paywallConfig, paywall, syncFacilitat
|
|
|
230
227
|
402
|
|
231
228
|
);
|
|
232
229
|
}
|
|
233
|
-
c.res = res;
|
|
234
230
|
return;
|
|
235
231
|
}
|
|
236
232
|
};
|
package/dist/cjs/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/index.ts","../../src/adapter.ts"],"sourcesContent":["import {\n HTTPRequestContext,\n PaywallConfig,\n PaywallProvider,\n t402HTTPResourceServer,\n t402ResourceServer,\n RoutesConfig,\n FacilitatorClient,\n} from \"@t402/core/server\";\nimport { SchemeNetworkServer, Network } from \"@t402/core/types\";\nimport { Context, MiddlewareHandler } from \"hono\";\nimport { HonoAdapter } from \"./adapter\";\n\n/**\n * Check if any routes in the configuration declare bazaar extensions\n *\n * @param routes - Route configuration\n * @returns True if any route has extensions.bazaar defined\n */\nfunction checkIfBazaarNeeded(routes: RoutesConfig): boolean {\n // Handle single route config\n if (\"accepts\" in routes) {\n return !!(routes.extensions && \"bazaar\" in routes.extensions);\n }\n\n // Handle multiple routes\n return Object.values(routes).some(routeConfig => {\n return !!(routeConfig.extensions && \"bazaar\" in routeConfig.extensions);\n });\n}\n\n/**\n * Configuration for registering a payment scheme with a specific network\n */\nexport interface SchemeRegistration {\n /**\n * The network identifier (e.g., 'eip155:84532', 'solana:mainnet')\n */\n network: Network;\n\n /**\n * The scheme server implementation for this network\n */\n server: SchemeNetworkServer;\n}\n\n/**\n * Hono payment middleware for t402 protocol (direct server instance).\n *\n * Use this when you want to pass a pre-configured t402ResourceServer instance.\n * This provides more flexibility for testing, custom configuration, and reusing\n * server instances across multiple middlewares.\n *\n * @param routes - Route configurations for protected endpoints\n * @param server - Pre-configured t402ResourceServer instance\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddleware } from \"@t402/hono\";\n * import { t402ResourceServer } from \"@t402/core/server\";\n * import { registerExactEvmScheme } from \"@t402/evm/exact/server\";\n *\n * const server = new t402ResourceServer(myFacilitatorClient);\n * registerExactEvmScheme(server, {});\n *\n * app.use(paymentMiddleware(routes, server, paywallConfig));\n * ```\n */\nexport function paymentMiddleware(\n routes: RoutesConfig,\n server: t402ResourceServer,\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n // Create the t402 HTTP server instance with the resource server\n const httpServer = new t402HTTPResourceServer(server, routes);\n\n // Register custom paywall provider if provided\n if (paywall) {\n httpServer.registerPaywallProvider(paywall);\n }\n\n // Store initialization promise (not the result)\n // httpServer.initialize() fetches facilitator support and validates routes\n let initPromise: Promise<void> | null = syncFacilitatorOnStart ? httpServer.initialize() : null;\n\n // Dynamically register bazaar extension if routes declare it\n let bazaarPromise: Promise<void> | null = null;\n if (checkIfBazaarNeeded(routes)) {\n bazaarPromise = import(\"@t402/extensions/bazaar\")\n .then(({ bazaarResourceServerExtension }) => {\n server.registerExtension(bazaarResourceServerExtension);\n })\n .catch(err => {\n console.error(\"Failed to load bazaar extension:\", err);\n });\n }\n\n return async (c: Context, next: () => Promise<void>) => {\n // Create adapter and context\n const adapter = new HonoAdapter(c);\n const context: HTTPRequestContext = {\n adapter,\n path: c.req.path,\n method: c.req.method,\n paymentHeader: adapter.getHeader(\"payment-signature\") || adapter.getHeader(\"x-payment\"),\n };\n\n // Check if route requires payment before initializing facilitator\n if (!httpServer.requiresPayment(context)) {\n return next();\n }\n\n // Only initialize when processing a protected route\n if (initPromise) {\n await initPromise;\n initPromise = null; // Clear after first await\n }\n\n // Await bazaar extension loading if needed\n if (bazaarPromise) {\n await bazaarPromise;\n bazaarPromise = null;\n }\n\n // Process payment requirement check\n const result = await httpServer.processHTTPRequest(context, paywallConfig);\n\n // Handle the different result types\n switch (result.type) {\n case \"no-payment-required\":\n // No payment needed, proceed directly to the route handler\n return next();\n\n case \"payment-error\":\n // Payment required but not provided or invalid\n const { response } = result;\n Object.entries(response.headers).forEach(([key, value]) => {\n c.header(key, value);\n });\n if (response.isHtml) {\n return c.html(response.body as string, response.status as 402);\n } else {\n return c.json(response.body || {}, response.status as 402);\n }\n\n case \"payment-verified\":\n // Payment is valid, need to wrap response for settlement\n const { paymentPayload, paymentRequirements } = result;\n\n // Proceed to the next middleware or route handler\n await next();\n\n // Get the current response\n let res = c.res;\n\n // If the response from the protected route is >= 400, do not settle payment\n if (res.status >= 400) {\n return;\n }\n\n // Clear the response so we can modify headers\n c.res = undefined;\n\n try {\n const settleResult = await httpServer.processSettlement(\n paymentPayload,\n paymentRequirements,\n );\n\n if (!settleResult.success) {\n // Settlement failed - do not return the protected resource\n res = c.json(\n {\n error: \"Settlement failed\",\n details: settleResult.errorReason,\n },\n 402,\n );\n } else {\n // Settlement succeeded - add headers to response\n Object.entries(settleResult.headers).forEach(([key, value]) => {\n res.headers.set(key, value);\n });\n }\n } catch (error) {\n console.error(error);\n // If settlement fails, return an error response\n res = c.json(\n {\n error: \"Settlement failed\",\n details: error instanceof Error ? error.message : \"Unknown error\",\n },\n 402,\n );\n }\n\n // Restore the response (potentially modified with settlement headers)\n c.res = res;\n return;\n }\n };\n}\n\n/**\n * Hono payment middleware for t402 protocol (configuration-based).\n *\n * Use this when you want to quickly set up middleware with simple configuration.\n * This function creates and configures the t402ResourceServer internally.\n *\n * @param routes - Route configurations for protected endpoints\n * @param facilitatorClients - Optional facilitator client(s) for payment processing\n * @param schemes - Optional array of scheme registrations for server-side payment processing\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddlewareFromConfig } from \"@t402/hono\";\n *\n * app.use(paymentMiddlewareFromConfig(\n * routes,\n * myFacilitatorClient,\n * [{ network: \"eip155:8453\", server: evmSchemeServer }],\n * paywallConfig\n * ));\n * ```\n */\nexport function paymentMiddlewareFromConfig(\n routes: RoutesConfig,\n facilitatorClients?: FacilitatorClient | FacilitatorClient[],\n schemes?: SchemeRegistration[],\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n const ResourceServer = new t402ResourceServer(facilitatorClients);\n\n if (schemes) {\n schemes.forEach(({ network, server: schemeServer }) => {\n ResourceServer.register(network, schemeServer);\n });\n }\n\n // Use the direct paymentMiddleware with the configured server\n // Note: paymentMiddleware handles dynamic bazaar registration\n return paymentMiddleware(routes, ResourceServer, paywallConfig, paywall, syncFacilitatorOnStart);\n}\n\nexport { t402ResourceServer, t402HTTPResourceServer } from \"@t402/core/server\";\n\nexport type {\n PaymentRequired,\n PaymentRequirements,\n PaymentPayload,\n Network,\n SchemeNetworkServer,\n} from \"@t402/core/types\";\n\nexport type { PaywallProvider, PaywallConfig } from \"@t402/core/server\";\n\nexport { RouteConfigurationError } from \"@t402/core/server\";\n\nexport type { RouteValidationError } from \"@t402/core/server\";\n\nexport { HonoAdapter } from \"./adapter\";\n","import { HTTPAdapter } from \"@t402/core/server\";\nimport { Context } from \"hono\";\n\n/**\n * Hono adapter implementation\n */\nexport class HonoAdapter implements HTTPAdapter {\n /**\n * Creates a new HonoAdapter instance.\n *\n * @param c - The Hono context object\n */\n constructor(private c: Context) {}\n\n /**\n * Gets a header value from the request.\n *\n * @param name - The header name\n * @returns The header value or undefined\n */\n getHeader(name: string): string | undefined {\n return this.c.req.header(name);\n }\n\n /**\n * Gets the HTTP method of the request.\n *\n * @returns The HTTP method\n */\n getMethod(): string {\n return this.c.req.method;\n }\n\n /**\n * Gets the path of the request.\n *\n * @returns The request path\n */\n getPath(): string {\n return this.c.req.path;\n }\n\n /**\n * Gets the full URL of the request.\n *\n * @returns The full request URL\n */\n getUrl(): string {\n return this.c.req.url;\n }\n\n /**\n * Gets the Accept header from the request.\n *\n * @returns The Accept header value or empty string\n */\n getAcceptHeader(): string {\n return this.c.req.header(\"Accept\") || \"\";\n }\n\n /**\n * Gets the User-Agent header from the request.\n *\n * @returns The User-Agent header value or empty string\n */\n getUserAgent(): string {\n return this.c.req.header(\"User-Agent\") || \"\";\n }\n\n /**\n * Gets all query parameters from the request URL.\n *\n * @returns Record of query parameter key-value pairs\n */\n getQueryParams(): Record<string, string | string[]> {\n const query = this.c.req.query();\n // Convert single values to match the interface\n const result: Record<string, string | string[]> = {};\n for (const [key, value] of Object.entries(query)) {\n result[key] = value;\n }\n return result;\n }\n\n /**\n * Gets a specific query parameter by name.\n *\n * @param name - The query parameter name\n * @returns The query parameter value(s) or undefined\n */\n getQueryParam(name: string): string | string[] | undefined {\n return this.c.req.query(name);\n }\n\n /**\n * Gets the parsed request body.\n * Requires appropriate body parsing middleware.\n *\n * @returns The parsed request body\n */\n async getBody(): Promise<unknown> {\n try {\n return await this.c.req.json();\n } catch {\n return undefined;\n }\n }\n}\n"],"mappings":"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","names":["import_server"]}
|
|
1
|
+
{"version":3,"sources":["../../src/index.ts","../../src/adapter.ts"],"sourcesContent":["import {\n HTTPRequestContext,\n PaywallConfig,\n PaywallProvider,\n t402HTTPResourceServer,\n t402ResourceServer,\n RoutesConfig,\n FacilitatorClient,\n} from \"@t402/core/server\";\nimport { SchemeNetworkServer, Network } from \"@t402/core/types\";\nimport { Context, MiddlewareHandler } from \"hono\";\nimport { HonoAdapter } from \"./adapter\";\n\n/**\n * Check if any routes in the configuration declare bazaar extensions\n *\n * @param routes - Route configuration\n * @returns True if any route has extensions.bazaar defined\n */\nfunction checkIfBazaarNeeded(routes: RoutesConfig): boolean {\n // Handle single route config\n if (\"accepts\" in routes) {\n return !!(routes.extensions && \"bazaar\" in routes.extensions);\n }\n\n // Handle multiple routes\n return Object.values(routes).some(routeConfig => {\n return !!(routeConfig.extensions && \"bazaar\" in routeConfig.extensions);\n });\n}\n\n/**\n * Configuration for registering a payment scheme with a specific network\n */\nexport interface SchemeRegistration {\n /**\n * The network identifier (e.g., 'eip155:84532', 'solana:mainnet')\n */\n network: Network;\n\n /**\n * The scheme server implementation for this network\n */\n server: SchemeNetworkServer;\n}\n\n/**\n * Hono payment middleware for t402 protocol (direct server instance).\n *\n * Use this when you want to pass a pre-configured t402ResourceServer instance.\n * This provides more flexibility for testing, custom configuration, and reusing\n * server instances across multiple middlewares.\n *\n * @param routes - Route configurations for protected endpoints\n * @param server - Pre-configured t402ResourceServer instance\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddleware } from \"@t402/hono\";\n * import { t402ResourceServer } from \"@t402/core/server\";\n * import { registerExactEvmScheme } from \"@t402/evm/exact/server\";\n *\n * const server = new t402ResourceServer(myFacilitatorClient);\n * registerExactEvmScheme(server, {});\n *\n * app.use(paymentMiddleware(routes, server, paywallConfig));\n * ```\n */\nexport function paymentMiddleware(\n routes: RoutesConfig,\n server: t402ResourceServer,\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n // Create the t402 HTTP server instance with the resource server\n const httpServer = new t402HTTPResourceServer(server, routes);\n\n // Register custom paywall provider if provided\n if (paywall) {\n httpServer.registerPaywallProvider(paywall);\n }\n\n // Store initialization promise (not the result)\n // httpServer.initialize() fetches facilitator support and validates routes\n let initPromise: Promise<void> | null = syncFacilitatorOnStart ? httpServer.initialize() : null;\n\n // Dynamically register bazaar extension if routes declare it\n let bazaarPromise: Promise<void> | null = null;\n if (checkIfBazaarNeeded(routes)) {\n bazaarPromise = import(\"@t402/extensions/bazaar\")\n .then(({ bazaarResourceServerExtension }) => {\n server.registerExtension(bazaarResourceServerExtension);\n })\n .catch(err => {\n console.error(\"Failed to load bazaar extension:\", err);\n });\n }\n\n return async (c: Context, next: () => Promise<void>) => {\n // Create adapter and context\n const adapter = new HonoAdapter(c);\n const context: HTTPRequestContext = {\n adapter,\n path: c.req.path,\n method: c.req.method,\n paymentHeader: adapter.getHeader(\"payment-signature\") || adapter.getHeader(\"x-payment\"),\n };\n\n // Check if route requires payment before initializing facilitator\n if (!httpServer.requiresPayment(context)) {\n return next();\n }\n\n // Only initialize when processing a protected route\n if (initPromise) {\n await initPromise;\n initPromise = null; // Clear after first await\n }\n\n // Await bazaar extension loading if needed\n if (bazaarPromise) {\n await bazaarPromise;\n bazaarPromise = null;\n }\n\n // Process payment requirement check\n const result = await httpServer.processHTTPRequest(context, paywallConfig);\n\n // Handle the different result types\n switch (result.type) {\n case \"no-payment-required\":\n // No payment needed, proceed directly to the route handler\n return next();\n\n case \"payment-error\":\n // Payment required but not provided or invalid\n const { response } = result;\n Object.entries(response.headers).forEach(([key, value]) => {\n c.header(key, value);\n });\n if (response.isHtml) {\n return c.html(response.body as string, response.status as 402);\n } else {\n return c.json(response.body || {}, response.status as 402);\n }\n\n case \"payment-verified\":\n // Payment is valid — settle BEFORE executing handler to prevent\n // side effects from leaking on settlement failure.\n const { paymentPayload, paymentRequirements } = result;\n\n // Settle payment first\n try {\n const settleResult = await httpServer.processSettlement(\n paymentPayload,\n paymentRequirements,\n );\n\n if (!settleResult.success) {\n return c.json(\n {\n error: \"Settlement failed\",\n details: settleResult.errorReason,\n },\n 402,\n );\n }\n\n // Settlement succeeded — now execute handler\n await next();\n\n // Add settlement headers to response\n let res = c.res;\n c.res = undefined;\n Object.entries(settleResult.headers).forEach(([key, value]) => {\n res.headers.set(key, value);\n });\n c.res = res;\n } catch (error) {\n console.error(error);\n return c.json(\n {\n error: \"Settlement failed\",\n details: error instanceof Error ? error.message : \"Unknown error\",\n },\n 402,\n );\n }\n return;\n }\n };\n}\n\n/**\n * Hono payment middleware for t402 protocol (configuration-based).\n *\n * Use this when you want to quickly set up middleware with simple configuration.\n * This function creates and configures the t402ResourceServer internally.\n *\n * @param routes - Route configurations for protected endpoints\n * @param facilitatorClients - Optional facilitator client(s) for payment processing\n * @param schemes - Optional array of scheme registrations for server-side payment processing\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddlewareFromConfig } from \"@t402/hono\";\n *\n * app.use(paymentMiddlewareFromConfig(\n * routes,\n * myFacilitatorClient,\n * [{ network: \"eip155:8453\", server: evmSchemeServer }],\n * paywallConfig\n * ));\n * ```\n */\nexport function paymentMiddlewareFromConfig(\n routes: RoutesConfig,\n facilitatorClients?: FacilitatorClient | FacilitatorClient[],\n schemes?: SchemeRegistration[],\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n const ResourceServer = new t402ResourceServer(facilitatorClients);\n\n if (schemes) {\n schemes.forEach(({ network, server: schemeServer }) => {\n ResourceServer.register(network, schemeServer);\n });\n }\n\n // Use the direct paymentMiddleware with the configured server\n // Note: paymentMiddleware handles dynamic bazaar registration\n return paymentMiddleware(routes, ResourceServer, paywallConfig, paywall, syncFacilitatorOnStart);\n}\n\nexport { t402ResourceServer, t402HTTPResourceServer } from \"@t402/core/server\";\n\nexport type {\n PaymentRequired,\n PaymentRequirements,\n PaymentPayload,\n Network,\n SchemeNetworkServer,\n} from \"@t402/core/types\";\n\nexport type { PaywallProvider, PaywallConfig } from \"@t402/core/server\";\n\nexport { RouteConfigurationError } from \"@t402/core/server\";\n\nexport type { RouteValidationError } from \"@t402/core/server\";\n\nexport { HonoAdapter } from \"./adapter\";\n","import { HTTPAdapter } from \"@t402/core/server\";\nimport { Context } from \"hono\";\n\n/**\n * Hono adapter implementation\n */\nexport class HonoAdapter implements HTTPAdapter {\n /**\n * Creates a new HonoAdapter instance.\n *\n * @param c - The Hono context object\n */\n constructor(private c: Context) {}\n\n /**\n * Gets a header value from the request.\n *\n * @param name - The header name\n * @returns The header value or undefined\n */\n getHeader(name: string): string | undefined {\n return this.c.req.header(name);\n }\n\n /**\n * Gets the HTTP method of the request.\n *\n * @returns The HTTP method\n */\n getMethod(): string {\n return this.c.req.method;\n }\n\n /**\n * Gets the path of the request.\n *\n * @returns The request path\n */\n getPath(): string {\n return this.c.req.path;\n }\n\n /**\n * Gets the full URL of the request.\n *\n * @returns The full request URL\n */\n getUrl(): string {\n return this.c.req.url;\n }\n\n /**\n * Gets the Accept header from the request.\n *\n * @returns The Accept header value or empty string\n */\n getAcceptHeader(): string {\n return this.c.req.header(\"Accept\") || \"\";\n }\n\n /**\n * Gets the User-Agent header from the request.\n *\n * @returns The User-Agent header value or empty string\n */\n getUserAgent(): string {\n return this.c.req.header(\"User-Agent\") || \"\";\n }\n\n /**\n * Gets all query parameters from the request URL.\n *\n * @returns Record of query parameter key-value pairs\n */\n getQueryParams(): Record<string, string | string[]> {\n const query = this.c.req.query();\n // Convert single values to match the interface\n const result: Record<string, string | string[]> = {};\n for (const [key, value] of Object.entries(query)) {\n result[key] = value;\n }\n return result;\n }\n\n /**\n * Gets a specific query parameter by name.\n *\n * @param name - The query parameter name\n * @returns The query parameter value(s) or undefined\n */\n getQueryParam(name: string): string | string[] | undefined {\n return this.c.req.query(name);\n }\n\n /**\n * Gets the parsed request body.\n * Requires appropriate body parsing middleware.\n *\n * @returns The parsed request body\n */\n async getBody(): Promise<unknown> {\n try {\n return await this.c.req.json();\n } catch {\n return undefined;\n }\n }\n}\n"],"mappings":"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","names":["import_server"]}
|
package/dist/esm/index.mjs
CHANGED
|
@@ -160,33 +160,30 @@ function paymentMiddleware(routes, server, paywallConfig, paywall, syncFacilitat
|
|
|
160
160
|
}
|
|
161
161
|
case "payment-verified":
|
|
162
162
|
const { paymentPayload, paymentRequirements } = result;
|
|
163
|
-
await next();
|
|
164
|
-
let res = c.res;
|
|
165
|
-
if (res.status >= 400) {
|
|
166
|
-
return;
|
|
167
|
-
}
|
|
168
|
-
c.res = void 0;
|
|
169
163
|
try {
|
|
170
164
|
const settleResult = await httpServer.processSettlement(
|
|
171
165
|
paymentPayload,
|
|
172
166
|
paymentRequirements
|
|
173
167
|
);
|
|
174
168
|
if (!settleResult.success) {
|
|
175
|
-
|
|
169
|
+
return c.json(
|
|
176
170
|
{
|
|
177
171
|
error: "Settlement failed",
|
|
178
172
|
details: settleResult.errorReason
|
|
179
173
|
},
|
|
180
174
|
402
|
|
181
175
|
);
|
|
182
|
-
} else {
|
|
183
|
-
Object.entries(settleResult.headers).forEach(([key, value]) => {
|
|
184
|
-
res.headers.set(key, value);
|
|
185
|
-
});
|
|
186
176
|
}
|
|
177
|
+
await next();
|
|
178
|
+
let res = c.res;
|
|
179
|
+
c.res = void 0;
|
|
180
|
+
Object.entries(settleResult.headers).forEach(([key, value]) => {
|
|
181
|
+
res.headers.set(key, value);
|
|
182
|
+
});
|
|
183
|
+
c.res = res;
|
|
187
184
|
} catch (error) {
|
|
188
185
|
console.error(error);
|
|
189
|
-
|
|
186
|
+
return c.json(
|
|
190
187
|
{
|
|
191
188
|
error: "Settlement failed",
|
|
192
189
|
details: error instanceof Error ? error.message : "Unknown error"
|
|
@@ -194,7 +191,6 @@ function paymentMiddleware(routes, server, paywallConfig, paywall, syncFacilitat
|
|
|
194
191
|
402
|
|
195
192
|
);
|
|
196
193
|
}
|
|
197
|
-
c.res = res;
|
|
198
194
|
return;
|
|
199
195
|
}
|
|
200
196
|
};
|
package/dist/esm/index.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/index.ts","../../src/adapter.ts"],"sourcesContent":["import {\n HTTPRequestContext,\n PaywallConfig,\n PaywallProvider,\n t402HTTPResourceServer,\n t402ResourceServer,\n RoutesConfig,\n FacilitatorClient,\n} from \"@t402/core/server\";\nimport { SchemeNetworkServer, Network } from \"@t402/core/types\";\nimport { Context, MiddlewareHandler } from \"hono\";\nimport { HonoAdapter } from \"./adapter\";\n\n/**\n * Check if any routes in the configuration declare bazaar extensions\n *\n * @param routes - Route configuration\n * @returns True if any route has extensions.bazaar defined\n */\nfunction checkIfBazaarNeeded(routes: RoutesConfig): boolean {\n // Handle single route config\n if (\"accepts\" in routes) {\n return !!(routes.extensions && \"bazaar\" in routes.extensions);\n }\n\n // Handle multiple routes\n return Object.values(routes).some(routeConfig => {\n return !!(routeConfig.extensions && \"bazaar\" in routeConfig.extensions);\n });\n}\n\n/**\n * Configuration for registering a payment scheme with a specific network\n */\nexport interface SchemeRegistration {\n /**\n * The network identifier (e.g., 'eip155:84532', 'solana:mainnet')\n */\n network: Network;\n\n /**\n * The scheme server implementation for this network\n */\n server: SchemeNetworkServer;\n}\n\n/**\n * Hono payment middleware for t402 protocol (direct server instance).\n *\n * Use this when you want to pass a pre-configured t402ResourceServer instance.\n * This provides more flexibility for testing, custom configuration, and reusing\n * server instances across multiple middlewares.\n *\n * @param routes - Route configurations for protected endpoints\n * @param server - Pre-configured t402ResourceServer instance\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddleware } from \"@t402/hono\";\n * import { t402ResourceServer } from \"@t402/core/server\";\n * import { registerExactEvmScheme } from \"@t402/evm/exact/server\";\n *\n * const server = new t402ResourceServer(myFacilitatorClient);\n * registerExactEvmScheme(server, {});\n *\n * app.use(paymentMiddleware(routes, server, paywallConfig));\n * ```\n */\nexport function paymentMiddleware(\n routes: RoutesConfig,\n server: t402ResourceServer,\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n // Create the t402 HTTP server instance with the resource server\n const httpServer = new t402HTTPResourceServer(server, routes);\n\n // Register custom paywall provider if provided\n if (paywall) {\n httpServer.registerPaywallProvider(paywall);\n }\n\n // Store initialization promise (not the result)\n // httpServer.initialize() fetches facilitator support and validates routes\n let initPromise: Promise<void> | null = syncFacilitatorOnStart ? httpServer.initialize() : null;\n\n // Dynamically register bazaar extension if routes declare it\n let bazaarPromise: Promise<void> | null = null;\n if (checkIfBazaarNeeded(routes)) {\n bazaarPromise = import(\"@t402/extensions/bazaar\")\n .then(({ bazaarResourceServerExtension }) => {\n server.registerExtension(bazaarResourceServerExtension);\n })\n .catch(err => {\n console.error(\"Failed to load bazaar extension:\", err);\n });\n }\n\n return async (c: Context, next: () => Promise<void>) => {\n // Create adapter and context\n const adapter = new HonoAdapter(c);\n const context: HTTPRequestContext = {\n adapter,\n path: c.req.path,\n method: c.req.method,\n paymentHeader: adapter.getHeader(\"payment-signature\") || adapter.getHeader(\"x-payment\"),\n };\n\n // Check if route requires payment before initializing facilitator\n if (!httpServer.requiresPayment(context)) {\n return next();\n }\n\n // Only initialize when processing a protected route\n if (initPromise) {\n await initPromise;\n initPromise = null; // Clear after first await\n }\n\n // Await bazaar extension loading if needed\n if (bazaarPromise) {\n await bazaarPromise;\n bazaarPromise = null;\n }\n\n // Process payment requirement check\n const result = await httpServer.processHTTPRequest(context, paywallConfig);\n\n // Handle the different result types\n switch (result.type) {\n case \"no-payment-required\":\n // No payment needed, proceed directly to the route handler\n return next();\n\n case \"payment-error\":\n // Payment required but not provided or invalid\n const { response } = result;\n Object.entries(response.headers).forEach(([key, value]) => {\n c.header(key, value);\n });\n if (response.isHtml) {\n return c.html(response.body as string, response.status as 402);\n } else {\n return c.json(response.body || {}, response.status as 402);\n }\n\n case \"payment-verified\":\n // Payment is valid, need to wrap response for settlement\n const { paymentPayload, paymentRequirements } = result;\n\n // Proceed to the next middleware or route handler\n await next();\n\n // Get the current response\n let res = c.res;\n\n // If the response from the protected route is >= 400, do not settle payment\n if (res.status >= 400) {\n return;\n }\n\n // Clear the response so we can modify headers\n c.res = undefined;\n\n try {\n const settleResult = await httpServer.processSettlement(\n paymentPayload,\n paymentRequirements,\n );\n\n if (!settleResult.success) {\n // Settlement failed - do not return the protected resource\n res = c.json(\n {\n error: \"Settlement failed\",\n details: settleResult.errorReason,\n },\n 402,\n );\n } else {\n // Settlement succeeded - add headers to response\n Object.entries(settleResult.headers).forEach(([key, value]) => {\n res.headers.set(key, value);\n });\n }\n } catch (error) {\n console.error(error);\n // If settlement fails, return an error response\n res = c.json(\n {\n error: \"Settlement failed\",\n details: error instanceof Error ? error.message : \"Unknown error\",\n },\n 402,\n );\n }\n\n // Restore the response (potentially modified with settlement headers)\n c.res = res;\n return;\n }\n };\n}\n\n/**\n * Hono payment middleware for t402 protocol (configuration-based).\n *\n * Use this when you want to quickly set up middleware with simple configuration.\n * This function creates and configures the t402ResourceServer internally.\n *\n * @param routes - Route configurations for protected endpoints\n * @param facilitatorClients - Optional facilitator client(s) for payment processing\n * @param schemes - Optional array of scheme registrations for server-side payment processing\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddlewareFromConfig } from \"@t402/hono\";\n *\n * app.use(paymentMiddlewareFromConfig(\n * routes,\n * myFacilitatorClient,\n * [{ network: \"eip155:8453\", server: evmSchemeServer }],\n * paywallConfig\n * ));\n * ```\n */\nexport function paymentMiddlewareFromConfig(\n routes: RoutesConfig,\n facilitatorClients?: FacilitatorClient | FacilitatorClient[],\n schemes?: SchemeRegistration[],\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n const ResourceServer = new t402ResourceServer(facilitatorClients);\n\n if (schemes) {\n schemes.forEach(({ network, server: schemeServer }) => {\n ResourceServer.register(network, schemeServer);\n });\n }\n\n // Use the direct paymentMiddleware with the configured server\n // Note: paymentMiddleware handles dynamic bazaar registration\n return paymentMiddleware(routes, ResourceServer, paywallConfig, paywall, syncFacilitatorOnStart);\n}\n\nexport { t402ResourceServer, t402HTTPResourceServer } from \"@t402/core/server\";\n\nexport type {\n PaymentRequired,\n PaymentRequirements,\n PaymentPayload,\n Network,\n SchemeNetworkServer,\n} from \"@t402/core/types\";\n\nexport type { PaywallProvider, PaywallConfig } from \"@t402/core/server\";\n\nexport { RouteConfigurationError } from \"@t402/core/server\";\n\nexport type { RouteValidationError } from \"@t402/core/server\";\n\nexport { HonoAdapter } from \"./adapter\";\n","import { HTTPAdapter } from \"@t402/core/server\";\nimport { Context } from \"hono\";\n\n/**\n * Hono adapter implementation\n */\nexport class HonoAdapter implements HTTPAdapter {\n /**\n * Creates a new HonoAdapter instance.\n *\n * @param c - The Hono context object\n */\n constructor(private c: Context) {}\n\n /**\n * Gets a header value from the request.\n *\n * @param name - The header name\n * @returns The header value or undefined\n */\n getHeader(name: string): string | undefined {\n return this.c.req.header(name);\n }\n\n /**\n * Gets the HTTP method of the request.\n *\n * @returns The HTTP method\n */\n getMethod(): string {\n return this.c.req.method;\n }\n\n /**\n * Gets the path of the request.\n *\n * @returns The request path\n */\n getPath(): string {\n return this.c.req.path;\n }\n\n /**\n * Gets the full URL of the request.\n *\n * @returns The full request URL\n */\n getUrl(): string {\n return this.c.req.url;\n }\n\n /**\n * Gets the Accept header from the request.\n *\n * @returns The Accept header value or empty string\n */\n getAcceptHeader(): string {\n return this.c.req.header(\"Accept\") || \"\";\n }\n\n /**\n * Gets the User-Agent header from the request.\n *\n * @returns The User-Agent header value or empty string\n */\n getUserAgent(): string {\n return this.c.req.header(\"User-Agent\") || \"\";\n }\n\n /**\n * Gets all query parameters from the request URL.\n *\n * @returns Record of query parameter key-value pairs\n */\n getQueryParams(): Record<string, string | string[]> {\n const query = this.c.req.query();\n // Convert single values to match the interface\n const result: Record<string, string | string[]> = {};\n for (const [key, value] of Object.entries(query)) {\n result[key] = value;\n }\n return result;\n }\n\n /**\n * Gets a specific query parameter by name.\n *\n * @param name - The query parameter name\n * @returns The query parameter value(s) or undefined\n */\n getQueryParam(name: string): string | string[] | undefined {\n return this.c.req.query(name);\n }\n\n /**\n * Gets the parsed request body.\n * Requires appropriate body parsing middleware.\n *\n * @returns The parsed request body\n */\n async getBody(): Promise<unknown> {\n try {\n return await this.c.req.json();\n } catch {\n return undefined;\n }\n }\n}\n"],"mappings":"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","names":["t402ResourceServer","t402HTTPResourceServer"]}
|
|
1
|
+
{"version":3,"sources":["../../src/index.ts","../../src/adapter.ts"],"sourcesContent":["import {\n HTTPRequestContext,\n PaywallConfig,\n PaywallProvider,\n t402HTTPResourceServer,\n t402ResourceServer,\n RoutesConfig,\n FacilitatorClient,\n} from \"@t402/core/server\";\nimport { SchemeNetworkServer, Network } from \"@t402/core/types\";\nimport { Context, MiddlewareHandler } from \"hono\";\nimport { HonoAdapter } from \"./adapter\";\n\n/**\n * Check if any routes in the configuration declare bazaar extensions\n *\n * @param routes - Route configuration\n * @returns True if any route has extensions.bazaar defined\n */\nfunction checkIfBazaarNeeded(routes: RoutesConfig): boolean {\n // Handle single route config\n if (\"accepts\" in routes) {\n return !!(routes.extensions && \"bazaar\" in routes.extensions);\n }\n\n // Handle multiple routes\n return Object.values(routes).some(routeConfig => {\n return !!(routeConfig.extensions && \"bazaar\" in routeConfig.extensions);\n });\n}\n\n/**\n * Configuration for registering a payment scheme with a specific network\n */\nexport interface SchemeRegistration {\n /**\n * The network identifier (e.g., 'eip155:84532', 'solana:mainnet')\n */\n network: Network;\n\n /**\n * The scheme server implementation for this network\n */\n server: SchemeNetworkServer;\n}\n\n/**\n * Hono payment middleware for t402 protocol (direct server instance).\n *\n * Use this when you want to pass a pre-configured t402ResourceServer instance.\n * This provides more flexibility for testing, custom configuration, and reusing\n * server instances across multiple middlewares.\n *\n * @param routes - Route configurations for protected endpoints\n * @param server - Pre-configured t402ResourceServer instance\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddleware } from \"@t402/hono\";\n * import { t402ResourceServer } from \"@t402/core/server\";\n * import { registerExactEvmScheme } from \"@t402/evm/exact/server\";\n *\n * const server = new t402ResourceServer(myFacilitatorClient);\n * registerExactEvmScheme(server, {});\n *\n * app.use(paymentMiddleware(routes, server, paywallConfig));\n * ```\n */\nexport function paymentMiddleware(\n routes: RoutesConfig,\n server: t402ResourceServer,\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n // Create the t402 HTTP server instance with the resource server\n const httpServer = new t402HTTPResourceServer(server, routes);\n\n // Register custom paywall provider if provided\n if (paywall) {\n httpServer.registerPaywallProvider(paywall);\n }\n\n // Store initialization promise (not the result)\n // httpServer.initialize() fetches facilitator support and validates routes\n let initPromise: Promise<void> | null = syncFacilitatorOnStart ? httpServer.initialize() : null;\n\n // Dynamically register bazaar extension if routes declare it\n let bazaarPromise: Promise<void> | null = null;\n if (checkIfBazaarNeeded(routes)) {\n bazaarPromise = import(\"@t402/extensions/bazaar\")\n .then(({ bazaarResourceServerExtension }) => {\n server.registerExtension(bazaarResourceServerExtension);\n })\n .catch(err => {\n console.error(\"Failed to load bazaar extension:\", err);\n });\n }\n\n return async (c: Context, next: () => Promise<void>) => {\n // Create adapter and context\n const adapter = new HonoAdapter(c);\n const context: HTTPRequestContext = {\n adapter,\n path: c.req.path,\n method: c.req.method,\n paymentHeader: adapter.getHeader(\"payment-signature\") || adapter.getHeader(\"x-payment\"),\n };\n\n // Check if route requires payment before initializing facilitator\n if (!httpServer.requiresPayment(context)) {\n return next();\n }\n\n // Only initialize when processing a protected route\n if (initPromise) {\n await initPromise;\n initPromise = null; // Clear after first await\n }\n\n // Await bazaar extension loading if needed\n if (bazaarPromise) {\n await bazaarPromise;\n bazaarPromise = null;\n }\n\n // Process payment requirement check\n const result = await httpServer.processHTTPRequest(context, paywallConfig);\n\n // Handle the different result types\n switch (result.type) {\n case \"no-payment-required\":\n // No payment needed, proceed directly to the route handler\n return next();\n\n case \"payment-error\":\n // Payment required but not provided or invalid\n const { response } = result;\n Object.entries(response.headers).forEach(([key, value]) => {\n c.header(key, value);\n });\n if (response.isHtml) {\n return c.html(response.body as string, response.status as 402);\n } else {\n return c.json(response.body || {}, response.status as 402);\n }\n\n case \"payment-verified\":\n // Payment is valid — settle BEFORE executing handler to prevent\n // side effects from leaking on settlement failure.\n const { paymentPayload, paymentRequirements } = result;\n\n // Settle payment first\n try {\n const settleResult = await httpServer.processSettlement(\n paymentPayload,\n paymentRequirements,\n );\n\n if (!settleResult.success) {\n return c.json(\n {\n error: \"Settlement failed\",\n details: settleResult.errorReason,\n },\n 402,\n );\n }\n\n // Settlement succeeded — now execute handler\n await next();\n\n // Add settlement headers to response\n let res = c.res;\n c.res = undefined;\n Object.entries(settleResult.headers).forEach(([key, value]) => {\n res.headers.set(key, value);\n });\n c.res = res;\n } catch (error) {\n console.error(error);\n return c.json(\n {\n error: \"Settlement failed\",\n details: error instanceof Error ? error.message : \"Unknown error\",\n },\n 402,\n );\n }\n return;\n }\n };\n}\n\n/**\n * Hono payment middleware for t402 protocol (configuration-based).\n *\n * Use this when you want to quickly set up middleware with simple configuration.\n * This function creates and configures the t402ResourceServer internally.\n *\n * @param routes - Route configurations for protected endpoints\n * @param facilitatorClients - Optional facilitator client(s) for payment processing\n * @param schemes - Optional array of scheme registrations for server-side payment processing\n * @param paywallConfig - Optional configuration for the built-in paywall UI\n * @param paywall - Optional custom paywall provider (overrides default)\n * @param syncFacilitatorOnStart - Whether to sync with the facilitator on startup (defaults to true)\n * @returns Hono middleware handler\n *\n * @example\n * ```typescript\n * import { paymentMiddlewareFromConfig } from \"@t402/hono\";\n *\n * app.use(paymentMiddlewareFromConfig(\n * routes,\n * myFacilitatorClient,\n * [{ network: \"eip155:8453\", server: evmSchemeServer }],\n * paywallConfig\n * ));\n * ```\n */\nexport function paymentMiddlewareFromConfig(\n routes: RoutesConfig,\n facilitatorClients?: FacilitatorClient | FacilitatorClient[],\n schemes?: SchemeRegistration[],\n paywallConfig?: PaywallConfig,\n paywall?: PaywallProvider,\n syncFacilitatorOnStart: boolean = true,\n): MiddlewareHandler {\n const ResourceServer = new t402ResourceServer(facilitatorClients);\n\n if (schemes) {\n schemes.forEach(({ network, server: schemeServer }) => {\n ResourceServer.register(network, schemeServer);\n });\n }\n\n // Use the direct paymentMiddleware with the configured server\n // Note: paymentMiddleware handles dynamic bazaar registration\n return paymentMiddleware(routes, ResourceServer, paywallConfig, paywall, syncFacilitatorOnStart);\n}\n\nexport { t402ResourceServer, t402HTTPResourceServer } from \"@t402/core/server\";\n\nexport type {\n PaymentRequired,\n PaymentRequirements,\n PaymentPayload,\n Network,\n SchemeNetworkServer,\n} from \"@t402/core/types\";\n\nexport type { PaywallProvider, PaywallConfig } from \"@t402/core/server\";\n\nexport { RouteConfigurationError } from \"@t402/core/server\";\n\nexport type { RouteValidationError } from \"@t402/core/server\";\n\nexport { HonoAdapter } from \"./adapter\";\n","import { HTTPAdapter } from \"@t402/core/server\";\nimport { Context } from \"hono\";\n\n/**\n * Hono adapter implementation\n */\nexport class HonoAdapter implements HTTPAdapter {\n /**\n * Creates a new HonoAdapter instance.\n *\n * @param c - The Hono context object\n */\n constructor(private c: Context) {}\n\n /**\n * Gets a header value from the request.\n *\n * @param name - The header name\n * @returns The header value or undefined\n */\n getHeader(name: string): string | undefined {\n return this.c.req.header(name);\n }\n\n /**\n * Gets the HTTP method of the request.\n *\n * @returns The HTTP method\n */\n getMethod(): string {\n return this.c.req.method;\n }\n\n /**\n * Gets the path of the request.\n *\n * @returns The request path\n */\n getPath(): string {\n return this.c.req.path;\n }\n\n /**\n * Gets the full URL of the request.\n *\n * @returns The full request URL\n */\n getUrl(): string {\n return this.c.req.url;\n }\n\n /**\n * Gets the Accept header from the request.\n *\n * @returns The Accept header value or empty string\n */\n getAcceptHeader(): string {\n return this.c.req.header(\"Accept\") || \"\";\n }\n\n /**\n * Gets the User-Agent header from the request.\n *\n * @returns The User-Agent header value or empty string\n */\n getUserAgent(): string {\n return this.c.req.header(\"User-Agent\") || \"\";\n }\n\n /**\n * Gets all query parameters from the request URL.\n *\n * @returns Record of query parameter key-value pairs\n */\n getQueryParams(): Record<string, string | string[]> {\n const query = this.c.req.query();\n // Convert single values to match the interface\n const result: Record<string, string | string[]> = {};\n for (const [key, value] of Object.entries(query)) {\n result[key] = value;\n }\n return result;\n }\n\n /**\n * Gets a specific query parameter by name.\n *\n * @param name - The query parameter name\n * @returns The query parameter value(s) or undefined\n */\n getQueryParam(name: string): string | string[] | undefined {\n return this.c.req.query(name);\n }\n\n /**\n * Gets the parsed request body.\n * Requires appropriate body parsing middleware.\n *\n * @returns The parsed request body\n */\n async getBody(): Promise<unknown> {\n try {\n return await this.c.req.json();\n } catch {\n return undefined;\n }\n }\n}\n"],"mappings":"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","names":["t402ResourceServer","t402HTTPResourceServer"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@t402/hono",
|
|
3
|
-
"version": "2.8.
|
|
3
|
+
"version": "2.8.1",
|
|
4
4
|
"main": "./dist/cjs/index.js",
|
|
5
5
|
"module": "./dist/esm/index.js",
|
|
6
6
|
"types": "./dist/index.d.ts",
|
|
@@ -23,30 +23,30 @@
|
|
|
23
23
|
"description": "Hono middleware for T402 HTTP 402 payment protocol",
|
|
24
24
|
"devDependencies": {
|
|
25
25
|
"@eslint/js": "^10.0.1",
|
|
26
|
-
"@types/node": "^25.
|
|
27
|
-
"@typescript-eslint/eslint-plugin": "^8.
|
|
28
|
-
"@typescript-eslint/parser": "^8.
|
|
29
|
-
"eslint": "^10.0
|
|
26
|
+
"@types/node": "^25.5.2",
|
|
27
|
+
"@typescript-eslint/eslint-plugin": "^8.58.0",
|
|
28
|
+
"@typescript-eslint/parser": "^8.58.0",
|
|
29
|
+
"eslint": "^10.2.0",
|
|
30
30
|
"eslint-plugin-import": "^2.31.0",
|
|
31
|
-
"eslint-plugin-jsdoc": "^62.
|
|
31
|
+
"eslint-plugin-jsdoc": "^62.9.0",
|
|
32
32
|
"eslint-plugin-prettier": "^5.5.5",
|
|
33
33
|
"glob": "^13.0.6",
|
|
34
|
-
"hono": "^4.12.
|
|
34
|
+
"hono": "^4.12.10",
|
|
35
35
|
"prettier": "3.8.1",
|
|
36
36
|
"tsup": "^8.5.1",
|
|
37
37
|
"tsx": "^4.21.0",
|
|
38
38
|
"typescript": "^5.9.3",
|
|
39
|
-
"vite": "^
|
|
39
|
+
"vite": "^8.0.3",
|
|
40
40
|
"vite-tsconfig-paths": "^6.1.1",
|
|
41
41
|
"vitest": "^3.2.4"
|
|
42
42
|
},
|
|
43
43
|
"dependencies": {
|
|
44
|
-
"@t402/core": "2.
|
|
45
|
-
"@t402/extensions": "2.8.
|
|
44
|
+
"@t402/core": "2.9.0",
|
|
45
|
+
"@t402/extensions": "2.8.1"
|
|
46
46
|
},
|
|
47
47
|
"peerDependencies": {
|
|
48
48
|
"hono": "^4.0.0",
|
|
49
|
-
"@t402/paywall": "2.8.
|
|
49
|
+
"@t402/paywall": "2.8.1"
|
|
50
50
|
},
|
|
51
51
|
"peerDependenciesMeta": {
|
|
52
52
|
"@t402/paywall": {
|