mppx 0.0.1 → 0.1.0
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/LICENSE +21 -0
- package/README.md +195 -0
- package/dist/BodyDigest.d.ts +42 -0
- package/dist/BodyDigest.d.ts.map +1 -0
- package/dist/BodyDigest.js +40 -0
- package/dist/BodyDigest.js.map +1 -0
- package/dist/Challenge.d.ts +271 -0
- package/dist/Challenge.d.ts.map +1 -0
- package/dist/Challenge.js +291 -0
- package/dist/Challenge.js.map +1 -0
- package/dist/Credential.d.ts +91 -0
- package/dist/Credential.d.ts.map +1 -0
- package/dist/Credential.js +122 -0
- package/dist/Credential.js.map +1 -0
- package/dist/Errors.d.ts +243 -0
- package/dist/Errors.d.ts.map +1 -0
- package/dist/Errors.js +201 -0
- package/dist/Errors.js.map +1 -0
- package/dist/Expires.d.ts +15 -0
- package/dist/Expires.d.ts.map +1 -0
- package/dist/Expires.js +29 -0
- package/dist/Expires.js.map +1 -0
- package/dist/Intent.d.ts +101 -0
- package/dist/Intent.d.ts.map +1 -0
- package/dist/Intent.js +83 -0
- package/dist/Intent.js.map +1 -0
- package/dist/Mcp.d.ts +74 -0
- package/dist/Mcp.d.ts.map +1 -0
- package/dist/Mcp.js +9 -0
- package/dist/Mcp.js.map +1 -0
- package/dist/MethodIntent.d.ts +225 -0
- package/dist/MethodIntent.d.ts.map +1 -0
- package/dist/MethodIntent.js +156 -0
- package/dist/MethodIntent.js.map +1 -0
- package/dist/PaymentRequest.d.ts +88 -0
- package/dist/PaymentRequest.d.ts.map +1 -0
- package/dist/PaymentRequest.js +81 -0
- package/dist/PaymentRequest.js.map +1 -0
- package/dist/Receipt.d.ts +110 -0
- package/dist/Receipt.d.ts.map +1 -0
- package/dist/Receipt.js +105 -0
- package/dist/Receipt.js.map +1 -0
- package/dist/Store.d.ts +28 -0
- package/dist/Store.d.ts.map +1 -0
- package/dist/Store.js +61 -0
- package/dist/Store.js.map +1 -0
- package/dist/cli.d.ts +3 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +1219 -0
- package/dist/cli.js.map +1 -0
- package/dist/client/Methods.d.ts +4 -0
- package/dist/client/Methods.d.ts.map +1 -0
- package/dist/client/Methods.js +4 -0
- package/dist/client/Methods.js.map +1 -0
- package/dist/client/Mppx.d.ts +84 -0
- package/dist/client/Mppx.d.ts.map +1 -0
- package/dist/client/Mppx.js +64 -0
- package/dist/client/Mppx.js.map +1 -0
- package/dist/client/Transport.d.ts +56 -0
- package/dist/client/Transport.d.ts.map +1 -0
- package/dist/client/Transport.js +81 -0
- package/dist/client/Transport.js.map +1 -0
- package/dist/client/index.d.ts +5 -0
- package/dist/client/index.d.ts.map +1 -0
- package/dist/client/index.js +5 -0
- package/dist/client/index.js.map +1 -0
- package/dist/client/internal/Fetch.d.ts +85 -0
- package/dist/client/internal/Fetch.d.ts.map +1 -0
- package/dist/client/internal/Fetch.js +95 -0
- package/dist/client/internal/Fetch.js.map +1 -0
- package/dist/index.d.ts +13 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +13 -0
- package/dist/index.js.map +1 -0
- package/dist/internal/types.d.ts +302 -0
- package/dist/internal/types.d.ts.map +1 -0
- package/dist/internal/types.js +2 -0
- package/dist/internal/types.js.map +1 -0
- package/dist/mcp-sdk/client/McpClient.d.ts +78 -0
- package/dist/mcp-sdk/client/McpClient.d.ts.map +1 -0
- package/dist/mcp-sdk/client/McpClient.js +98 -0
- package/dist/mcp-sdk/client/McpClient.js.map +1 -0
- package/dist/mcp-sdk/client/index.d.ts +3 -0
- package/dist/mcp-sdk/client/index.d.ts.map +1 -0
- package/dist/mcp-sdk/client/index.js +3 -0
- package/dist/mcp-sdk/client/index.js.map +1 -0
- package/dist/mcp-sdk/server/Transport.d.ts +43 -0
- package/dist/mcp-sdk/server/Transport.d.ts.map +1 -0
- package/dist/mcp-sdk/server/Transport.js +71 -0
- package/dist/mcp-sdk/server/Transport.js.map +1 -0
- package/dist/mcp-sdk/server/index.d.ts +2 -0
- package/dist/mcp-sdk/server/index.d.ts.map +1 -0
- package/dist/mcp-sdk/server/index.js +2 -0
- package/dist/mcp-sdk/server/index.js.map +1 -0
- package/dist/middlewares/elysia.d.ts +51 -0
- package/dist/middlewares/elysia.d.ts.map +1 -0
- package/dist/middlewares/elysia.js +59 -0
- package/dist/middlewares/elysia.js.map +1 -0
- package/dist/middlewares/express.d.ts +46 -0
- package/dist/middlewares/express.d.ts.map +1 -0
- package/dist/middlewares/express.js +69 -0
- package/dist/middlewares/express.js.map +1 -0
- package/dist/middlewares/hono.d.ts +46 -0
- package/dist/middlewares/hono.d.ts.map +1 -0
- package/dist/middlewares/hono.js +57 -0
- package/dist/middlewares/hono.js.map +1 -0
- package/dist/middlewares/internal/mppx.d.ts +16 -0
- package/dist/middlewares/internal/mppx.d.ts.map +1 -0
- package/dist/middlewares/internal/mppx.js +16 -0
- package/dist/middlewares/internal/mppx.js.map +1 -0
- package/dist/middlewares/nextjs.d.ts +45 -0
- package/dist/middlewares/nextjs.d.ts.map +1 -0
- package/dist/middlewares/nextjs.js +57 -0
- package/dist/middlewares/nextjs.js.map +1 -0
- package/dist/proxy/Proxy.d.ts +47 -0
- package/dist/proxy/Proxy.d.ts.map +1 -0
- package/dist/proxy/Proxy.js +126 -0
- package/dist/proxy/Proxy.js.map +1 -0
- package/dist/proxy/Service.d.ts +100 -0
- package/dist/proxy/Service.d.ts.map +1 -0
- package/dist/proxy/Service.js +147 -0
- package/dist/proxy/Service.js.map +1 -0
- package/dist/proxy/index.d.ts +7 -0
- package/dist/proxy/index.d.ts.map +1 -0
- package/dist/proxy/index.js +7 -0
- package/dist/proxy/index.js.map +1 -0
- package/dist/proxy/internal/Headers.d.ts +3 -0
- package/dist/proxy/internal/Headers.d.ts.map +1 -0
- package/dist/proxy/internal/Headers.js +41 -0
- package/dist/proxy/internal/Headers.js.map +1 -0
- package/dist/proxy/internal/Route.d.ts +14 -0
- package/dist/proxy/internal/Route.d.ts.map +1 -0
- package/dist/proxy/internal/Route.js +47 -0
- package/dist/proxy/internal/Route.js.map +1 -0
- package/dist/proxy/services/anthropic.d.ts +29 -0
- package/dist/proxy/services/anthropic.d.ts.map +1 -0
- package/dist/proxy/services/anthropic.js +30 -0
- package/dist/proxy/services/anthropic.js.map +1 -0
- package/dist/proxy/services/openai.d.ts +29 -0
- package/dist/proxy/services/openai.d.ts.map +1 -0
- package/dist/proxy/services/openai.js +30 -0
- package/dist/proxy/services/openai.js.map +1 -0
- package/dist/proxy/services/stripe.d.ts +29 -0
- package/dist/proxy/services/stripe.d.ts.map +1 -0
- package/dist/proxy/services/stripe.js +30 -0
- package/dist/proxy/services/stripe.js.map +1 -0
- package/dist/server/Methods.d.ts +3 -0
- package/dist/server/Methods.d.ts.map +1 -0
- package/dist/server/Methods.js +3 -0
- package/dist/server/Methods.js.map +1 -0
- package/dist/server/Mppx.d.ts +116 -0
- package/dist/server/Mppx.d.ts.map +1 -0
- package/dist/server/Mppx.js +207 -0
- package/dist/server/Mppx.js.map +1 -0
- package/dist/server/NodeListener.d.ts +3 -0
- package/dist/server/NodeListener.d.ts.map +1 -0
- package/dist/server/NodeListener.js +3 -0
- package/dist/server/NodeListener.js.map +1 -0
- package/dist/server/Request.d.ts +24 -0
- package/dist/server/Request.d.ts.map +1 -0
- package/dist/server/Request.js +26 -0
- package/dist/server/Request.js.map +1 -0
- package/dist/server/Response.d.ts +10 -0
- package/dist/server/Response.d.ts.map +1 -0
- package/dist/server/Response.js +15 -0
- package/dist/server/Response.js.map +1 -0
- package/dist/server/Transport.d.ts +93 -0
- package/dist/server/Transport.d.ts.map +1 -0
- package/dist/server/Transport.js +132 -0
- package/dist/server/Transport.js.map +1 -0
- package/dist/server/index.d.ts +9 -0
- package/dist/server/index.d.ts.map +1 -0
- package/dist/server/index.js +9 -0
- package/dist/server/index.js.map +1 -0
- package/dist/stripe/Intents.d.ts +54 -0
- package/dist/stripe/Intents.d.ts.map +1 -0
- package/dist/stripe/Intents.js +27 -0
- package/dist/stripe/Intents.js.map +1 -0
- package/dist/stripe/client/Charge.d.ts +114 -0
- package/dist/stripe/client/Charge.d.ts.map +1 -0
- package/dist/stripe/client/Charge.js +77 -0
- package/dist/stripe/client/Charge.js.map +1 -0
- package/dist/stripe/client/MethodIntents.d.ts +80 -0
- package/dist/stripe/client/MethodIntents.d.ts.map +1 -0
- package/dist/stripe/client/MethodIntents.js +34 -0
- package/dist/stripe/client/MethodIntents.js.map +1 -0
- package/dist/stripe/client/index.d.ts +3 -0
- package/dist/stripe/client/index.d.ts.map +1 -0
- package/dist/stripe/client/index.js +3 -0
- package/dist/stripe/client/index.js.map +1 -0
- package/dist/stripe/index.d.ts +2 -0
- package/dist/stripe/index.d.ts.map +1 -0
- package/dist/stripe/index.js +2 -0
- package/dist/stripe/index.js.map +1 -0
- package/dist/stripe/server/Charge.d.ts +74 -0
- package/dist/stripe/server/Charge.d.ts.map +1 -0
- package/dist/stripe/server/Charge.js +79 -0
- package/dist/stripe/server/Charge.js.map +1 -0
- package/dist/stripe/server/MethodIntents.d.ts +65 -0
- package/dist/stripe/server/MethodIntents.d.ts.map +1 -0
- package/dist/stripe/server/MethodIntents.js +21 -0
- package/dist/stripe/server/MethodIntents.js.map +1 -0
- package/dist/stripe/server/index.d.ts +3 -0
- package/dist/stripe/server/index.d.ts.map +1 -0
- package/dist/stripe/server/index.js +3 -0
- package/dist/stripe/server/index.js.map +1 -0
- package/dist/tempo/Attribution.d.ts +101 -0
- package/dist/tempo/Attribution.d.ts.map +1 -0
- package/dist/tempo/Attribution.js +124 -0
- package/dist/tempo/Attribution.js.map +1 -0
- package/dist/tempo/Intents.d.ts +132 -0
- package/dist/tempo/Intents.d.ts.map +1 -0
- package/dist/tempo/Intents.js +81 -0
- package/dist/tempo/Intents.js.map +1 -0
- package/dist/tempo/client/ChannelOps.d.ts +54 -0
- package/dist/tempo/client/ChannelOps.d.ts.map +1 -0
- package/dist/tempo/client/ChannelOps.js +138 -0
- package/dist/tempo/client/ChannelOps.js.map +1 -0
- package/dist/tempo/client/Charge.d.ts +76 -0
- package/dist/tempo/client/Charge.d.ts.map +1 -0
- package/dist/tempo/client/Charge.js +69 -0
- package/dist/tempo/client/Charge.js.map +1 -0
- package/dist/tempo/client/MethodIntents.d.ts +157 -0
- package/dist/tempo/client/MethodIntents.d.ts.map +1 -0
- package/dist/tempo/client/MethodIntents.js +25 -0
- package/dist/tempo/client/MethodIntents.js.map +1 -0
- package/dist/tempo/client/Session.d.ts +159 -0
- package/dist/tempo/client/Session.d.ts.map +1 -0
- package/dist/tempo/client/Session.js +263 -0
- package/dist/tempo/client/Session.js.map +1 -0
- package/dist/tempo/client/SessionManager.d.ts +62 -0
- package/dist/tempo/client/SessionManager.d.ts.map +1 -0
- package/dist/tempo/client/SessionManager.js +196 -0
- package/dist/tempo/client/SessionManager.js.map +1 -0
- package/dist/tempo/client/index.d.ts +6 -0
- package/dist/tempo/client/index.d.ts.map +1 -0
- package/dist/tempo/client/index.js +5 -0
- package/dist/tempo/client/index.js.map +1 -0
- package/dist/tempo/index.d.ts +3 -0
- package/dist/tempo/index.d.ts.map +1 -0
- package/dist/tempo/index.js +3 -0
- package/dist/tempo/index.js.map +1 -0
- package/dist/tempo/internal/account.d.ts +32 -0
- package/dist/tempo/internal/account.d.ts.map +1 -0
- package/dist/tempo/internal/account.js +33 -0
- package/dist/tempo/internal/account.js.map +1 -0
- package/dist/tempo/internal/defaults.d.ts +18 -0
- package/dist/tempo/internal/defaults.d.ts.map +1 -0
- package/dist/tempo/internal/defaults.js +18 -0
- package/dist/tempo/internal/defaults.js.map +1 -0
- package/dist/tempo/internal/types.d.ts +11 -0
- package/dist/tempo/internal/types.d.ts.map +1 -0
- package/dist/tempo/internal/types.js +2 -0
- package/dist/tempo/internal/types.js.map +1 -0
- package/dist/tempo/server/Charge.d.ts +77 -0
- package/dist/tempo/server/Charge.d.ts.map +1 -0
- package/dist/tempo/server/Charge.js +228 -0
- package/dist/tempo/server/Charge.js.map +1 -0
- package/dist/tempo/server/MethodIntents.d.ts +140 -0
- package/dist/tempo/server/MethodIntents.d.ts.map +1 -0
- package/dist/tempo/server/MethodIntents.js +26 -0
- package/dist/tempo/server/MethodIntents.js.map +1 -0
- package/dist/tempo/server/Session.d.ts +148 -0
- package/dist/tempo/server/Session.d.ts.map +1 -0
- package/dist/tempo/server/Session.js +529 -0
- package/dist/tempo/server/Session.js.map +1 -0
- package/dist/tempo/server/internal/transport.d.ts +47 -0
- package/dist/tempo/server/internal/transport.d.ts.map +1 -0
- package/dist/tempo/server/internal/transport.js +118 -0
- package/dist/tempo/server/internal/transport.js.map +1 -0
- package/dist/tempo/stream/Chain.d.ts +52 -0
- package/dist/tempo/stream/Chain.d.ts.map +1 -0
- package/dist/tempo/stream/Chain.js +215 -0
- package/dist/tempo/stream/Chain.js.map +1 -0
- package/dist/tempo/stream/Channel.d.ts +26 -0
- package/dist/tempo/stream/Channel.d.ts.map +1 -0
- package/dist/tempo/stream/Channel.js +27 -0
- package/dist/tempo/stream/Channel.js.map +1 -0
- package/dist/tempo/stream/ChannelStore.d.ts +103 -0
- package/dist/tempo/stream/ChannelStore.d.ts.map +1 -0
- package/dist/tempo/stream/ChannelStore.js +100 -0
- package/dist/tempo/stream/ChannelStore.js.map +1 -0
- package/dist/tempo/stream/Receipt.d.ts +22 -0
- package/dist/tempo/stream/Receipt.d.ts.map +1 -0
- package/dist/tempo/stream/Receipt.js +34 -0
- package/dist/tempo/stream/Receipt.js.map +1 -0
- package/dist/tempo/stream/Sse.d.ts +134 -0
- package/dist/tempo/stream/Sse.d.ts.map +1 -0
- package/dist/tempo/stream/Sse.js +288 -0
- package/dist/tempo/stream/Sse.js.map +1 -0
- package/dist/tempo/stream/Types.d.ts +78 -0
- package/dist/tempo/stream/Types.d.ts.map +1 -0
- package/dist/tempo/stream/Types.js +2 -0
- package/dist/tempo/stream/Types.js.map +1 -0
- package/dist/tempo/stream/Voucher.d.ts +20 -0
- package/dist/tempo/stream/Voucher.d.ts.map +1 -0
- package/dist/tempo/stream/Voucher.js +98 -0
- package/dist/tempo/stream/Voucher.js.map +1 -0
- package/dist/tempo/stream/escrow.abi.d.ts +598 -0
- package/dist/tempo/stream/escrow.abi.d.ts.map +1 -0
- package/dist/tempo/stream/escrow.abi.js +760 -0
- package/dist/tempo/stream/escrow.abi.js.map +1 -0
- package/dist/tempo/stream/index.d.ts +8 -0
- package/dist/tempo/stream/index.d.ts.map +1 -0
- package/dist/tempo/stream/index.js +8 -0
- package/dist/tempo/stream/index.js.map +1 -0
- package/dist/viem/Account.d.ts +12 -0
- package/dist/viem/Account.d.ts.map +1 -0
- package/dist/viem/Account.js +14 -0
- package/dist/viem/Account.js.map +1 -0
- package/dist/viem/Client.d.ts +21 -0
- package/dist/viem/Client.d.ts.map +1 -0
- package/dist/viem/Client.js +19 -0
- package/dist/viem/Client.js.map +1 -0
- package/dist/zod.d.ts +17 -0
- package/dist/zod.d.ts.map +1 -0
- package/dist/zod.js +35 -0
- package/dist/zod.js.map +1 -0
- package/package.json +117 -4
- package/src/BodyDigest.test.ts +43 -0
- package/src/BodyDigest.ts +53 -0
- package/src/Challenge.test-d.ts +81 -0
- package/src/Challenge.test.ts +414 -0
- package/src/Challenge.ts +429 -0
- package/src/Credential.test.ts +227 -0
- package/src/Credential.ts +154 -0
- package/src/Errors.test.ts +402 -0
- package/src/Errors.ts +348 -0
- package/src/Expires.ts +34 -0
- package/src/Intent.test.ts +180 -0
- package/src/Intent.ts +109 -0
- package/src/Mcp.ts +81 -0
- package/src/MethodIntent.test.ts +303 -0
- package/src/MethodIntent.ts +388 -0
- package/src/PaymentRequest.test.ts +152 -0
- package/src/PaymentRequest.ts +107 -0
- package/src/Receipt.test.ts +98 -0
- package/src/Receipt.ts +129 -0
- package/src/Store.ts +84 -0
- package/src/cli.test.ts +542 -0
- package/src/cli.ts +1319 -0
- package/src/client/Methods.ts +3 -0
- package/src/client/Mppx.test-d.ts +90 -0
- package/src/client/Mppx.test.ts +468 -0
- package/src/client/Mppx.ts +149 -0
- package/src/client/Transport.test.ts +283 -0
- package/src/client/Transport.ts +115 -0
- package/src/client/index.ts +4 -0
- package/src/client/internal/Fetch.test-d.ts +57 -0
- package/src/client/internal/Fetch.test.ts +281 -0
- package/src/client/internal/Fetch.ts +157 -0
- package/src/env.d.ts +11 -0
- package/src/index.ts +12 -0
- package/src/internal/types.ts +403 -0
- package/src/mcp-sdk/client/McpClient.test-d.ts +109 -0
- package/src/mcp-sdk/client/McpClient.test.ts +219 -0
- package/src/mcp-sdk/client/McpClient.ts +187 -0
- package/src/mcp-sdk/client/index.ts +2 -0
- package/src/mcp-sdk/server/Transport.ts +94 -0
- package/src/mcp-sdk/server/index.ts +1 -0
- package/src/middlewares/elysia.ts +66 -0
- package/src/middlewares/express.test.ts +155 -0
- package/src/middlewares/express.ts +82 -0
- package/src/middlewares/hono.test.ts +148 -0
- package/src/middlewares/hono.ts +62 -0
- package/src/middlewares/internal/mppx.ts +30 -0
- package/src/middlewares/nextjs.test.ts +164 -0
- package/src/middlewares/nextjs.ts +66 -0
- package/src/proxy/Proxy.test.ts +472 -0
- package/src/proxy/Proxy.ts +175 -0
- package/src/proxy/Service.test.ts +125 -0
- package/src/proxy/Service.ts +227 -0
- package/src/proxy/index.ts +6 -0
- package/src/proxy/internal/Headers.test.ts +100 -0
- package/src/proxy/internal/Headers.ts +40 -0
- package/src/proxy/internal/Route.test.ts +143 -0
- package/src/proxy/internal/Route.ts +54 -0
- package/src/proxy/services/anthropic.ts +45 -0
- package/src/proxy/services/openai.test.ts +97 -0
- package/src/proxy/services/openai.ts +48 -0
- package/src/proxy/services/stripe.ts +49 -0
- package/src/server/Methods.ts +2 -0
- package/src/server/Mppx.test-d.ts +343 -0
- package/src/server/Mppx.test.ts +342 -0
- package/src/server/Mppx.ts +378 -0
- package/src/server/NodeListener.test.ts +188 -0
- package/src/server/NodeListener.ts +3 -0
- package/src/server/Request.test.ts +102 -0
- package/src/server/Request.ts +33 -0
- package/src/server/Response.test.ts +31 -0
- package/src/server/Response.ts +27 -0
- package/src/server/Transport.test.ts +294 -0
- package/src/server/Transport.ts +222 -0
- package/src/server/index.ts +8 -0
- package/src/stripe/Charge.integration.test.ts +326 -0
- package/src/stripe/Intents.test.ts +52 -0
- package/src/stripe/Intents.ts +27 -0
- package/src/stripe/client/Charge.ts +119 -0
- package/src/stripe/client/MethodIntents.ts +37 -0
- package/src/stripe/client/index.ts +2 -0
- package/src/stripe/index.ts +1 -0
- package/src/stripe/server/Charge.ts +121 -0
- package/src/stripe/server/MethodIntents.ts +24 -0
- package/src/stripe/server/index.ts +2 -0
- package/src/tempo/Attribution.test.ts +187 -0
- package/src/tempo/Attribution.ts +156 -0
- package/src/tempo/Intents.test.ts +84 -0
- package/src/tempo/Intents.ts +93 -0
- package/src/tempo/client/ChannelOps.ts +233 -0
- package/src/tempo/client/Charge.ts +84 -0
- package/src/tempo/client/MethodIntents.ts +28 -0
- package/src/tempo/client/Session.ts +369 -0
- package/src/tempo/client/SessionManager.test.ts +223 -0
- package/src/tempo/client/SessionManager.ts +270 -0
- package/src/tempo/client/index.ts +5 -0
- package/src/tempo/index.ts +2 -0
- package/src/tempo/internal/account.ts +47 -0
- package/src/tempo/internal/defaults.ts +20 -0
- package/src/tempo/internal/types.ts +8 -0
- package/src/tempo/server/Charge.test.ts +847 -0
- package/src/tempo/server/Charge.ts +309 -0
- package/src/tempo/server/MethodIntents.ts +29 -0
- package/src/tempo/server/Session.test.ts +1349 -0
- package/src/tempo/server/Session.ts +773 -0
- package/src/tempo/server/Sse.test.ts +289 -0
- package/src/tempo/server/index.ts +5 -0
- package/src/tempo/server/internal/transport.ts +153 -0
- package/src/tempo/stream/Chain.ts +333 -0
- package/src/tempo/stream/Channel.ts +50 -0
- package/src/tempo/stream/ChannelStore.test.ts +473 -0
- package/src/tempo/stream/ChannelStore.ts +202 -0
- package/src/tempo/stream/Receipt.test.ts +84 -0
- package/src/tempo/stream/Receipt.ts +45 -0
- package/src/tempo/stream/Sse.test.ts +401 -0
- package/src/tempo/stream/Sse.ts +375 -0
- package/src/tempo/stream/Types.ts +86 -0
- package/src/tempo/stream/Voucher.test.ts +134 -0
- package/src/tempo/stream/Voucher.ts +123 -0
- package/src/tempo/stream/escrow.abi.ts +759 -0
- package/src/tempo/stream/index.ts +7 -0
- package/src/tsconfig.json +10 -0
- package/src/viem/Account.test.ts +71 -0
- package/src/viem/Account.ts +30 -0
- package/src/viem/Client.test.ts +58 -0
- package/src/viem/Client.ts +33 -0
- package/src/zod.ts +47 -0
|
@@ -0,0 +1,289 @@
|
|
|
1
|
+
import type { Address, Hex } from 'viem'
|
|
2
|
+
import { describe, expect, test } from 'vitest'
|
|
3
|
+
import type * as ChannelStore from '../stream/ChannelStore.js'
|
|
4
|
+
import { serve, toResponse } from '../stream/Sse.js'
|
|
5
|
+
|
|
6
|
+
const channelId = '0x0000000000000000000000000000000000000000000000000000000000000001' as Hex
|
|
7
|
+
const challengeId = 'test-challenge-id'
|
|
8
|
+
const tickCost = 1000000n
|
|
9
|
+
|
|
10
|
+
function memoryStore(): ChannelStore.ChannelStore {
|
|
11
|
+
const channels = new Map()
|
|
12
|
+
return {
|
|
13
|
+
async getChannel(id) {
|
|
14
|
+
return channels.get(id) ?? null
|
|
15
|
+
},
|
|
16
|
+
async updateChannel(id, fn) {
|
|
17
|
+
const result = fn(channels.get(id) ?? null)
|
|
18
|
+
if (result) channels.set(id, result)
|
|
19
|
+
else channels.delete(id)
|
|
20
|
+
return result
|
|
21
|
+
},
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
function seedChannel(
|
|
26
|
+
store: ChannelStore.ChannelStore,
|
|
27
|
+
balance: bigint,
|
|
28
|
+
): Promise<ChannelStore.State | null> {
|
|
29
|
+
return store.updateChannel(channelId, () => ({
|
|
30
|
+
channelId,
|
|
31
|
+
payer: '0x0000000000000000000000000000000000000001' as Address,
|
|
32
|
+
payee: '0x0000000000000000000000000000000000000002' as Address,
|
|
33
|
+
token: '0x0000000000000000000000000000000000000003' as Address,
|
|
34
|
+
authorizedSigner: '0x0000000000000000000000000000000000000004' as Address,
|
|
35
|
+
chainId: 42431,
|
|
36
|
+
escrowContract: '0x542831e3E4Ace07559b7C8787395f4Fb99F70787' as Address,
|
|
37
|
+
deposit: balance,
|
|
38
|
+
settledOnChain: 0n,
|
|
39
|
+
highestVoucherAmount: balance,
|
|
40
|
+
highestVoucher: null,
|
|
41
|
+
spent: 0n,
|
|
42
|
+
units: 0,
|
|
43
|
+
finalized: false,
|
|
44
|
+
createdAt: new Date().toISOString(),
|
|
45
|
+
}))
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
async function readStream(stream: ReadableStream<Uint8Array>): Promise<string> {
|
|
49
|
+
const reader = stream.getReader()
|
|
50
|
+
const decoder = new TextDecoder()
|
|
51
|
+
let result = ''
|
|
52
|
+
while (true) {
|
|
53
|
+
const { done, value } = await reader.read()
|
|
54
|
+
if (done) break
|
|
55
|
+
result += decoder.decode(value, { stream: true })
|
|
56
|
+
}
|
|
57
|
+
return result
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
describe('Sse.serve', () => {
|
|
61
|
+
test('emits message events for each yielded value (StreamController)', async () => {
|
|
62
|
+
const store = memoryStore()
|
|
63
|
+
await seedChannel(store, 3000000n)
|
|
64
|
+
|
|
65
|
+
const response = toResponse(
|
|
66
|
+
serve({
|
|
67
|
+
store,
|
|
68
|
+
channelId,
|
|
69
|
+
challengeId,
|
|
70
|
+
tickCost,
|
|
71
|
+
generate: async function* (stream) {
|
|
72
|
+
await stream.charge()
|
|
73
|
+
yield 'hello'
|
|
74
|
+
await stream.charge()
|
|
75
|
+
yield 'world'
|
|
76
|
+
await stream.charge()
|
|
77
|
+
yield 'done'
|
|
78
|
+
},
|
|
79
|
+
}),
|
|
80
|
+
)
|
|
81
|
+
|
|
82
|
+
expect(response).toBeInstanceOf(Response)
|
|
83
|
+
expect(response.headers.get('Content-Type')).toBe('text/event-stream; charset=utf-8')
|
|
84
|
+
|
|
85
|
+
const output = await readStream(response.body!)
|
|
86
|
+
|
|
87
|
+
expect(output).toContain('event: message\ndata: hello\n\n')
|
|
88
|
+
expect(output).toContain('event: message\ndata: world\n\n')
|
|
89
|
+
expect(output).toContain('event: message\ndata: done\n\n')
|
|
90
|
+
expect(output).toContain('event: payment-receipt\n')
|
|
91
|
+
|
|
92
|
+
const channel = await store.getChannel(channelId)
|
|
93
|
+
expect(channel!.spent).toBe(3000000n)
|
|
94
|
+
expect(channel!.units).toBe(3)
|
|
95
|
+
})
|
|
96
|
+
|
|
97
|
+
test('emits payment-need-voucher when balance exhausted and resumes after top-up', async () => {
|
|
98
|
+
const store = memoryStore()
|
|
99
|
+
await seedChannel(store, 1000000n)
|
|
100
|
+
|
|
101
|
+
const response = toResponse(
|
|
102
|
+
serve({
|
|
103
|
+
store,
|
|
104
|
+
channelId,
|
|
105
|
+
challengeId,
|
|
106
|
+
tickCost,
|
|
107
|
+
pollIntervalMs: 10,
|
|
108
|
+
generate: async function* (stream) {
|
|
109
|
+
await stream.charge()
|
|
110
|
+
yield 'first'
|
|
111
|
+
await stream.charge()
|
|
112
|
+
yield 'second'
|
|
113
|
+
},
|
|
114
|
+
}),
|
|
115
|
+
)
|
|
116
|
+
|
|
117
|
+
const reader = response.body!.getReader()
|
|
118
|
+
const decoder = new TextDecoder()
|
|
119
|
+
const chunks: string[] = []
|
|
120
|
+
|
|
121
|
+
const { value: chunk1 } = await reader.read()
|
|
122
|
+
chunks.push(decoder.decode(chunk1, { stream: true }))
|
|
123
|
+
expect(chunks[0]).toContain('event: message\ndata: first\n\n')
|
|
124
|
+
|
|
125
|
+
const readNext = reader.read().then(({ value }) => {
|
|
126
|
+
const text = decoder.decode(value, { stream: true })
|
|
127
|
+
chunks.push(text)
|
|
128
|
+
return text
|
|
129
|
+
})
|
|
130
|
+
|
|
131
|
+
await new Promise((r) => setTimeout(r, 30))
|
|
132
|
+
|
|
133
|
+
await store.updateChannel(channelId, (current) => {
|
|
134
|
+
if (!current) return null
|
|
135
|
+
return { ...current, highestVoucherAmount: current.highestVoucherAmount + 2000000n }
|
|
136
|
+
})
|
|
137
|
+
|
|
138
|
+
const secondChunk = await readNext
|
|
139
|
+
expect(secondChunk).toContain('event: payment-need-voucher\n')
|
|
140
|
+
|
|
141
|
+
const remaining: string[] = []
|
|
142
|
+
while (true) {
|
|
143
|
+
const { done, value } = await reader.read()
|
|
144
|
+
if (done) break
|
|
145
|
+
remaining.push(decoder.decode(value, { stream: true }))
|
|
146
|
+
}
|
|
147
|
+
const all = remaining.join('')
|
|
148
|
+
expect(all).toContain('event: message\ndata: second\n\n')
|
|
149
|
+
expect(all).toContain('event: payment-receipt\n')
|
|
150
|
+
})
|
|
151
|
+
|
|
152
|
+
test('respects abort signal', async () => {
|
|
153
|
+
const store = memoryStore()
|
|
154
|
+
await seedChannel(store, 10000000n)
|
|
155
|
+
|
|
156
|
+
const controller = new AbortController()
|
|
157
|
+
|
|
158
|
+
const response = toResponse(
|
|
159
|
+
serve({
|
|
160
|
+
store,
|
|
161
|
+
channelId,
|
|
162
|
+
challengeId,
|
|
163
|
+
tickCost,
|
|
164
|
+
signal: controller.signal,
|
|
165
|
+
generate: async function* (stream) {
|
|
166
|
+
let i = 0
|
|
167
|
+
while (true) {
|
|
168
|
+
await stream.charge()
|
|
169
|
+
yield `chunk-${i++}`
|
|
170
|
+
await new Promise((r) => setTimeout(r, 5))
|
|
171
|
+
}
|
|
172
|
+
},
|
|
173
|
+
}),
|
|
174
|
+
)
|
|
175
|
+
|
|
176
|
+
const reader = response.body!.getReader()
|
|
177
|
+
const decoder = new TextDecoder()
|
|
178
|
+
|
|
179
|
+
const { value: first } = await reader.read()
|
|
180
|
+
expect(decoder.decode(first)).toContain('event: message\ndata: chunk-0\n\n')
|
|
181
|
+
|
|
182
|
+
controller.abort()
|
|
183
|
+
|
|
184
|
+
while (true) {
|
|
185
|
+
const { done } = await reader.read()
|
|
186
|
+
if (done) break
|
|
187
|
+
}
|
|
188
|
+
})
|
|
189
|
+
|
|
190
|
+
test('emits receipt with correct spent and units', async () => {
|
|
191
|
+
const store = memoryStore()
|
|
192
|
+
await seedChannel(store, 2000000n)
|
|
193
|
+
|
|
194
|
+
const response = toResponse(
|
|
195
|
+
serve({
|
|
196
|
+
store,
|
|
197
|
+
channelId,
|
|
198
|
+
challengeId,
|
|
199
|
+
tickCost,
|
|
200
|
+
generate: async function* (stream) {
|
|
201
|
+
await stream.charge()
|
|
202
|
+
yield 'a'
|
|
203
|
+
await stream.charge()
|
|
204
|
+
yield 'b'
|
|
205
|
+
},
|
|
206
|
+
}),
|
|
207
|
+
)
|
|
208
|
+
|
|
209
|
+
const output = await readStream(response.body!)
|
|
210
|
+
const receiptRaw = output.split('event: payment-receipt\ndata: ')[1]?.split('\n\n')[0]
|
|
211
|
+
const receipt = JSON.parse(receiptRaw!)
|
|
212
|
+
|
|
213
|
+
expect(receipt.challengeId).toBe('test-challenge-id')
|
|
214
|
+
expect(receipt.channelId).toBe(channelId)
|
|
215
|
+
expect(receipt.spent).toBe('2000000')
|
|
216
|
+
expect(receipt.units).toBe(2)
|
|
217
|
+
})
|
|
218
|
+
|
|
219
|
+
test('handles empty generator', async () => {
|
|
220
|
+
const store = memoryStore()
|
|
221
|
+
await seedChannel(store, 1000000n)
|
|
222
|
+
|
|
223
|
+
const response = toResponse(
|
|
224
|
+
serve({
|
|
225
|
+
store,
|
|
226
|
+
channelId,
|
|
227
|
+
challengeId,
|
|
228
|
+
tickCost,
|
|
229
|
+
generate: async function* () {},
|
|
230
|
+
}),
|
|
231
|
+
)
|
|
232
|
+
|
|
233
|
+
const output = await readStream(response.body!)
|
|
234
|
+
expect(output).toContain('event: payment-receipt\n')
|
|
235
|
+
expect(output).not.toContain('event: message\n')
|
|
236
|
+
|
|
237
|
+
const channel = await store.getChannel(channelId)
|
|
238
|
+
expect(channel!.spent).toBe(0n)
|
|
239
|
+
expect(channel!.units).toBe(0)
|
|
240
|
+
})
|
|
241
|
+
|
|
242
|
+
test('allows tickCost override', async () => {
|
|
243
|
+
const store = memoryStore()
|
|
244
|
+
await seedChannel(store, 500n)
|
|
245
|
+
|
|
246
|
+
const response = toResponse(
|
|
247
|
+
serve({
|
|
248
|
+
store,
|
|
249
|
+
channelId,
|
|
250
|
+
challengeId,
|
|
251
|
+
tickCost: 100n,
|
|
252
|
+
generate: async function* (stream) {
|
|
253
|
+
for (let i = 0; i < 5; i++) {
|
|
254
|
+
await stream.charge()
|
|
255
|
+
yield `tok-${i}`
|
|
256
|
+
}
|
|
257
|
+
},
|
|
258
|
+
}),
|
|
259
|
+
)
|
|
260
|
+
|
|
261
|
+
const output = await readStream(response.body!)
|
|
262
|
+
for (let i = 0; i < 5; i++) {
|
|
263
|
+
expect(output).toContain(`event: message\ndata: tok-${i}\n\n`)
|
|
264
|
+
}
|
|
265
|
+
|
|
266
|
+
const channel = await store.getChannel(channelId)
|
|
267
|
+
expect(channel!.spent).toBe(500n)
|
|
268
|
+
expect(channel!.units).toBe(5)
|
|
269
|
+
})
|
|
270
|
+
|
|
271
|
+
test('sets correct SSE response headers', async () => {
|
|
272
|
+
const store = memoryStore()
|
|
273
|
+
await seedChannel(store, 1000000n)
|
|
274
|
+
|
|
275
|
+
const response = toResponse(
|
|
276
|
+
serve({
|
|
277
|
+
store,
|
|
278
|
+
channelId,
|
|
279
|
+
challengeId,
|
|
280
|
+
tickCost,
|
|
281
|
+
generate: async function* () {},
|
|
282
|
+
}),
|
|
283
|
+
)
|
|
284
|
+
|
|
285
|
+
expect(response.headers.get('Cache-Control')).toBe('no-cache, no-transform')
|
|
286
|
+
expect(response.headers.get('Connection')).toBe('keep-alive')
|
|
287
|
+
expect(response.headers.get('Content-Type')).toBe('text/event-stream; charset=utf-8')
|
|
288
|
+
})
|
|
289
|
+
})
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Tempo-specific SSE transport that wraps the base HTTP transport
|
|
3
|
+
* with metering logic (context capture from credentials, per-token
|
|
4
|
+
* charging via Sse.serve).
|
|
5
|
+
*
|
|
6
|
+
* @internal
|
|
7
|
+
*/
|
|
8
|
+
import * as Transport from '../../../server/Transport.js'
|
|
9
|
+
import type * as ChannelStore from '../../stream/ChannelStore.js'
|
|
10
|
+
import * as Sse_core from '../../stream/Sse.js'
|
|
11
|
+
|
|
12
|
+
/** SSE transport with Tempo stream controller. */
|
|
13
|
+
export type Sse = Transport.Sse<Sse_core.StreamController>
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Creates a Tempo-metered SSE transport.
|
|
17
|
+
*
|
|
18
|
+
* Wraps an HTTP transport with:
|
|
19
|
+
* - Context capture from credentials (channelId, tickCost)
|
|
20
|
+
* - Per-token charging via Sse.serve for generator/iterable responses
|
|
21
|
+
* - Auto-detection of upstream SSE responses
|
|
22
|
+
* - Fallback to standard HTTP receipt handling for plain Response
|
|
23
|
+
*/
|
|
24
|
+
export function sse(options: sse.Options & { store: ChannelStore.ChannelStore }): Sse {
|
|
25
|
+
const { pollingInterval, poll } = options
|
|
26
|
+
|
|
27
|
+
// When `poll` is true, strip `waitForUpdate` so the SSE charge loop
|
|
28
|
+
// falls back to polling. This is needed for runtimes like Cloudflare Workers
|
|
29
|
+
// where resolving promises across request contexts is not supported.
|
|
30
|
+
const store = (() => {
|
|
31
|
+
if (!poll) return options.store
|
|
32
|
+
const { waitForUpdate: _, ...store } = options.store
|
|
33
|
+
return store
|
|
34
|
+
})()
|
|
35
|
+
|
|
36
|
+
const contextMap = new Map<string, Sse_core.fromRequest.Context>()
|
|
37
|
+
|
|
38
|
+
const base = Transport.http()
|
|
39
|
+
return Transport.from<Request, Response, Transport.ReceiptResponseOf<Sse>, Response>({
|
|
40
|
+
name: 'sse',
|
|
41
|
+
|
|
42
|
+
getCredential(request) {
|
|
43
|
+
const credential = base.getCredential(request)
|
|
44
|
+
if (credential) {
|
|
45
|
+
try {
|
|
46
|
+
const ctx = Sse_core.fromRequest(request)
|
|
47
|
+
contextMap.set(ctx.challengeId, ctx)
|
|
48
|
+
} catch {
|
|
49
|
+
// ignore — non-SSE credentials won't have stream context
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
return credential
|
|
53
|
+
},
|
|
54
|
+
|
|
55
|
+
respondChallenge(options) {
|
|
56
|
+
return base.respondChallenge(options) as Response
|
|
57
|
+
},
|
|
58
|
+
|
|
59
|
+
respondReceipt({ receipt, response, challengeId }) {
|
|
60
|
+
// Auto-detect upstream SSE responses and parse them into an
|
|
61
|
+
// AsyncIterable so they flow through the metered pipeline.
|
|
62
|
+
// This lets proxy consumers simply pass `result.withReceipt(upstreamRes)`
|
|
63
|
+
// and get per-event charging automatically.
|
|
64
|
+
const resolved =
|
|
65
|
+
response instanceof Response && Sse_core.isEventStream(response) && response.body
|
|
66
|
+
? Sse_core.iterateData(response, { skip: (d) => d === '[DONE]' })
|
|
67
|
+
: response
|
|
68
|
+
|
|
69
|
+
if (isAsyncGeneratorFunction(resolved) || isAsyncIterable(resolved)) {
|
|
70
|
+
const ctx = contextMap.get(challengeId)
|
|
71
|
+
if (!ctx) throw new Error('No SSE context available — credential was not parsed')
|
|
72
|
+
contextMap.delete(challengeId)
|
|
73
|
+
|
|
74
|
+
// Pass async generator functions directly so Sse.serve gives them
|
|
75
|
+
// a StreamController for manual charge(). Pass raw AsyncIterables
|
|
76
|
+
// as-is so Sse.serve auto-charges per yielded value.
|
|
77
|
+
const generate: Sse_core.serve.Options['generate'] = isAsyncGeneratorFunction(resolved)
|
|
78
|
+
? (resolved as Sse_core.serve.Options['generate'])
|
|
79
|
+
: (resolved as AsyncIterable<string>)
|
|
80
|
+
const stream = Sse_core.serve({
|
|
81
|
+
store,
|
|
82
|
+
channelId: ctx.channelId,
|
|
83
|
+
challengeId,
|
|
84
|
+
tickCost: ctx.tickCost,
|
|
85
|
+
pollIntervalMs: pollingInterval,
|
|
86
|
+
generate,
|
|
87
|
+
})
|
|
88
|
+
return Sse_core.toResponse(stream)
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
return base.respondReceipt({ receipt, response: response as Response, challengeId })
|
|
92
|
+
},
|
|
93
|
+
})
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
export declare namespace sse {
|
|
97
|
+
type Options = {
|
|
98
|
+
/**
|
|
99
|
+
* When true, the charge loop uses polling instead of `waitForUpdate()`.
|
|
100
|
+
*
|
|
101
|
+
* Required for runtimes like Cloudflare Workers where resolving promises
|
|
102
|
+
* across request contexts is not supported. Without this flag, a mid-stream
|
|
103
|
+
* voucher POST (Request B) would resolve a waiter created in the streaming
|
|
104
|
+
* request context (Request A), causing a Workers error.
|
|
105
|
+
*
|
|
106
|
+
* @default false
|
|
107
|
+
*/
|
|
108
|
+
poll?: boolean | undefined
|
|
109
|
+
/** Polling interval (in milliseconds). @default 10 */
|
|
110
|
+
pollingInterval?: number | undefined
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
/** Default SSE serve: iterates values and emits `event: message` per value. */
|
|
115
|
+
export function defaultServe(options: {
|
|
116
|
+
generate: AsyncIterable<string> | ((...args: any[]) => AsyncIterable<string>)
|
|
117
|
+
challengeId: string
|
|
118
|
+
}): Response {
|
|
119
|
+
const iterable =
|
|
120
|
+
typeof options.generate === 'function' ? options.generate(undefined as any) : options.generate
|
|
121
|
+
const encoder = new TextEncoder()
|
|
122
|
+
const stream = new ReadableStream<Uint8Array>({
|
|
123
|
+
async start(controller) {
|
|
124
|
+
try {
|
|
125
|
+
for await (const value of iterable) {
|
|
126
|
+
controller.enqueue(encoder.encode(`event: message\ndata: ${value}\n\n`))
|
|
127
|
+
}
|
|
128
|
+
} catch (e) {
|
|
129
|
+
controller.error(e)
|
|
130
|
+
} finally {
|
|
131
|
+
controller.close()
|
|
132
|
+
}
|
|
133
|
+
},
|
|
134
|
+
})
|
|
135
|
+
return new Response(stream, {
|
|
136
|
+
headers: {
|
|
137
|
+
'Content-Type': 'text/event-stream; charset=utf-8',
|
|
138
|
+
'Cache-Control': 'no-cache, no-transform',
|
|
139
|
+
Connection: 'keep-alive',
|
|
140
|
+
},
|
|
141
|
+
})
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
function isAsyncGeneratorFunction(
|
|
145
|
+
value: unknown,
|
|
146
|
+
): value is (...args: unknown[]) => AsyncIterable<string> {
|
|
147
|
+
if (typeof value !== 'function') return false
|
|
148
|
+
return value.constructor?.name === 'AsyncGeneratorFunction'
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
function isAsyncIterable(value: unknown): value is AsyncIterable<string> {
|
|
152
|
+
return value !== null && typeof value === 'object' && Symbol.asyncIterator in (value as object)
|
|
153
|
+
}
|