@mitralab.io/functions-sdk 0.2.0-beta.1 → 0.2.0-beta.2

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/README.md CHANGED
@@ -28,6 +28,7 @@ It also accepts the canonical aliases:
28
28
  - `MITRA_PLATFORM_ACCESS_TOKEN`
29
29
  - `MITRA_APP_ID`
30
30
  - `MITRA_DATA_SOURCE_ID`, retained for runtime compatibility when already resolved
31
+ - `MITRA_API_KEY`, read by `createClientFromApiKey()`
31
32
 
32
33
  When only the existing names are present, the SDK removes a trailing `/legacy` from
33
34
  `MITRA_BASE_URL` and calls the owning services from that gateway root. It forwards `MITRA_TOKEN`
@@ -61,6 +62,39 @@ const mitra = createClient({
61
62
 
62
63
  `createClientFromEnvironment(env)` is available when a function needs to supply a specific environment object, such as in tests.
63
64
 
65
+ ### Authenticating with an api key
66
+
67
+ Outside the Functions runtime there is no token to inject. A process that runs on its own — a cron,
68
+ a background collector, another service — authenticates with an api key created in
69
+ **Settings -> API keys**:
70
+
71
+ ```typescript
72
+ import { createClientFromApiKey } from "@mitralab.io/functions-sdk"
73
+
74
+ const mitra = await createClientFromApiKey({
75
+ apiUrl: "https://api.example.com",
76
+ apiKey: process.env.MITRA_API_KEY,
77
+ appId: "app-id",
78
+ })
79
+ ```
80
+
81
+ The factory is asynchronous because trading the key for a token is a network call. It fails there,
82
+ where the client is built, rather than inside an unrelated call later.
83
+
84
+ Which key to create depends on what the process does. A **Business** key reaches the published
85
+ product: read and write records, run queries, execute functions and integrations. A **Developer**
86
+ key adds authoring — schema, code, publishing. An **Administrator** key belongs to a workspace
87
+ rather than a product; the SDK issues the token for the configured `appId` from it, and the
88
+ platform decides on that call what this user actually reaches in that product.
89
+
90
+ The token lasts 48 hours and the exchange returns no refresh token, by design: the key does not
91
+ expire and is revoked by deleting it, so the SDK renews by trading the key again. It does this on
92
+ its own when a request comes back unauthorized, which is why a process may stay up for weeks. Keep
93
+ the key where you keep passwords — it is valid until someone deletes it.
94
+
95
+ This authentication path expects a server runtime. Never ship an api key in code that reaches a
96
+ browser: it would be served to every visitor.
97
+
64
98
  ## Initialization
65
99
 
66
100
  Entity and Custom Query operations use the app identity from the token and `X-App-Id`, so they are
@@ -0,0 +1,15 @@
1
+ {
2
+ "contract": "SDK-PARITY-001",
3
+ "version": "0.2.0-beta.3",
4
+ "dependency": {
5
+ "package": "@mitralab.io/sdk-core",
6
+ "version": "0.2.0-beta.3",
7
+ "contractPath": "contracts/v0.2.0-beta.3/sdk-parity.json"
8
+ },
9
+ "sha256": "61b49a71457190173ee749e9603f5a7f8f226caabf6ad0a8fa94a66b683c4ec9",
10
+ "source": {
11
+ "repository": "https://github.com/mitralab-dev/mitra-core-sdk",
12
+ "commit": "dd0aa46c5b3e5c7ea0a907355f428b1963a95e8b",
13
+ "path": "contracts/v0.2.0-beta.3/sdk-parity.json"
14
+ }
15
+ }
package/dist/index.cjs CHANGED
@@ -30,13 +30,14 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
30
30
  // src/index.ts
31
31
  var index_exports = {};
32
32
  __export(index_exports, {
33
- AgentTaskTurnError: () => import_sdk_core3.AgentTaskTurnError,
33
+ AgentTaskTurnError: () => import_sdk_core4.AgentTaskTurnError,
34
34
  MitraApiError: () => MitraApiError,
35
35
  MitraConfigurationError: () => MitraConfigurationError,
36
36
  callIntegrationMitra: () => callIntegrationMitra2,
37
37
  configureSdkMitra: () => configureSdkMitra3,
38
38
  createAgentMitra: () => createAgentMitra2,
39
39
  createClient: () => createClient,
40
+ createClientFromApiKey: () => createClientFromApiKey,
40
41
  createClientFromEnvironment: () => createClientFromEnvironment,
41
42
  createIntegrationMitra: () => createIntegrationMitra2,
42
43
  createJdbcConnectionMitra: () => createJdbcConnectionMitra2,
@@ -100,7 +101,7 @@ __export(index_exports, {
100
101
  module.exports = __toCommonJS(index_exports);
101
102
 
102
103
  // src/client.ts
103
- var import_sdk_core2 = require("@mitralab.io/sdk-core");
104
+ var import_sdk_core3 = require("@mitralab.io/sdk-core");
104
105
 
105
106
  // src/agent-task-sse.ts
106
107
  var import_sdk_core = require("@mitralab.io/sdk-core");
@@ -213,9 +214,13 @@ function createApiError(response, payload, accessToken) {
213
214
  ...retryable === void 0 ? {} : { retryable }
214
215
  });
215
216
  }
217
+ function isUnauthorized(error) {
218
+ return error instanceof MitraApiError && error.status === 401;
219
+ }
216
220
  var HttpClient = class {
217
221
  #authentication;
218
222
  #accessToken;
223
+ #tokenProvider;
219
224
  baseUrl;
220
225
  appId;
221
226
  timeoutMs;
@@ -224,21 +229,28 @@ var HttpClient = class {
224
229
  this.baseUrl = config.baseUrl;
225
230
  this.#authentication = config.authentication;
226
231
  this.#accessToken = config.authentication === "bearer" ? config.accessToken : void 0;
232
+ this.#tokenProvider = config.authentication === "bearer" ? config.tokenProvider : void 0;
227
233
  this.appId = config.authentication === "bearer" ? config.appId : void 0;
228
234
  this.timeoutMs = config.timeoutMs;
229
235
  this.fetchImplementation = config.fetch;
230
236
  }
231
237
  async request(path, options = {}) {
238
+ try {
239
+ return await this.attempt(path, options);
240
+ } catch (error) {
241
+ if (this.#tokenProvider === void 0 || !isUnauthorized(error)) throw error;
242
+ this.#tokenProvider.invalidate();
243
+ return this.attempt(path, options);
244
+ }
245
+ }
246
+ async attempt(path, options) {
232
247
  const url = new URL(`${this.baseUrl}${path}`);
233
248
  appendQueryParameters(url, options.params ?? {});
234
249
  const controller = this.timeoutMs === void 0 ? void 0 : new AbortController();
235
250
  const timeout = controller === void 0 ? void 0 : setTimeout(() => controller.abort(), this.timeoutMs);
236
251
  const hasBody = options.body !== void 0;
237
- const authentication = this.#authentication === "bearer" ? {
238
- type: "bearer",
239
- accessToken: this.#accessToken,
240
- appId: this.appId
241
- } : { type: "anonymous" };
252
+ const accessToken = this.#authentication === "bearer" ? await this.#tokenProvider?.get() ?? this.#accessToken : void 0;
253
+ const authentication = accessToken === void 0 ? { type: "anonymous" } : { type: "bearer", accessToken, appId: this.appId };
242
254
  try {
243
255
  const response = await this.fetchImplementation(url, {
244
256
  method: options.method ?? "GET",
@@ -249,7 +261,7 @@ var HttpClient = class {
249
261
  });
250
262
  if (response.status === 204) return void 0;
251
263
  const payload = await parsePayload(response);
252
- if (!response.ok) throw createApiError(response, payload, this.#accessToken);
264
+ if (!response.ok) throw createApiError(response, payload, accessToken);
253
265
  return payload;
254
266
  } catch (error) {
255
267
  if (error instanceof MitraApiError) throw error;
@@ -550,6 +562,75 @@ function createAppScopedAppsModule(apps, appId) {
550
562
  };
551
563
  }
552
564
 
565
+ // src/api-key.ts
566
+ var import_sdk_core2 = require("@mitralab.io/sdk-core");
567
+
568
+ // src/core-errors.ts
569
+ var coreErrors = {
570
+ configuration: (message) => new MitraConfigurationError(message),
571
+ invalidResponse: (message) => new MitraApiError(message, 200, { code: "INVALID_RESPONSE", retryable: false })
572
+ };
573
+
574
+ // src/api-key.ts
575
+ var EXPIRY_SKEW_MS = 5 * 60 * 1e3;
576
+ var IAM_BASE = "/iam";
577
+ async function exchangeApiKey(options) {
578
+ const { apiUrl, apiKey, appId, fetch: fetchImplementation } = options;
579
+ return (0, import_sdk_core2.resolveApiKeyToken)(
580
+ async (path, init) => {
581
+ const response = await fetchImplementation(new URL(`${apiUrl}${IAM_BASE}${path}`), {
582
+ method: "POST",
583
+ headers: {
584
+ "Content-Type": "application/json",
585
+ ...init.bearer === void 0 ? {} : { Authorization: `Bearer ${init.bearer}` }
586
+ },
587
+ ...init.body === void 0 ? {} : { body: JSON.stringify(init.body) },
588
+ redirect: "manual"
589
+ });
590
+ if (!response.ok) {
591
+ throw new MitraApiError(
592
+ `Api key authentication failed with status ${response.status}`,
593
+ response.status,
594
+ {
595
+ code: response.status === 401 ? "INVALID_CREDENTIALS" : "AUTHENTICATION_FAILED",
596
+ retryable: response.status >= 500
597
+ }
598
+ );
599
+ }
600
+ return response.json();
601
+ },
602
+ appId,
603
+ apiKey,
604
+ coreErrors
605
+ );
606
+ }
607
+ function createApiKeyTokenProvider(options) {
608
+ if (!options.apiKey.trim()) {
609
+ throw new MitraConfigurationError("apiKey must not be empty");
610
+ }
611
+ let token = null;
612
+ let renewAfter = 0;
613
+ let pending = null;
614
+ return {
615
+ async get() {
616
+ if (token !== null && Date.now() < renewAfter) return token;
617
+ pending ??= exchangeApiKey(options).then((fresh) => {
618
+ const expiry = (0, import_sdk_core2.readTokenExpiry)(fresh);
619
+ token = fresh;
620
+ renewAfter = expiry === null ? Number.MAX_SAFE_INTEGER : expiry - EXPIRY_SKEW_MS;
621
+ return fresh;
622
+ }).finally(() => {
623
+ pending = null;
624
+ });
625
+ return pending;
626
+ },
627
+ invalidate() {
628
+ token = null;
629
+ renewAfter = 0;
630
+ }
631
+ };
632
+ }
633
+
553
634
  // src/config.ts
554
635
  function readDefaultEnvironment() {
555
636
  return typeof process === "undefined" ? {} : process.env;
@@ -588,6 +669,26 @@ function deriveNativeApiUrl(legacyBaseUrl) {
588
669
  parsed.pathname = parsed.pathname.replace(/\/legacy\/?$/, "") || "/";
589
670
  return removeTrailingSlashes(parsed.toString());
590
671
  }
672
+ function resolveApiKeyOptions(config = {}, environment = readDefaultEnvironment()) {
673
+ const fetchImplementation = config.fetch ?? globalThis.fetch;
674
+ if (typeof fetchImplementation !== "function") {
675
+ throw new MitraConfigurationError("A fetch implementation is required");
676
+ }
677
+ return {
678
+ apiUrl: normalizeApiUrl(
679
+ requiredValue(
680
+ config.apiUrl ?? environment.MITRA_API_URL ?? deriveNativeApiUrl(environment.MITRA_BASE_URL),
681
+ "apiUrl"
682
+ )
683
+ ),
684
+ appId: requiredValue(
685
+ config.appId ?? environment.MITRA_APP_ID ?? environment.MITRA_PROJECT_ID,
686
+ "appId"
687
+ ),
688
+ apiKey: requiredValue(config.apiKey ?? environment.MITRA_API_KEY, "apiKey"),
689
+ fetch: fetchImplementation
690
+ };
691
+ }
591
692
  function resolveConfig(config = {}, environment = readDefaultEnvironment()) {
592
693
  const apiUrl = normalizeApiUrl(
593
694
  requiredValue(
@@ -637,10 +738,6 @@ function configureLegacySdk(config) {
637
738
  }
638
739
 
639
740
  // src/client.ts
640
- var coreErrors = {
641
- configuration: (message) => new MitraConfigurationError(message),
642
- invalidResponse: (message) => new MitraApiError(message, 200, { code: "INVALID_RESPONSE", retryable: false })
643
- };
644
741
  var DefaultMitraClient = class {
645
742
  agentConnections;
646
743
  agentCredentials;
@@ -679,10 +776,11 @@ var DefaultMitraClient = class {
679
776
  authentication: "bearer",
680
777
  accessToken: config.accessToken,
681
778
  appId: config.appId,
779
+ ...config.tokenProvider === void 0 ? {} : { tokenProvider: config.tokenProvider },
682
780
  ...config.timeoutMs === void 0 ? {} : { timeoutMs: config.timeoutMs },
683
781
  fetch: config.fetch
684
782
  });
685
- const core = (0, import_sdk_core2.createSdkCore)({
783
+ const core = (0, import_sdk_core3.createSdkCore)({
686
784
  transports: {
687
785
  auth: httpClient("iam"),
688
786
  codeStudio: httpClient("code-studio"),
@@ -706,7 +804,7 @@ var DefaultMitraClient = class {
706
804
  this.agentConnections = core.agentConnections;
707
805
  this.agentCredentials = core.agentCredentials;
708
806
  this.agents = core.agents;
709
- const agentSessionManager = (0, import_sdk_core2.createAgentTaskSessionManager)({
807
+ const agentSessionManager = (0, import_sdk_core3.createAgentTaskSessionManager)({
710
808
  tasks: core.agentTasks,
711
809
  eventSource: new AgentTaskSseEventSource({
712
810
  baseUrl: `${config.apiUrl}/copilot`,
@@ -717,7 +815,7 @@ var DefaultMitraClient = class {
717
815
  errors: coreErrors
718
816
  })
719
817
  });
720
- this.agentTasks = (0, import_sdk_core2.withAgentTaskSessions)(core.agentTasks, {
818
+ this.agentTasks = (0, import_sdk_core3.withAgentTaskSessions)(core.agentTasks, {
721
819
  session: (options) => {
722
820
  if (options.transport === "websocket") {
723
821
  throw new MitraConfigurationError(
@@ -761,9 +859,9 @@ var DefaultMitraClient = class {
761
859
  return this.#initPromise;
762
860
  }
763
861
  async resolveDataSourceId() {
764
- const appInfo = (0, import_sdk_core2.expectObject)(
862
+ const appInfo = (0, import_sdk_core3.expectObject)(
765
863
  await this.#codeStudioHttpClient.get(
766
- `/api/v1/apps/${(0, import_sdk_core2.encodePathSegment)(this.#appId, "appId", coreErrors)}/info`
864
+ `/api/v1/apps/${(0, import_sdk_core3.encodePathSegment)(this.#appId, "appId", coreErrors)}/info`
767
865
  ),
768
866
  "App info response",
769
867
  coreErrors
@@ -788,9 +886,18 @@ function createClient(config = {}) {
788
886
  function createClientFromEnvironment(environment) {
789
887
  return createConfiguredClient(resolveConfig({}, environment));
790
888
  }
889
+ async function createClientFromApiKey(config = {}, environment) {
890
+ const options = resolveApiKeyOptions(config, environment);
891
+ const tokenProvider = createApiKeyTokenProvider(options);
892
+ const accessToken = await tokenProvider.get();
893
+ return createConfiguredClient({
894
+ ...resolveConfig({ ...config, accessToken, appId: options.appId }, environment),
895
+ tokenProvider
896
+ });
897
+ }
791
898
 
792
899
  // src/index.ts
793
- var import_sdk_core3 = require("@mitralab.io/sdk-core");
900
+ var import_sdk_core4 = require("@mitralab.io/sdk-core");
794
901
 
795
902
  // src/legacy/index.ts
796
903
  var legacy = __toESM(require("mitra-sdk"), 1);
@@ -864,6 +971,7 @@ var getDeployStatusMitra2 = legacy.getDeployStatusMitra;
864
971
  configureSdkMitra,
865
972
  createAgentMitra,
866
973
  createClient,
974
+ createClientFromApiKey,
867
975
  createClientFromEnvironment,
868
976
  createIntegrationMitra,
869
977
  createJdbcConnectionMitra,
package/dist/index.d.cts CHANGED
@@ -27,6 +27,8 @@ type Fetch = typeof globalThis.fetch;
27
27
  interface MitraEnvironment {
28
28
  MITRA_API_URL?: string;
29
29
  MITRA_PLATFORM_ACCESS_TOKEN?: string;
30
+ /** Api key created in Settings -> API keys. Traded for a token by the SDK. */
31
+ MITRA_API_KEY?: string;
30
32
  MITRA_APP_ID?: string;
31
33
  MITRA_DATA_SOURCE_ID?: string;
32
34
  /** Existing Server Function base URL. Used to derive the native API root when needed. */
@@ -42,6 +44,8 @@ interface MitraClientConfig {
42
44
  /** Optional BFF base URL used only to configure deprecated reexports. */
43
45
  legacyBaseUrl?: string;
44
46
  accessToken?: string;
47
+ /** Api key created in Settings -> API keys, used by `createClientFromApiKey`. */
48
+ apiKey?: string;
45
49
  appId?: string;
46
50
  dataSourceId?: string;
47
51
  /** Optional request deadline. By default, the Functions runtime owns operation time limits. */
@@ -79,6 +83,19 @@ interface MitraClient {
79
83
  }
80
84
  declare function createClient(config?: MitraClientConfig): MitraClient;
81
85
  declare function createClientFromEnvironment(environment?: MitraEnvironment): MitraClient;
86
+ /**
87
+ * Builds a client that authenticates with an api key instead of a token you already hold.
88
+ *
89
+ * The key is traded for a token here and again whenever that token ages out, so a process
90
+ * that stays up for days keeps working. Reads `MITRA_API_KEY` when `apiKey` is omitted.
91
+ */
92
+ declare function createClientFromApiKey(config?: MitraClientConfig, environment?: MitraEnvironment): Promise<MitraClient>;
93
+
94
+ /** Resolves the bearer token for each request, renewing it when it expires. */
95
+ interface AccessTokenProvider {
96
+ get(): Promise<string>;
97
+ invalidate(): void;
98
+ }
82
99
 
83
100
  declare class MitraConfigurationError extends Error {
84
101
  constructor(message: string);
@@ -1023,4 +1040,4 @@ type GetDeployStatusOptions = legacy.GetDeployStatusOptions;
1023
1040
  */
1024
1041
  type GetDeployStatusResponse = legacy.GetDeployStatusResponse;
1025
1042
 
1026
- export { type Agent, type AgentChat, type AgentConnection, type AgentCredentialStatus, type AgentDeltaEvent, type AgentErrorEvent, type AgentMessage, type AgentModel, type AgentProvider, type AgentQueueChangeEvent, type AgentRawEvent, type AgentStatusChangeEvent, type AgentTaskCreatedEvent, type AgentTaskEventMap, type AgentTaskEventName, type AgentTaskSession, type AgentTaskStatus, type AgentTaskTransport, type AgentTimelineItem, type AgentToolEvent, type AgentTurnEndEvent, type AgentType, type AppScopedAppsModule, type AuthAgentCredentialResult, type AuthorizationConfig, type CallIntegrationOptions, type CallIntegrationResponse, type ChatManageAction, type ConnectAgentCredentialResult, type ConnectorTemplateResponse, type CreateAgentOptions, type CreateAgentResponse, type CreateIntegrationOptions, type CreateJdbcConnectionOptions, type CreateJdbcConnectionResponse, type CreateOnlineTableOptions, type CreateOnlineTableResponse, type CreateProjectOptions, type CreateProjectResponse, type CreateRecordOptions, type CreateRecordsBatchOptions, type CreateServerFunctionOptions, type CreateServerFunctionResponse, type CredentialAction, type CurrentAppModule, type DeleteAgentChatResult, type DeleteAgentOptions, type DeleteAgentResponse, type DeleteIntegrationOptions, type DeleteJdbcConnectionOptions, type DeleteJdbcConnectionResponse, type DeleteOnlineTableOptions, type DeleteOnlineTableResponse, type DeleteRecordOptions, type DeleteServerFunctionOptions, type DeleteServerFunctionResponse, type DeployToS3Options, type DeployToS3Response, type DeviceAuthAgentCredentialResult, type ExecutePublicServerFunctionAsyncResponse, type ExecutePublicServerFunctionOptions, type ExecuteServerFunctionAsyncOptions, type ExecuteServerFunctionAsyncResponse, type ExecuteServerFunctionOptions, type ExecuteServerFunctionResponse, type Fetch, type GetAgentTaskCreateOptions, type GetAgentTaskOpenOptions, type GetAgentTaskOptions, type GetDeployStatusOptions, type GetDeployStatusResponse, type GetGitConfigOptions, type GetGitConfigResponse, type GetIntegrationTemplateOptions, type GetProjectContextOptions, type GetProjectContextResponse, type GetProjectsResponse, type GetRecordOptions, type GetServerFunctionExecutionOptions, type GetServerFunctionExecutionResponse, type IntegrationResponse, type InviteUserOptions, type InviteUserResult, type ListAgentConnectionsResult, type ListAgentModelsResult, type ListAgentProvidersResult, type ListAgentsOptions, type ListAgentsResponse, type ListIntegrationTemplatesOptions, type ListIntegrationsOptions, type ListJdbcConnectionsOptions, type ListJdbcConnectionsResponse, type ListOnlineTablesOptions, type ListOnlineTablesResponse, type ListProjectsOptions, type ListProjectsResponse, type ListRecordsOptions, type ListRecordsResponse, type ListServerFunctionsOptions, type ListServerFunctionsResponse, type ListTablesOptions, type ListTablesResponse, type ManageAgentChatDeleteOptions, type ManageAgentChatListOptions, type ManageAgentChatOptions, type ManageAgentChatRenameOptions, type ManageAgentConnectionOptions, type ManageAgentCredentialOptions, MitraApiError, type MitraClient, type MitraClientConfig, type MitraConfig, MitraConfigurationError, type MitraEnvironment, type MitraSdkInstance, type PatchRecordOptions, type QueuedItem, type ReadAgentOptions, type ReadAgentResponse, type ReadServerFunctionOptions, type ReadServerFunctionResponse, type RenameAgentChatResult, type RunDdlOptions, type RunDdlResponse, type RunDmlOptions, type RunDmlResponse, type RunQueryOptions, type RunQueryResponse, type SendOptions, type StopServerFunctionExecutionOptions, type StopServerFunctionExecutionResponse, type TemplateField, type TestConnectionResponse, type TestIntegrationByIdOptions, type TestIntegrationOptions, type TogglePublicExecutionOptions, type TogglePublicExecutionResponse, type UnsubscribeUserOptions, type UnsubscribeUserResult, type UpdateAgentOptions, type UpdateAgentResponse, type UpdateIntegrationOptions, type UpdateJdbcConnectionOptions, type UpdateJdbcConnectionResponse, type UpdateOnlineTableOptions, type UpdateOnlineTableResponse, type UpdateProjectSettingsOptions, type UpdateProjectSettingsResponse, type UpdateRecordOptions, type UpdateServerFunctionOptions, type UpdateServerFunctionResponse, callIntegrationMitra, configureSdkMitra, createAgentMitra, createClient, createClientFromEnvironment, createIntegrationMitra, createJdbcConnectionMitra, createMitraSdkInstance, createOnlineTableMitra, createProjectMitra, createRecordMitra, createRecordsBatchMitra, createServerFunctionMitra, deleteAgentMitra, deleteIntegrationMitra, deleteJdbcConnectionMitra, deleteOnlineTableMitra, deleteRecordMitra, deleteServerFunctionMitra, deployToS3Mitra, executePublicServerFunctionAsyncMitra, executeServerFunctionAsyncMitra, executeServerFunctionMitra, getAgentTaskMitra, getDeployStatusMitra, getGitConfigMitra, getIntegrationTemplateMitra, getProjectContextMitra, getProjectsMitra, getRecordMitra, getServerFunctionExecutionMitra, inviteUserMitra, listAgentsMitra, listIntegrationTemplatesMitra, listIntegrationsMitra, listJdbcConnectionsMitra, listOnlineTablesMitra, listProjectsMitra, listRecordsMitra, listServerFunctionsMitra, listTablesMitra, manageAgentChatMitra, manageAgentConnectionMitra, manageAgentCredentialMitra, patchRecordMitra, readAgentMitra, readServerFunctionMitra, resolveProjectId, runDdlMitra, runDmlMitra, runQueryMitra, stopServerFunctionExecutionMitra, testIntegrationByIdMitra, testIntegrationMitra, togglePublicExecutionMitra, unsubscribeUserMitra, updateAgentMitra, updateIntegrationMitra, updateJdbcConnectionMitra, updateOnlineTableMitra, updateProjectSettingsMitra, updateRecordMitra, updateServerFunctionMitra };
1043
+ export { type AccessTokenProvider, type Agent, type AgentChat, type AgentConnection, type AgentCredentialStatus, type AgentDeltaEvent, type AgentErrorEvent, type AgentMessage, type AgentModel, type AgentProvider, type AgentQueueChangeEvent, type AgentRawEvent, type AgentStatusChangeEvent, type AgentTaskCreatedEvent, type AgentTaskEventMap, type AgentTaskEventName, type AgentTaskSession, type AgentTaskStatus, type AgentTaskTransport, type AgentTimelineItem, type AgentToolEvent, type AgentTurnEndEvent, type AgentType, type AppScopedAppsModule, type AuthAgentCredentialResult, type AuthorizationConfig, type CallIntegrationOptions, type CallIntegrationResponse, type ChatManageAction, type ConnectAgentCredentialResult, type ConnectorTemplateResponse, type CreateAgentOptions, type CreateAgentResponse, type CreateIntegrationOptions, type CreateJdbcConnectionOptions, type CreateJdbcConnectionResponse, type CreateOnlineTableOptions, type CreateOnlineTableResponse, type CreateProjectOptions, type CreateProjectResponse, type CreateRecordOptions, type CreateRecordsBatchOptions, type CreateServerFunctionOptions, type CreateServerFunctionResponse, type CredentialAction, type CurrentAppModule, type DeleteAgentChatResult, type DeleteAgentOptions, type DeleteAgentResponse, type DeleteIntegrationOptions, type DeleteJdbcConnectionOptions, type DeleteJdbcConnectionResponse, type DeleteOnlineTableOptions, type DeleteOnlineTableResponse, type DeleteRecordOptions, type DeleteServerFunctionOptions, type DeleteServerFunctionResponse, type DeployToS3Options, type DeployToS3Response, type DeviceAuthAgentCredentialResult, type ExecutePublicServerFunctionAsyncResponse, type ExecutePublicServerFunctionOptions, type ExecuteServerFunctionAsyncOptions, type ExecuteServerFunctionAsyncResponse, type ExecuteServerFunctionOptions, type ExecuteServerFunctionResponse, type Fetch, type GetAgentTaskCreateOptions, type GetAgentTaskOpenOptions, type GetAgentTaskOptions, type GetDeployStatusOptions, type GetDeployStatusResponse, type GetGitConfigOptions, type GetGitConfigResponse, type GetIntegrationTemplateOptions, type GetProjectContextOptions, type GetProjectContextResponse, type GetProjectsResponse, type GetRecordOptions, type GetServerFunctionExecutionOptions, type GetServerFunctionExecutionResponse, type IntegrationResponse, type InviteUserOptions, type InviteUserResult, type ListAgentConnectionsResult, type ListAgentModelsResult, type ListAgentProvidersResult, type ListAgentsOptions, type ListAgentsResponse, type ListIntegrationTemplatesOptions, type ListIntegrationsOptions, type ListJdbcConnectionsOptions, type ListJdbcConnectionsResponse, type ListOnlineTablesOptions, type ListOnlineTablesResponse, type ListProjectsOptions, type ListProjectsResponse, type ListRecordsOptions, type ListRecordsResponse, type ListServerFunctionsOptions, type ListServerFunctionsResponse, type ListTablesOptions, type ListTablesResponse, type ManageAgentChatDeleteOptions, type ManageAgentChatListOptions, type ManageAgentChatOptions, type ManageAgentChatRenameOptions, type ManageAgentConnectionOptions, type ManageAgentCredentialOptions, MitraApiError, type MitraClient, type MitraClientConfig, type MitraConfig, MitraConfigurationError, type MitraEnvironment, type MitraSdkInstance, type PatchRecordOptions, type QueuedItem, type ReadAgentOptions, type ReadAgentResponse, type ReadServerFunctionOptions, type ReadServerFunctionResponse, type RenameAgentChatResult, type RunDdlOptions, type RunDdlResponse, type RunDmlOptions, type RunDmlResponse, type RunQueryOptions, type RunQueryResponse, type SendOptions, type StopServerFunctionExecutionOptions, type StopServerFunctionExecutionResponse, type TemplateField, type TestConnectionResponse, type TestIntegrationByIdOptions, type TestIntegrationOptions, type TogglePublicExecutionOptions, type TogglePublicExecutionResponse, type UnsubscribeUserOptions, type UnsubscribeUserResult, type UpdateAgentOptions, type UpdateAgentResponse, type UpdateIntegrationOptions, type UpdateJdbcConnectionOptions, type UpdateJdbcConnectionResponse, type UpdateOnlineTableOptions, type UpdateOnlineTableResponse, type UpdateProjectSettingsOptions, type UpdateProjectSettingsResponse, type UpdateRecordOptions, type UpdateServerFunctionOptions, type UpdateServerFunctionResponse, callIntegrationMitra, configureSdkMitra, createAgentMitra, createClient, createClientFromApiKey, createClientFromEnvironment, createIntegrationMitra, createJdbcConnectionMitra, createMitraSdkInstance, createOnlineTableMitra, createProjectMitra, createRecordMitra, createRecordsBatchMitra, createServerFunctionMitra, deleteAgentMitra, deleteIntegrationMitra, deleteJdbcConnectionMitra, deleteOnlineTableMitra, deleteRecordMitra, deleteServerFunctionMitra, deployToS3Mitra, executePublicServerFunctionAsyncMitra, executeServerFunctionAsyncMitra, executeServerFunctionMitra, getAgentTaskMitra, getDeployStatusMitra, getGitConfigMitra, getIntegrationTemplateMitra, getProjectContextMitra, getProjectsMitra, getRecordMitra, getServerFunctionExecutionMitra, inviteUserMitra, listAgentsMitra, listIntegrationTemplatesMitra, listIntegrationsMitra, listJdbcConnectionsMitra, listOnlineTablesMitra, listProjectsMitra, listRecordsMitra, listServerFunctionsMitra, listTablesMitra, manageAgentChatMitra, manageAgentConnectionMitra, manageAgentCredentialMitra, patchRecordMitra, readAgentMitra, readServerFunctionMitra, resolveProjectId, runDdlMitra, runDmlMitra, runQueryMitra, stopServerFunctionExecutionMitra, testIntegrationByIdMitra, testIntegrationMitra, togglePublicExecutionMitra, unsubscribeUserMitra, updateAgentMitra, updateIntegrationMitra, updateJdbcConnectionMitra, updateOnlineTableMitra, updateProjectSettingsMitra, updateRecordMitra, updateServerFunctionMitra };
package/dist/index.d.ts CHANGED
@@ -27,6 +27,8 @@ type Fetch = typeof globalThis.fetch;
27
27
  interface MitraEnvironment {
28
28
  MITRA_API_URL?: string;
29
29
  MITRA_PLATFORM_ACCESS_TOKEN?: string;
30
+ /** Api key created in Settings -> API keys. Traded for a token by the SDK. */
31
+ MITRA_API_KEY?: string;
30
32
  MITRA_APP_ID?: string;
31
33
  MITRA_DATA_SOURCE_ID?: string;
32
34
  /** Existing Server Function base URL. Used to derive the native API root when needed. */
@@ -42,6 +44,8 @@ interface MitraClientConfig {
42
44
  /** Optional BFF base URL used only to configure deprecated reexports. */
43
45
  legacyBaseUrl?: string;
44
46
  accessToken?: string;
47
+ /** Api key created in Settings -> API keys, used by `createClientFromApiKey`. */
48
+ apiKey?: string;
45
49
  appId?: string;
46
50
  dataSourceId?: string;
47
51
  /** Optional request deadline. By default, the Functions runtime owns operation time limits. */
@@ -79,6 +83,19 @@ interface MitraClient {
79
83
  }
80
84
  declare function createClient(config?: MitraClientConfig): MitraClient;
81
85
  declare function createClientFromEnvironment(environment?: MitraEnvironment): MitraClient;
86
+ /**
87
+ * Builds a client that authenticates with an api key instead of a token you already hold.
88
+ *
89
+ * The key is traded for a token here and again whenever that token ages out, so a process
90
+ * that stays up for days keeps working. Reads `MITRA_API_KEY` when `apiKey` is omitted.
91
+ */
92
+ declare function createClientFromApiKey(config?: MitraClientConfig, environment?: MitraEnvironment): Promise<MitraClient>;
93
+
94
+ /** Resolves the bearer token for each request, renewing it when it expires. */
95
+ interface AccessTokenProvider {
96
+ get(): Promise<string>;
97
+ invalidate(): void;
98
+ }
82
99
 
83
100
  declare class MitraConfigurationError extends Error {
84
101
  constructor(message: string);
@@ -1023,4 +1040,4 @@ type GetDeployStatusOptions = legacy.GetDeployStatusOptions;
1023
1040
  */
1024
1041
  type GetDeployStatusResponse = legacy.GetDeployStatusResponse;
1025
1042
 
1026
- export { type Agent, type AgentChat, type AgentConnection, type AgentCredentialStatus, type AgentDeltaEvent, type AgentErrorEvent, type AgentMessage, type AgentModel, type AgentProvider, type AgentQueueChangeEvent, type AgentRawEvent, type AgentStatusChangeEvent, type AgentTaskCreatedEvent, type AgentTaskEventMap, type AgentTaskEventName, type AgentTaskSession, type AgentTaskStatus, type AgentTaskTransport, type AgentTimelineItem, type AgentToolEvent, type AgentTurnEndEvent, type AgentType, type AppScopedAppsModule, type AuthAgentCredentialResult, type AuthorizationConfig, type CallIntegrationOptions, type CallIntegrationResponse, type ChatManageAction, type ConnectAgentCredentialResult, type ConnectorTemplateResponse, type CreateAgentOptions, type CreateAgentResponse, type CreateIntegrationOptions, type CreateJdbcConnectionOptions, type CreateJdbcConnectionResponse, type CreateOnlineTableOptions, type CreateOnlineTableResponse, type CreateProjectOptions, type CreateProjectResponse, type CreateRecordOptions, type CreateRecordsBatchOptions, type CreateServerFunctionOptions, type CreateServerFunctionResponse, type CredentialAction, type CurrentAppModule, type DeleteAgentChatResult, type DeleteAgentOptions, type DeleteAgentResponse, type DeleteIntegrationOptions, type DeleteJdbcConnectionOptions, type DeleteJdbcConnectionResponse, type DeleteOnlineTableOptions, type DeleteOnlineTableResponse, type DeleteRecordOptions, type DeleteServerFunctionOptions, type DeleteServerFunctionResponse, type DeployToS3Options, type DeployToS3Response, type DeviceAuthAgentCredentialResult, type ExecutePublicServerFunctionAsyncResponse, type ExecutePublicServerFunctionOptions, type ExecuteServerFunctionAsyncOptions, type ExecuteServerFunctionAsyncResponse, type ExecuteServerFunctionOptions, type ExecuteServerFunctionResponse, type Fetch, type GetAgentTaskCreateOptions, type GetAgentTaskOpenOptions, type GetAgentTaskOptions, type GetDeployStatusOptions, type GetDeployStatusResponse, type GetGitConfigOptions, type GetGitConfigResponse, type GetIntegrationTemplateOptions, type GetProjectContextOptions, type GetProjectContextResponse, type GetProjectsResponse, type GetRecordOptions, type GetServerFunctionExecutionOptions, type GetServerFunctionExecutionResponse, type IntegrationResponse, type InviteUserOptions, type InviteUserResult, type ListAgentConnectionsResult, type ListAgentModelsResult, type ListAgentProvidersResult, type ListAgentsOptions, type ListAgentsResponse, type ListIntegrationTemplatesOptions, type ListIntegrationsOptions, type ListJdbcConnectionsOptions, type ListJdbcConnectionsResponse, type ListOnlineTablesOptions, type ListOnlineTablesResponse, type ListProjectsOptions, type ListProjectsResponse, type ListRecordsOptions, type ListRecordsResponse, type ListServerFunctionsOptions, type ListServerFunctionsResponse, type ListTablesOptions, type ListTablesResponse, type ManageAgentChatDeleteOptions, type ManageAgentChatListOptions, type ManageAgentChatOptions, type ManageAgentChatRenameOptions, type ManageAgentConnectionOptions, type ManageAgentCredentialOptions, MitraApiError, type MitraClient, type MitraClientConfig, type MitraConfig, MitraConfigurationError, type MitraEnvironment, type MitraSdkInstance, type PatchRecordOptions, type QueuedItem, type ReadAgentOptions, type ReadAgentResponse, type ReadServerFunctionOptions, type ReadServerFunctionResponse, type RenameAgentChatResult, type RunDdlOptions, type RunDdlResponse, type RunDmlOptions, type RunDmlResponse, type RunQueryOptions, type RunQueryResponse, type SendOptions, type StopServerFunctionExecutionOptions, type StopServerFunctionExecutionResponse, type TemplateField, type TestConnectionResponse, type TestIntegrationByIdOptions, type TestIntegrationOptions, type TogglePublicExecutionOptions, type TogglePublicExecutionResponse, type UnsubscribeUserOptions, type UnsubscribeUserResult, type UpdateAgentOptions, type UpdateAgentResponse, type UpdateIntegrationOptions, type UpdateJdbcConnectionOptions, type UpdateJdbcConnectionResponse, type UpdateOnlineTableOptions, type UpdateOnlineTableResponse, type UpdateProjectSettingsOptions, type UpdateProjectSettingsResponse, type UpdateRecordOptions, type UpdateServerFunctionOptions, type UpdateServerFunctionResponse, callIntegrationMitra, configureSdkMitra, createAgentMitra, createClient, createClientFromEnvironment, createIntegrationMitra, createJdbcConnectionMitra, createMitraSdkInstance, createOnlineTableMitra, createProjectMitra, createRecordMitra, createRecordsBatchMitra, createServerFunctionMitra, deleteAgentMitra, deleteIntegrationMitra, deleteJdbcConnectionMitra, deleteOnlineTableMitra, deleteRecordMitra, deleteServerFunctionMitra, deployToS3Mitra, executePublicServerFunctionAsyncMitra, executeServerFunctionAsyncMitra, executeServerFunctionMitra, getAgentTaskMitra, getDeployStatusMitra, getGitConfigMitra, getIntegrationTemplateMitra, getProjectContextMitra, getProjectsMitra, getRecordMitra, getServerFunctionExecutionMitra, inviteUserMitra, listAgentsMitra, listIntegrationTemplatesMitra, listIntegrationsMitra, listJdbcConnectionsMitra, listOnlineTablesMitra, listProjectsMitra, listRecordsMitra, listServerFunctionsMitra, listTablesMitra, manageAgentChatMitra, manageAgentConnectionMitra, manageAgentCredentialMitra, patchRecordMitra, readAgentMitra, readServerFunctionMitra, resolveProjectId, runDdlMitra, runDmlMitra, runQueryMitra, stopServerFunctionExecutionMitra, testIntegrationByIdMitra, testIntegrationMitra, togglePublicExecutionMitra, unsubscribeUserMitra, updateAgentMitra, updateIntegrationMitra, updateJdbcConnectionMitra, updateOnlineTableMitra, updateProjectSettingsMitra, updateRecordMitra, updateServerFunctionMitra };
1043
+ export { type AccessTokenProvider, type Agent, type AgentChat, type AgentConnection, type AgentCredentialStatus, type AgentDeltaEvent, type AgentErrorEvent, type AgentMessage, type AgentModel, type AgentProvider, type AgentQueueChangeEvent, type AgentRawEvent, type AgentStatusChangeEvent, type AgentTaskCreatedEvent, type AgentTaskEventMap, type AgentTaskEventName, type AgentTaskSession, type AgentTaskStatus, type AgentTaskTransport, type AgentTimelineItem, type AgentToolEvent, type AgentTurnEndEvent, type AgentType, type AppScopedAppsModule, type AuthAgentCredentialResult, type AuthorizationConfig, type CallIntegrationOptions, type CallIntegrationResponse, type ChatManageAction, type ConnectAgentCredentialResult, type ConnectorTemplateResponse, type CreateAgentOptions, type CreateAgentResponse, type CreateIntegrationOptions, type CreateJdbcConnectionOptions, type CreateJdbcConnectionResponse, type CreateOnlineTableOptions, type CreateOnlineTableResponse, type CreateProjectOptions, type CreateProjectResponse, type CreateRecordOptions, type CreateRecordsBatchOptions, type CreateServerFunctionOptions, type CreateServerFunctionResponse, type CredentialAction, type CurrentAppModule, type DeleteAgentChatResult, type DeleteAgentOptions, type DeleteAgentResponse, type DeleteIntegrationOptions, type DeleteJdbcConnectionOptions, type DeleteJdbcConnectionResponse, type DeleteOnlineTableOptions, type DeleteOnlineTableResponse, type DeleteRecordOptions, type DeleteServerFunctionOptions, type DeleteServerFunctionResponse, type DeployToS3Options, type DeployToS3Response, type DeviceAuthAgentCredentialResult, type ExecutePublicServerFunctionAsyncResponse, type ExecutePublicServerFunctionOptions, type ExecuteServerFunctionAsyncOptions, type ExecuteServerFunctionAsyncResponse, type ExecuteServerFunctionOptions, type ExecuteServerFunctionResponse, type Fetch, type GetAgentTaskCreateOptions, type GetAgentTaskOpenOptions, type GetAgentTaskOptions, type GetDeployStatusOptions, type GetDeployStatusResponse, type GetGitConfigOptions, type GetGitConfigResponse, type GetIntegrationTemplateOptions, type GetProjectContextOptions, type GetProjectContextResponse, type GetProjectsResponse, type GetRecordOptions, type GetServerFunctionExecutionOptions, type GetServerFunctionExecutionResponse, type IntegrationResponse, type InviteUserOptions, type InviteUserResult, type ListAgentConnectionsResult, type ListAgentModelsResult, type ListAgentProvidersResult, type ListAgentsOptions, type ListAgentsResponse, type ListIntegrationTemplatesOptions, type ListIntegrationsOptions, type ListJdbcConnectionsOptions, type ListJdbcConnectionsResponse, type ListOnlineTablesOptions, type ListOnlineTablesResponse, type ListProjectsOptions, type ListProjectsResponse, type ListRecordsOptions, type ListRecordsResponse, type ListServerFunctionsOptions, type ListServerFunctionsResponse, type ListTablesOptions, type ListTablesResponse, type ManageAgentChatDeleteOptions, type ManageAgentChatListOptions, type ManageAgentChatOptions, type ManageAgentChatRenameOptions, type ManageAgentConnectionOptions, type ManageAgentCredentialOptions, MitraApiError, type MitraClient, type MitraClientConfig, type MitraConfig, MitraConfigurationError, type MitraEnvironment, type MitraSdkInstance, type PatchRecordOptions, type QueuedItem, type ReadAgentOptions, type ReadAgentResponse, type ReadServerFunctionOptions, type ReadServerFunctionResponse, type RenameAgentChatResult, type RunDdlOptions, type RunDdlResponse, type RunDmlOptions, type RunDmlResponse, type RunQueryOptions, type RunQueryResponse, type SendOptions, type StopServerFunctionExecutionOptions, type StopServerFunctionExecutionResponse, type TemplateField, type TestConnectionResponse, type TestIntegrationByIdOptions, type TestIntegrationOptions, type TogglePublicExecutionOptions, type TogglePublicExecutionResponse, type UnsubscribeUserOptions, type UnsubscribeUserResult, type UpdateAgentOptions, type UpdateAgentResponse, type UpdateIntegrationOptions, type UpdateJdbcConnectionOptions, type UpdateJdbcConnectionResponse, type UpdateOnlineTableOptions, type UpdateOnlineTableResponse, type UpdateProjectSettingsOptions, type UpdateProjectSettingsResponse, type UpdateRecordOptions, type UpdateServerFunctionOptions, type UpdateServerFunctionResponse, callIntegrationMitra, configureSdkMitra, createAgentMitra, createClient, createClientFromApiKey, createClientFromEnvironment, createIntegrationMitra, createJdbcConnectionMitra, createMitraSdkInstance, createOnlineTableMitra, createProjectMitra, createRecordMitra, createRecordsBatchMitra, createServerFunctionMitra, deleteAgentMitra, deleteIntegrationMitra, deleteJdbcConnectionMitra, deleteOnlineTableMitra, deleteRecordMitra, deleteServerFunctionMitra, deployToS3Mitra, executePublicServerFunctionAsyncMitra, executeServerFunctionAsyncMitra, executeServerFunctionMitra, getAgentTaskMitra, getDeployStatusMitra, getGitConfigMitra, getIntegrationTemplateMitra, getProjectContextMitra, getProjectsMitra, getRecordMitra, getServerFunctionExecutionMitra, inviteUserMitra, listAgentsMitra, listIntegrationTemplatesMitra, listIntegrationsMitra, listJdbcConnectionsMitra, listOnlineTablesMitra, listProjectsMitra, listRecordsMitra, listServerFunctionsMitra, listTablesMitra, manageAgentChatMitra, manageAgentConnectionMitra, manageAgentCredentialMitra, patchRecordMitra, readAgentMitra, readServerFunctionMitra, resolveProjectId, runDdlMitra, runDmlMitra, runQueryMitra, stopServerFunctionExecutionMitra, testIntegrationByIdMitra, testIntegrationMitra, togglePublicExecutionMitra, unsubscribeUserMitra, updateAgentMitra, updateIntegrationMitra, updateJdbcConnectionMitra, updateOnlineTableMitra, updateProjectSettingsMitra, updateRecordMitra, updateServerFunctionMitra };
package/dist/index.js CHANGED
@@ -120,9 +120,13 @@ function createApiError(response, payload, accessToken) {
120
120
  ...retryable === void 0 ? {} : { retryable }
121
121
  });
122
122
  }
123
+ function isUnauthorized(error) {
124
+ return error instanceof MitraApiError && error.status === 401;
125
+ }
123
126
  var HttpClient = class {
124
127
  #authentication;
125
128
  #accessToken;
129
+ #tokenProvider;
126
130
  baseUrl;
127
131
  appId;
128
132
  timeoutMs;
@@ -131,21 +135,28 @@ var HttpClient = class {
131
135
  this.baseUrl = config.baseUrl;
132
136
  this.#authentication = config.authentication;
133
137
  this.#accessToken = config.authentication === "bearer" ? config.accessToken : void 0;
138
+ this.#tokenProvider = config.authentication === "bearer" ? config.tokenProvider : void 0;
134
139
  this.appId = config.authentication === "bearer" ? config.appId : void 0;
135
140
  this.timeoutMs = config.timeoutMs;
136
141
  this.fetchImplementation = config.fetch;
137
142
  }
138
143
  async request(path, options = {}) {
144
+ try {
145
+ return await this.attempt(path, options);
146
+ } catch (error) {
147
+ if (this.#tokenProvider === void 0 || !isUnauthorized(error)) throw error;
148
+ this.#tokenProvider.invalidate();
149
+ return this.attempt(path, options);
150
+ }
151
+ }
152
+ async attempt(path, options) {
139
153
  const url = new URL(`${this.baseUrl}${path}`);
140
154
  appendQueryParameters(url, options.params ?? {});
141
155
  const controller = this.timeoutMs === void 0 ? void 0 : new AbortController();
142
156
  const timeout = controller === void 0 ? void 0 : setTimeout(() => controller.abort(), this.timeoutMs);
143
157
  const hasBody = options.body !== void 0;
144
- const authentication = this.#authentication === "bearer" ? {
145
- type: "bearer",
146
- accessToken: this.#accessToken,
147
- appId: this.appId
148
- } : { type: "anonymous" };
158
+ const accessToken = this.#authentication === "bearer" ? await this.#tokenProvider?.get() ?? this.#accessToken : void 0;
159
+ const authentication = accessToken === void 0 ? { type: "anonymous" } : { type: "bearer", accessToken, appId: this.appId };
149
160
  try {
150
161
  const response = await this.fetchImplementation(url, {
151
162
  method: options.method ?? "GET",
@@ -156,7 +167,7 @@ var HttpClient = class {
156
167
  });
157
168
  if (response.status === 204) return void 0;
158
169
  const payload = await parsePayload(response);
159
- if (!response.ok) throw createApiError(response, payload, this.#accessToken);
170
+ if (!response.ok) throw createApiError(response, payload, accessToken);
160
171
  return payload;
161
172
  } catch (error) {
162
173
  if (error instanceof MitraApiError) throw error;
@@ -457,6 +468,75 @@ function createAppScopedAppsModule(apps, appId) {
457
468
  };
458
469
  }
459
470
 
471
+ // src/api-key.ts
472
+ import { readTokenExpiry, resolveApiKeyToken } from "@mitralab.io/sdk-core";
473
+
474
+ // src/core-errors.ts
475
+ var coreErrors = {
476
+ configuration: (message) => new MitraConfigurationError(message),
477
+ invalidResponse: (message) => new MitraApiError(message, 200, { code: "INVALID_RESPONSE", retryable: false })
478
+ };
479
+
480
+ // src/api-key.ts
481
+ var EXPIRY_SKEW_MS = 5 * 60 * 1e3;
482
+ var IAM_BASE = "/iam";
483
+ async function exchangeApiKey(options) {
484
+ const { apiUrl, apiKey, appId, fetch: fetchImplementation } = options;
485
+ return resolveApiKeyToken(
486
+ async (path, init) => {
487
+ const response = await fetchImplementation(new URL(`${apiUrl}${IAM_BASE}${path}`), {
488
+ method: "POST",
489
+ headers: {
490
+ "Content-Type": "application/json",
491
+ ...init.bearer === void 0 ? {} : { Authorization: `Bearer ${init.bearer}` }
492
+ },
493
+ ...init.body === void 0 ? {} : { body: JSON.stringify(init.body) },
494
+ redirect: "manual"
495
+ });
496
+ if (!response.ok) {
497
+ throw new MitraApiError(
498
+ `Api key authentication failed with status ${response.status}`,
499
+ response.status,
500
+ {
501
+ code: response.status === 401 ? "INVALID_CREDENTIALS" : "AUTHENTICATION_FAILED",
502
+ retryable: response.status >= 500
503
+ }
504
+ );
505
+ }
506
+ return response.json();
507
+ },
508
+ appId,
509
+ apiKey,
510
+ coreErrors
511
+ );
512
+ }
513
+ function createApiKeyTokenProvider(options) {
514
+ if (!options.apiKey.trim()) {
515
+ throw new MitraConfigurationError("apiKey must not be empty");
516
+ }
517
+ let token = null;
518
+ let renewAfter = 0;
519
+ let pending = null;
520
+ return {
521
+ async get() {
522
+ if (token !== null && Date.now() < renewAfter) return token;
523
+ pending ??= exchangeApiKey(options).then((fresh) => {
524
+ const expiry = readTokenExpiry(fresh);
525
+ token = fresh;
526
+ renewAfter = expiry === null ? Number.MAX_SAFE_INTEGER : expiry - EXPIRY_SKEW_MS;
527
+ return fresh;
528
+ }).finally(() => {
529
+ pending = null;
530
+ });
531
+ return pending;
532
+ },
533
+ invalidate() {
534
+ token = null;
535
+ renewAfter = 0;
536
+ }
537
+ };
538
+ }
539
+
460
540
  // src/config.ts
461
541
  function readDefaultEnvironment() {
462
542
  return typeof process === "undefined" ? {} : process.env;
@@ -495,6 +575,26 @@ function deriveNativeApiUrl(legacyBaseUrl) {
495
575
  parsed.pathname = parsed.pathname.replace(/\/legacy\/?$/, "") || "/";
496
576
  return removeTrailingSlashes(parsed.toString());
497
577
  }
578
+ function resolveApiKeyOptions(config = {}, environment = readDefaultEnvironment()) {
579
+ const fetchImplementation = config.fetch ?? globalThis.fetch;
580
+ if (typeof fetchImplementation !== "function") {
581
+ throw new MitraConfigurationError("A fetch implementation is required");
582
+ }
583
+ return {
584
+ apiUrl: normalizeApiUrl(
585
+ requiredValue(
586
+ config.apiUrl ?? environment.MITRA_API_URL ?? deriveNativeApiUrl(environment.MITRA_BASE_URL),
587
+ "apiUrl"
588
+ )
589
+ ),
590
+ appId: requiredValue(
591
+ config.appId ?? environment.MITRA_APP_ID ?? environment.MITRA_PROJECT_ID,
592
+ "appId"
593
+ ),
594
+ apiKey: requiredValue(config.apiKey ?? environment.MITRA_API_KEY, "apiKey"),
595
+ fetch: fetchImplementation
596
+ };
597
+ }
498
598
  function resolveConfig(config = {}, environment = readDefaultEnvironment()) {
499
599
  const apiUrl = normalizeApiUrl(
500
600
  requiredValue(
@@ -544,10 +644,6 @@ function configureLegacySdk(config) {
544
644
  }
545
645
 
546
646
  // src/client.ts
547
- var coreErrors = {
548
- configuration: (message) => new MitraConfigurationError(message),
549
- invalidResponse: (message) => new MitraApiError(message, 200, { code: "INVALID_RESPONSE", retryable: false })
550
- };
551
647
  var DefaultMitraClient = class {
552
648
  agentConnections;
553
649
  agentCredentials;
@@ -586,6 +682,7 @@ var DefaultMitraClient = class {
586
682
  authentication: "bearer",
587
683
  accessToken: config.accessToken,
588
684
  appId: config.appId,
685
+ ...config.tokenProvider === void 0 ? {} : { tokenProvider: config.tokenProvider },
589
686
  ...config.timeoutMs === void 0 ? {} : { timeoutMs: config.timeoutMs },
590
687
  fetch: config.fetch
591
688
  });
@@ -695,6 +792,15 @@ function createClient(config = {}) {
695
792
  function createClientFromEnvironment(environment) {
696
793
  return createConfiguredClient(resolveConfig({}, environment));
697
794
  }
795
+ async function createClientFromApiKey(config = {}, environment) {
796
+ const options = resolveApiKeyOptions(config, environment);
797
+ const tokenProvider = createApiKeyTokenProvider(options);
798
+ const accessToken = await tokenProvider.get();
799
+ return createConfiguredClient({
800
+ ...resolveConfig({ ...config, accessToken, appId: options.appId }, environment),
801
+ tokenProvider
802
+ });
803
+ }
698
804
 
699
805
  // src/index.ts
700
806
  import { AgentTaskTurnError } from "@mitralab.io/sdk-core";
@@ -770,6 +876,7 @@ export {
770
876
  configureSdkMitra3 as configureSdkMitra,
771
877
  createAgentMitra2 as createAgentMitra,
772
878
  createClient,
879
+ createClientFromApiKey,
773
880
  createClientFromEnvironment,
774
881
  createIntegrationMitra2 as createIntegrationMitra,
775
882
  createJdbcConnectionMitra2 as createJdbcConnectionMitra,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mitralab.io/functions-sdk",
3
- "version": "0.2.0-beta.1",
3
+ "version": "0.2.0-beta.2",
4
4
  "description": "JavaScript and TypeScript SDK for Mitra Server Functions",
5
5
  "type": "module",
6
6
  "sideEffects": false,
@@ -67,7 +67,7 @@
67
67
  "node": ">=18.0.0"
68
68
  },
69
69
  "dependencies": {
70
- "@mitralab.io/sdk-core": "0.2.0-beta.1",
70
+ "@mitralab.io/sdk-core": "0.2.0-beta.3",
71
71
  "mitra-sdk": "1.0.63-beta.42"
72
72
  },
73
73
  "devDependencies": {