@inferencesh/sdk 0.21.0 → 0.22.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.
Files changed (57) hide show
  1. package/CHANGELOG.md +53 -0
  2. package/dist/agent/api.d.ts +35 -1
  3. package/dist/agent/api.js +43 -7
  4. package/dist/agent/reducer.js +23 -7
  5. package/dist/agent/types.d.ts +29 -4
  6. package/dist/api/agents.d.ts +9 -3
  7. package/dist/api/agents.js +87 -63
  8. package/dist/api/api-keys.d.ts +2 -5
  9. package/dist/api/apps.d.ts +9 -2
  10. package/dist/api/apps.js +9 -1
  11. package/dist/api/chats.d.ts +13 -3
  12. package/dist/api/chats.js +13 -2
  13. package/dist/api/engines.d.ts +4 -2
  14. package/dist/api/engines.js +3 -2
  15. package/dist/api/flow-runs.d.ts +7 -2
  16. package/dist/api/flow-runs.js +7 -2
  17. package/dist/api/flows.d.ts +13 -2
  18. package/dist/api/flows.js +15 -1
  19. package/dist/api/knowledge.d.ts +7 -4
  20. package/dist/api/knowledge.js +6 -4
  21. package/dist/api/mcp-servers.d.ts +2 -1
  22. package/dist/api/projects.d.ts +5 -3
  23. package/dist/api/projects.js +3 -2
  24. package/dist/api/secrets.d.ts +2 -2
  25. package/dist/api/tasks.js +38 -56
  26. package/dist/api/teams.d.ts +4 -2
  27. package/dist/api/teams.js +3 -2
  28. package/dist/api/write-bodies.d.ts +110 -0
  29. package/dist/api/write-bodies.js +1 -0
  30. package/dist/http/client.d.ts +1 -1
  31. package/dist/http/client.js +2 -1
  32. package/dist/http/loopback.d.ts +8 -0
  33. package/dist/http/loopback.js +18 -0
  34. package/dist/http/stream-until-terminal.d.ts +55 -0
  35. package/dist/http/stream-until-terminal.js +88 -0
  36. package/dist/http/stream.d.ts +1 -0
  37. package/dist/http/stream.js +7 -3
  38. package/dist/index.d.ts +2 -0
  39. package/dist/index.js +1 -0
  40. package/dist/proxy/endpoints.json +156 -0
  41. package/dist/proxy/express.d.ts +5 -6
  42. package/dist/proxy/express.js +18 -2
  43. package/dist/proxy/hono.d.ts +5 -3
  44. package/dist/proxy/hono.js +4 -3
  45. package/dist/proxy/index.d.ts +165 -6
  46. package/dist/proxy/index.js +409 -25
  47. package/dist/proxy/nextjs.d.ts +29 -17
  48. package/dist/proxy/nextjs.js +72 -62
  49. package/dist/proxy/remix.d.ts +5 -3
  50. package/dist/proxy/remix.js +4 -3
  51. package/dist/proxy/svelte.d.ts +5 -4
  52. package/dist/proxy/svelte.js +4 -4
  53. package/dist/types.d.ts +423 -6
  54. package/dist/types.js +111 -0
  55. package/dist/version.d.ts +1 -0
  56. package/dist/version.js +7 -0
  57. package/package.json +2 -1
@@ -103,7 +103,7 @@ export declare class HttpClient {
103
103
  /**
104
104
  * Make an HTTP request to the API
105
105
  */
106
- request<T, P extends object = Record<string, unknown>>(method: 'get' | 'post' | 'put' | 'delete', endpoint: string, { handleErrors, ...options }?: {
106
+ request<T, P extends object = Record<string, unknown>>(method: 'get' | 'post' | 'put' | 'patch' | 'delete', endpoint: string, { handleErrors, ...options }?: {
107
107
  params?: P;
108
108
  data?: unknown;
109
109
  /**
@@ -1,5 +1,6 @@
1
1
  import { InferenceError, RequirementsNotMetException } from './errors';
2
2
  import { EventSource } from 'eventsource';
3
+ import { SDK_VERSION } from '../version';
3
4
  /**
4
5
  * Low-level HTTP client for inference.sh API
5
6
  *
@@ -16,7 +17,7 @@ export class HttpClient {
16
17
  this.baseUrl = config.baseUrl || 'https://api.inference.sh';
17
18
  this.proxyUrl = config.proxyUrl;
18
19
  this.getToken = config.getToken;
19
- this.customHeaders = { 'X-Client-Source': 'inference-sdk-js/0.5.13', ...config.headers };
20
+ this.customHeaders = { 'X-Client-Source': `inference-sdk-js/${SDK_VERSION}`, ...config.headers };
20
21
  // Bearer auth needs no cookies, and 'include' makes browsers reject the
21
22
  // response unless the API answers with Allow-Credentials — which it does not
22
23
  // for third-party origins (WebKit reports that as "Load failed"). Cookies
@@ -0,0 +1,8 @@
1
+ /**
2
+ * Loopback hosts, where plain http never leaves the machine (local dev):
3
+ * `localhost`, any `*.localhost`, `[::1]` and 127.0.0.0/8. This is the one
4
+ * copy of the rule; the proxy, the app and common-js all ask it.
5
+ */
6
+ export declare function isLoopbackHost(hostname: string): boolean;
7
+ /** Whether `url` is https, or plain http to a loopback host. */
8
+ export declare function isHttpsOrLoopback(url: URL): boolean;
@@ -0,0 +1,18 @@
1
+ /**
2
+ * Loopback hosts, where plain http never leaves the machine (local dev):
3
+ * `localhost`, any `*.localhost`, `[::1]` and 127.0.0.0/8. This is the one
4
+ * copy of the rule; the proxy, the app and common-js all ask it.
5
+ */
6
+ export function isLoopbackHost(hostname) {
7
+ const h = hostname.toLowerCase();
8
+ return h === 'localhost'
9
+ || h.endsWith('.localhost')
10
+ || h === '[::1]'
11
+ || /^127(\.\d{1,3}){3}$/.test(h);
12
+ }
13
+ /** Whether `url` is https, or plain http to a loopback host. */
14
+ export function isHttpsOrLoopback(url) {
15
+ if (url.protocol === 'https:')
16
+ return true;
17
+ return url.protocol === 'http:' && isLoopbackHost(url.hostname);
18
+ }
@@ -0,0 +1,55 @@
1
+ /**
2
+ * Follow a resource's NDJSON stream until the resource reaches a terminal
3
+ * state.
4
+ *
5
+ * StreamableManager never reconnects, and a stream can close cleanly before
6
+ * the resource is done (load balancer idle timeout, API deploy). A wait built
7
+ * on it must not hang then. This helper owns that contract for every
8
+ * "stream until done" wait: when the stream ends early it fetches the
9
+ * resource once (`reconcile`) and settles with what that shows, or rejects
10
+ * when the resource is still not terminal. sdk-py's `wait_for_completion`
11
+ * does the same final GET.
12
+ */
13
+ import { type StreamableManagerOptions, type StreamRequest } from './streamable';
14
+ /** Settles a stream-until-terminal wait. Calls after the first are ignored. */
15
+ export interface TerminalSettler<R> {
16
+ resolve(value: R): void;
17
+ reject(error: Error): void;
18
+ }
19
+ /** The stream to follow and how to tell when its resource is done. */
20
+ export type StreamUntilTerminalSpec<T> = Pick<StreamableManagerOptions<T>, 'body' | 'onData' | 'onPartialData' | 'onStart' | 'onDelta'> & {
21
+ /** Sends the stream request, e.g. `(init) => http.fetch(endpoint, init)`. */
22
+ request: StreamRequest;
23
+ /** Typed event listeners ({"event": name, "data": ...} messages). */
24
+ events?: Record<string, (data: any, fields?: string[]) => void>;
25
+ /**
26
+ * Called once when the stream ends cleanly before the wait settled. Fetch
27
+ * the resource and settle if it is terminal; returning without settling
28
+ * rejects the wait with `closedMessage`.
29
+ */
30
+ reconcile: () => Promise<void>;
31
+ /** Rejection message when the stream closed and the resource is still not terminal. */
32
+ closedMessage: string;
33
+ /**
34
+ * Called when the wait ends because `stop()` was called. Without it `done`
35
+ * stays pending.
36
+ */
37
+ onStopped?: () => void;
38
+ /**
39
+ * Keep the stream open after the wait settled so its listeners go on
40
+ * seeing updates (default false: settling stops the stream).
41
+ */
42
+ keepOpen?: boolean;
43
+ };
44
+ export interface StreamUntilTerminal<R> {
45
+ /** Settles when the resource is terminal, the stream fails, or it closed early and the resource is not terminal. */
46
+ done: Promise<R>;
47
+ /** Ends the stream on purpose; see `onStopped`. */
48
+ stop(): void;
49
+ }
50
+ /**
51
+ * `build` receives the settler and returns the stream spec; its handlers call
52
+ * `settle.resolve`/`settle.reject` once the resource is terminal. Settling
53
+ * stops the stream unless the spec says `keepOpen`.
54
+ */
55
+ export declare function streamUntilTerminal<T, R>(build: (settle: TerminalSettler<R>) => StreamUntilTerminalSpec<T>): StreamUntilTerminal<R>;
@@ -0,0 +1,88 @@
1
+ /**
2
+ * Follow a resource's NDJSON stream until the resource reaches a terminal
3
+ * state.
4
+ *
5
+ * StreamableManager never reconnects, and a stream can close cleanly before
6
+ * the resource is done (load balancer idle timeout, API deploy). A wait built
7
+ * on it must not hang then. This helper owns that contract for every
8
+ * "stream until done" wait: when the stream ends early it fetches the
9
+ * resource once (`reconcile`) and settles with what that shows, or rejects
10
+ * when the resource is still not terminal. sdk-py's `wait_for_completion`
11
+ * does the same final GET.
12
+ */
13
+ import { StreamableManager } from './streamable';
14
+ /**
15
+ * `build` receives the settler and returns the stream spec; its handlers call
16
+ * `settle.resolve`/`settle.reject` once the resource is terminal. Settling
17
+ * stops the stream unless the spec says `keepOpen`.
18
+ */
19
+ export function streamUntilTerminal(build) {
20
+ let settled = false;
21
+ let stopped = false;
22
+ let manager;
23
+ const done = new Promise((resolve, reject) => {
24
+ const settle = {
25
+ resolve: (value) => {
26
+ if (settled)
27
+ return;
28
+ settled = true;
29
+ if (!keepOpen)
30
+ manager?.stop();
31
+ resolve(value);
32
+ },
33
+ reject: (error) => {
34
+ if (settled)
35
+ return;
36
+ settled = true;
37
+ if (!keepOpen)
38
+ manager?.stop();
39
+ reject(error);
40
+ },
41
+ };
42
+ const { events, reconcile, closedMessage, onStopped, keepOpen, ...managerOptions } = build(settle);
43
+ let streamError = null;
44
+ manager = new StreamableManager({
45
+ ...managerOptions,
46
+ onError: (error) => {
47
+ streamError = error;
48
+ },
49
+ onEnd: () => {
50
+ if (settled)
51
+ return;
52
+ if (stopped) {
53
+ onStopped?.();
54
+ return;
55
+ }
56
+ if (streamError) {
57
+ settle.reject(streamError);
58
+ return;
59
+ }
60
+ // Closed cleanly before the resource was terminal: ask the API once.
61
+ const closed = (cause) => {
62
+ if (stopped && !settled) {
63
+ onStopped?.();
64
+ return;
65
+ }
66
+ const error = new Error(closedMessage);
67
+ if (cause !== undefined)
68
+ error.cause = cause;
69
+ settle.reject(error);
70
+ };
71
+ reconcile().then(() => closed(), closed);
72
+ },
73
+ });
74
+ for (const [name, listener] of Object.entries(events ?? {})) {
75
+ manager.addEventListener(name, listener);
76
+ }
77
+ });
78
+ manager.start();
79
+ return {
80
+ done,
81
+ stop: () => {
82
+ if (stopped)
83
+ return;
84
+ stopped = true;
85
+ manager.stop();
86
+ },
87
+ };
88
+ }
@@ -24,6 +24,7 @@ export declare class StreamManager<T> {
24
24
  private initialConnectionAttempts;
25
25
  private consecutiveErrors;
26
26
  private isConnected;
27
+ private hasEverConnected;
27
28
  private isStopped;
28
29
  private eventListeners;
29
30
  constructor(options: StreamManagerOptions<T>);
@@ -17,6 +17,7 @@ export class StreamManager {
17
17
  this.initialConnectionAttempts = 0;
18
18
  this.consecutiveErrors = 0;
19
19
  this.isConnected = false;
20
+ this.hasEverConnected = false;
20
21
  this.isStopped = false;
21
22
  this.eventListeners = new Map();
22
23
  this.options = {
@@ -53,6 +54,8 @@ export class StreamManager {
53
54
  source.addEventListener(eventName, (e) => {
54
55
  if (this.isStopped)
55
56
  return;
57
+ // A delivered event proves the connection works, same as onmessage.
58
+ this.consecutiveErrors = 0;
56
59
  try {
57
60
  const parsed = JSON.parse(e.data);
58
61
  const listeners = this.eventListeners.get(eventName);
@@ -114,15 +117,15 @@ export class StreamManager {
114
117
  if (!this.options.autoReconnect || this.isStopped)
115
118
  return false;
116
119
  const maxReconnects = this.options.maxReconnects ?? 5;
117
- if (!this.isConnected && this.initialConnectionAttempts >= maxReconnects) {
120
+ if (!this.hasEverConnected && this.initialConnectionAttempts >= maxReconnects) {
118
121
  return false;
119
122
  }
120
- if (this.isConnected && this.consecutiveErrors >= maxReconnects) {
123
+ if (this.hasEverConnected && this.consecutiveErrors >= maxReconnects) {
121
124
  return false;
122
125
  }
123
126
  this.reconnectTimeout = setTimeout(() => {
124
127
  if (!this.isStopped) {
125
- if (!this.isConnected) {
128
+ if (!this.hasEverConnected) {
126
129
  this.initialConnectionAttempts++;
127
130
  }
128
131
  this.consecutiveErrors++;
@@ -142,6 +145,7 @@ export class StreamManager {
142
145
  return;
143
146
  this.eventSource = source;
144
147
  this.isConnected = true;
148
+ this.hasEverConnected = true;
145
149
  this.options.onStart?.();
146
150
  // Set up typed event listeners (for events with `event: eventName` header)
147
151
  this.setupAllEventListeners(source);
package/dist/index.d.ts CHANGED
@@ -4,6 +4,7 @@ import type { Response } from './http/response';
4
4
  export { StreamManager, type StreamManagerOptions, type PartialDataWrapper } from './http/stream';
5
5
  export { StreamableManager, type StreamableManagerOptions, type StreamableSource, type StreamRequest, type StreamRequestInit, type StreamableMessage, streamable, streamableRaw } from './http/streamable';
6
6
  export { PollManager, type PollManagerOptions } from './http/poll';
7
+ export { isLoopbackHost, isHttpsOrLoopback } from './http/loopback';
7
8
  export { InferenceError, RequirementsNotMetException, SessionError, SessionNotFoundError, SessionExpiredError, SessionEndedError, WorkerLostError, isRequirementsNotMetException, isInferenceError, isSessionError, } from './http/errors';
8
9
  export { TasksAPI, type RunOptions, type WatchOptions, type TaskWatch } from './api/tasks';
9
10
  export { SocketsAPI, type SocketTarget, type OpenSocketOptions } from './api/sockets';
@@ -17,6 +18,7 @@ export { FlowRunsAPI } from './api/flow-runs';
17
18
  export { EnginesAPI } from './api/engines';
18
19
  export { KnowledgeAPI, SkillsAPI } from './api/knowledge';
19
20
  export { ArtifactsAPI } from './api/artifacts';
21
+ export type { AgentUpdateBody, AppPatchBody, AppUpdateBody, ChatUpdateBody, EngineUpdateBody, FlowUpdateBody, FlowPatchBody, FlowViewportBody, ProjectWriteBody, KnowledgeUpdateBody, TeamUpdateBody, MCPServerUpdateBody, } from './api/write-bodies';
20
22
  export { TeamsAPI } from './api/teams';
21
23
  export { SecretsAPI } from './api/secrets';
22
24
  export { ApiKeysAPI } from './api/api-keys';
package/dist/index.js CHANGED
@@ -3,6 +3,7 @@ export { HttpClient, createHttpClient } from './http/client';
3
3
  export { StreamManager } from './http/stream';
4
4
  export { StreamableManager, streamable, streamableRaw } from './http/streamable';
5
5
  export { PollManager } from './http/poll';
6
+ export { isLoopbackHost, isHttpsOrLoopback } from './http/loopback';
6
7
  export { InferenceError, RequirementsNotMetException, SessionError, SessionNotFoundError, SessionExpiredError, SessionEndedError, WorkerLostError,
7
8
  // Type guards (use these instead of instanceof for reliability)
8
9
  isRequirementsNotMetException, isInferenceError, isSessionError, } from './http/errors';
@@ -0,0 +1,156 @@
1
+ {
2
+ "$comment": "Generated by `make proxy-endpoints` from the route table (internal/api/proxy_endpoints_test.go). Do not edit.",
3
+ "preset": "run-only",
4
+ "endpoints": [
5
+ {
6
+ "method": "POST",
7
+ "path": "/apps/run",
8
+ "purpose": "run an app",
9
+ "scopes": [
10
+ "apps:execute",
11
+ "apps:read",
12
+ "conversations:read"
13
+ ]
14
+ },
15
+ {
16
+ "method": "POST",
17
+ "path": "/files",
18
+ "purpose": "upload a file input of a run or message",
19
+ "scopes": [
20
+ "files:write"
21
+ ]
22
+ },
23
+ {
24
+ "method": "GET",
25
+ "path": "/tasks/{id}",
26
+ "purpose": "read a task",
27
+ "scopes": [
28
+ "apps:read"
29
+ ]
30
+ },
31
+ {
32
+ "method": "GET",
33
+ "path": "/tasks/{id}/status",
34
+ "purpose": "poll a task",
35
+ "scopes": [
36
+ "apps:read"
37
+ ]
38
+ },
39
+ {
40
+ "method": "GET",
41
+ "path": "/tasks/{id}/stream",
42
+ "purpose": "stream a task",
43
+ "scopes": [
44
+ "apps:read",
45
+ "conversations:read",
46
+ "flows:read"
47
+ ]
48
+ },
49
+ {
50
+ "method": "POST",
51
+ "path": "/tasks/{id}/cancel",
52
+ "purpose": "cancel a task",
53
+ "scopes": [
54
+ "apps:execute"
55
+ ]
56
+ },
57
+ {
58
+ "method": "POST",
59
+ "path": "/agents/run",
60
+ "purpose": "send a message to an agent",
61
+ "scopes": [
62
+ "agents:execute",
63
+ "conversations:read"
64
+ ]
65
+ },
66
+ {
67
+ "method": "POST",
68
+ "path": "/chats",
69
+ "purpose": "start a chat with an agent",
70
+ "scopes": [
71
+ "conversations:write"
72
+ ]
73
+ },
74
+ {
75
+ "method": "POST",
76
+ "path": "/chats/{id}/messages",
77
+ "purpose": "send a message in a chat",
78
+ "scopes": [
79
+ "agents:execute"
80
+ ]
81
+ },
82
+ {
83
+ "method": "POST",
84
+ "path": "/chats/{id}/agent",
85
+ "purpose": "hand a chat to another agent",
86
+ "scopes": [
87
+ "conversations:write"
88
+ ]
89
+ },
90
+ {
91
+ "method": "GET",
92
+ "path": "/agents/{namespace}/{name}",
93
+ "purpose": "read an agent's info",
94
+ "scopes": [
95
+ "agents:read"
96
+ ]
97
+ },
98
+ {
99
+ "method": "GET",
100
+ "path": "/chats/{id}",
101
+ "purpose": "read a chat",
102
+ "scopes": [
103
+ "conversations:read"
104
+ ]
105
+ },
106
+ {
107
+ "method": "GET",
108
+ "path": "/chats/{id}/status",
109
+ "purpose": "poll a chat",
110
+ "scopes": [
111
+ "conversations:read"
112
+ ]
113
+ },
114
+ {
115
+ "method": "GET",
116
+ "path": "/chats/{id}/messages",
117
+ "purpose": "read a chat's messages",
118
+ "scopes": [
119
+ "conversations:read"
120
+ ]
121
+ },
122
+ {
123
+ "method": "GET",
124
+ "path": "/chats/{id}/stream",
125
+ "purpose": "stream a chat",
126
+ "scopes": [
127
+ "conversations:read"
128
+ ]
129
+ },
130
+ {
131
+ "method": "POST",
132
+ "path": "/chats/{id}/stop",
133
+ "purpose": "stop a chat",
134
+ "scopes": [
135
+ "conversations:write"
136
+ ]
137
+ },
138
+ {
139
+ "method": "POST",
140
+ "path": "/chats/messages/{messageId}/cancel",
141
+ "purpose": "cancel a message",
142
+ "scopes": [
143
+ "conversations:read",
144
+ "conversations:write"
145
+ ]
146
+ },
147
+ {
148
+ "method": "POST",
149
+ "path": "/tools/{toolId}",
150
+ "purpose": "answer a client tool call",
151
+ "scopes": [
152
+ "conversations:write"
153
+ ]
154
+ }
155
+ ]
156
+ }
@@ -8,18 +8,17 @@
8
8
  *
9
9
  * const app = express();
10
10
  * app.use(express.json());
11
- * app.all(PROXY_ROUTE, createHandler());
11
+ * app.all(PROXY_ROUTE, createHandler({ allowedEndpoints: ["my-team/*"] }));
12
12
  * ```
13
13
  */
14
- import type { RequestHandler } from "express";
14
+ import type { Request, RequestHandler } from "express";
15
+ import { type ProxyOptions } from "./index";
15
16
  /** Default proxy route path */
16
17
  export declare const PROXY_ROUTE = "/api/inference/proxy";
17
18
  /** @deprecated Use PROXY_ROUTE */
18
19
  export declare const route = "/api/inference/proxy";
19
- export interface ExpressProxyOptions {
20
- /** Custom API key (overrides INFERENCE_API_KEY env var) */
21
- apiKey?: string;
22
- }
20
+ /** Proxy options; `isAuthenticated` receives the Express request. */
21
+ export type ExpressProxyOptions = ProxyOptions<Request>;
23
22
  /**
24
23
  * Creates an Express middleware handler for the Inference.sh proxy.
25
24
  *
@@ -8,7 +8,7 @@
8
8
  *
9
9
  * const app = express();
10
10
  * app.use(express.json());
11
- * app.all(PROXY_ROUTE, createHandler());
11
+ * app.all(PROXY_ROUTE, createHandler({ allowedEndpoints: ["my-team/*"] }));
12
12
  * ```
13
13
  */
14
14
  import { PROXY_PATH, processProxyRequest, } from "./index";
@@ -23,8 +23,19 @@ export const route = PROXY_ROUTE;
23
23
  */
24
24
  export function createHandler(options) {
25
25
  return async (req, res, _next) => {
26
+ // The client hung up before the response finished: stop the upstream
27
+ // request too. Chat and task streams never end on their own, so
28
+ // without this the proxy keeps reading them for nobody and the open
29
+ // upstream connection keeps the server process alive.
30
+ const upstream = new AbortController();
31
+ res.on("close", () => {
32
+ if (!res.writableFinished)
33
+ upstream.abort();
34
+ });
26
35
  return processProxyRequest({
27
36
  framework: "express",
37
+ signal: upstream.signal,
38
+ request: req,
28
39
  method: req.method,
29
40
  body: async () => JSON.stringify(req.body),
30
41
  headers: () => req.headers,
@@ -61,7 +72,12 @@ export function createHandler(options) {
61
72
  // Handle text responses
62
73
  return res.send(await response.text());
63
74
  },
64
- }, options);
75
+ }, options).catch((error) => {
76
+ // Aborted because the client left; there is nobody to answer.
77
+ if (upstream.signal.aborted)
78
+ return res;
79
+ throw error;
80
+ });
65
81
  };
66
82
  }
67
83
  /** @deprecated Use createHandler() */
@@ -9,11 +9,13 @@
9
9
  * import { createHandler } from "@inferencesh/sdk/proxy/hono";
10
10
  *
11
11
  * const app = new Hono();
12
- * app.all("/api/inference/proxy", createHandler());
12
+ * app.all("/api/inference/proxy", createHandler({ allowedEndpoints: ["my-team/*"] }));
13
13
  * ```
14
14
  */
15
15
  import type { Context } from "hono";
16
- export interface HonoProxyOptions {
16
+ import { type ProxyOptions } from "./index";
17
+ /** Proxy options; `isAuthenticated` receives the Context. */
18
+ export interface HonoProxyOptions extends ProxyOptions<Context> {
17
19
  /** Custom function to resolve the API key */
18
20
  resolveApiKey?: () => Promise<string | undefined>;
19
21
  }
@@ -21,7 +23,7 @@ type HonoHandler = (context: Context) => Promise<Response>;
21
23
  /**
22
24
  * Creates a Hono route handler for the Inference.sh proxy.
23
25
  */
24
- export declare function createHandler({ resolveApiKey, }?: HonoProxyOptions): HonoHandler;
26
+ export declare function createHandler({ resolveApiKey, ...options }?: HonoProxyOptions): HonoHandler;
25
27
  /** @deprecated Use createHandler */
26
28
  export declare const createRouteHandler: typeof createHandler;
27
29
  export {};
@@ -9,19 +9,20 @@
9
9
  * import { createHandler } from "@inferencesh/sdk/proxy/hono";
10
10
  *
11
11
  * const app = new Hono();
12
- * app.all("/api/inference/proxy", createHandler());
12
+ * app.all("/api/inference/proxy", createHandler({ allowedEndpoints: ["my-team/*"] }));
13
13
  * ```
14
14
  */
15
15
  import { processProxyRequest, getEnvApiKey, passthrough, headersToRecord, } from "./index";
16
16
  /**
17
17
  * Creates a Hono route handler for the Inference.sh proxy.
18
18
  */
19
- export function createHandler({ resolveApiKey = getEnvApiKey, } = {}) {
19
+ export function createHandler({ resolveApiKey = getEnvApiKey, ...options } = {}) {
20
20
  return async (context) => {
21
21
  const responseHeaders = new Headers();
22
22
  const url = new URL(context.req.url);
23
23
  return processProxyRequest({
24
24
  framework: "hono",
25
+ request: context,
25
26
  method: context.req.method,
26
27
  body: async () => {
27
28
  try {
@@ -44,7 +45,7 @@ export function createHandler({ resolveApiKey = getEnvApiKey, } = {}) {
44
45
  }),
45
46
  respond: passthrough,
46
47
  apiKey: resolveApiKey,
47
- });
48
+ }, options);
48
49
  };
49
50
  }
50
51
  /** @deprecated Use createHandler */