@workos-inc/node 10.7.0 → 10.8.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.
@@ -49,7 +49,7 @@ var SubtleCryptoProvider = class extends CryptoProvider {
49
49
  return await crypto.subtle.verify(algorithm, key, hmac, bufferB);
50
50
  }
51
51
  async encrypt(plaintext, key, iv, aad) {
52
- const actualIv = iv || crypto.getRandomValues(new Uint8Array(32));
52
+ const actualIv = iv || crypto.getRandomValues(/* @__PURE__ */ new Uint8Array(32));
53
53
  const cryptoKey = await this.subtleCrypto.importKey("raw", key, { name: "AES-GCM" }, false, ["encrypt"]);
54
54
  const encryptParams = {
55
55
  name: "AES-GCM",
@@ -95,23 +95,31 @@ var SubtleCryptoProvider = class extends CryptoProvider {
95
95
  };
96
96
  const byteHexMapping = new Array(256);
97
97
  for (let i = 0; i < byteHexMapping.length; i++) byteHexMapping[i] = i.toString(16).padStart(2, "0");
98
- //#endregion
99
- //#region src/common/net/http-client.ts
98
+ /**
99
+ * Upper bound on a server-provided `Retry-After` delay. Caps how long a
100
+ * single retry can sleep so an aggressive proxy or an HTTP-date far in the
101
+ * future can't hang the caller indefinitely.
102
+ */
103
+ const MAXIMUM_RETRY_AFTER_TIME_IN_MILLISECONDS = 6e4;
100
104
  var HttpClient = class HttpClient {
101
105
  baseURL;
102
106
  options;
103
- MAX_RETRY_ATTEMPTS = 3;
107
+ MAX_RETRY_ATTEMPTS;
104
108
  BACKOFF_MULTIPLIER = 1.5;
105
109
  MINIMUM_SLEEP_TIME_IN_MILLISECONDS = 500;
110
+ MAXIMUM_SLEEP_TIME_IN_MILLISECONDS = 8e3;
106
111
  RETRY_STATUS_CODES = [
107
112
  408,
113
+ 429,
108
114
  500,
109
115
  502,
116
+ 503,
110
117
  504
111
118
  ];
112
119
  constructor(baseURL, options) {
113
120
  this.baseURL = baseURL;
114
121
  this.options = options;
122
+ this.MAX_RETRY_ATTEMPTS = options?.maxRetries ?? 3;
115
123
  }
116
124
  static getResourceURL(baseURL, path, params) {
117
125
  const queryString = HttpClient.getQueryString(params);
@@ -132,13 +140,38 @@ var HttpClient = class HttpClient {
132
140
  if (entity === null || entity instanceof URLSearchParams) return entity;
133
141
  return JSON.stringify(entity);
134
142
  }
135
- static isPathRetryable(path) {
136
- return path.startsWith("/vault/") || path.startsWith("/audit_logs/events");
143
+ /**
144
+ * Generate a random idempotency key used to make retried write requests
145
+ * safe. Mirrors the behavior of the other WorkOS SDKs (Kotlin, Go), which
146
+ * attach an `Idempotency-Key` header to POST requests that did not already
147
+ * specify one, so a retried request is not applied more than once.
148
+ */
149
+ static generateIdempotencyKey() {
150
+ return `retry-${globalThis.crypto.randomUUID()}`;
151
+ }
152
+ /**
153
+ * Parse a `Retry-After` header value into milliseconds. Supports both the
154
+ * delay-seconds form (e.g. `120`) and the HTTP-date form. The result is
155
+ * capped at {@link MAXIMUM_RETRY_AFTER_TIME_IN_MILLISECONDS}. Returns
156
+ * `null` when the value is absent or unparseable so the caller falls back
157
+ * to the computed exponential backoff.
158
+ */
159
+ static parseRetryAfter(headerValue) {
160
+ if (headerValue == null) return null;
161
+ const trimmed = headerValue.trim();
162
+ if (trimmed === "") return null;
163
+ if (/^\d+$/.test(trimmed)) return Math.min(Number(trimmed) * 1e3, MAXIMUM_RETRY_AFTER_TIME_IN_MILLISECONDS);
164
+ const asDate = Date.parse(trimmed);
165
+ if (!Number.isNaN(asDate)) {
166
+ const delta = asDate - Date.now();
167
+ return delta < 0 ? 0 : Math.min(delta, MAXIMUM_RETRY_AFTER_TIME_IN_MILLISECONDS);
168
+ }
169
+ return null;
137
170
  }
138
171
  getSleepTimeInMilliseconds(retryAttempt) {
139
- return this.MINIMUM_SLEEP_TIME_IN_MILLISECONDS * Math.pow(this.BACKOFF_MULTIPLIER, retryAttempt) * (Math.random() + .5);
172
+ return Math.min(this.MINIMUM_SLEEP_TIME_IN_MILLISECONDS * Math.pow(this.BACKOFF_MULTIPLIER, retryAttempt), this.MAXIMUM_SLEEP_TIME_IN_MILLISECONDS) * (Math.random() + .5);
140
173
  }
141
- sleep = (retryAttempt) => new Promise((resolve) => setTimeout(resolve, this.getSleepTimeInMilliseconds(retryAttempt)));
174
+ sleep = (retryAttempt, retryAfterMs) => new Promise((resolve) => setTimeout(resolve, retryAfterMs != null ? retryAfterMs : this.getSleepTimeInMilliseconds(retryAttempt)));
142
175
  };
143
176
  var HttpClientResponse = class {
144
177
  _statusCode;
@@ -172,17 +205,19 @@ var ParseError = class extends Error {
172
205
  rawBody;
173
206
  rawStatus;
174
207
  requestID;
175
- constructor({ message, rawBody, rawStatus, requestID }) {
208
+ rawHeaders;
209
+ constructor({ message, rawBody, rawStatus, requestID, rawHeaders }) {
176
210
  super(message);
177
211
  this.rawBody = rawBody;
178
212
  this.rawStatus = rawStatus;
179
213
  this.requestID = requestID;
214
+ this.rawHeaders = rawHeaders;
180
215
  }
181
216
  };
182
217
  //#endregion
183
218
  //#region src/common/net/fetch-client.ts
184
219
  const DEFAULT_FETCH_TIMEOUT = 6e4;
185
- var FetchHttpClient = class extends HttpClient {
220
+ var FetchHttpClient = class FetchHttpClient extends HttpClient {
186
221
  baseURL;
187
222
  options;
188
223
  _fetchFn;
@@ -198,57 +233,39 @@ var FetchHttpClient = class extends HttpClient {
198
233
  }
199
234
  async get(path, options) {
200
235
  const resourceURL = HttpClient.getResourceURL(this.baseURL, path, options.params);
201
- if (HttpClient.isPathRetryable(path)) return await this.fetchRequestWithRetry(resourceURL, "GET", null, options.headers);
202
- else return await this.fetchRequest(resourceURL, "GET", null, options.headers);
236
+ return await this.fetchRequestWithRetry(resourceURL, "GET", null, options.headers, options.maxRetries);
203
237
  }
204
238
  async post(path, entity, options) {
205
239
  const resourceURL = HttpClient.getResourceURL(this.baseURL, path, options.params);
206
- if (HttpClient.isPathRetryable(path)) return await this.fetchRequestWithRetry(resourceURL, "POST", HttpClient.getBody(entity), {
207
- ...HttpClient.getContentTypeHeader(entity),
208
- ...options.headers
209
- });
210
- else return await this.fetchRequest(resourceURL, "POST", HttpClient.getBody(entity), {
240
+ return await this.fetchRequestWithRetry(resourceURL, "POST", HttpClient.getBody(entity), {
211
241
  ...HttpClient.getContentTypeHeader(entity),
212
242
  ...options.headers
213
- });
243
+ }, options.maxRetries);
214
244
  }
215
245
  async put(path, entity, options) {
216
246
  const resourceURL = HttpClient.getResourceURL(this.baseURL, path, options.params);
217
- if (HttpClient.isPathRetryable(path)) return await this.fetchRequestWithRetry(resourceURL, "PUT", HttpClient.getBody(entity), {
218
- ...HttpClient.getContentTypeHeader(entity),
219
- ...options.headers
220
- });
221
- else return await this.fetchRequest(resourceURL, "PUT", HttpClient.getBody(entity), {
247
+ return await this.fetchRequestWithRetry(resourceURL, "PUT", HttpClient.getBody(entity), {
222
248
  ...HttpClient.getContentTypeHeader(entity),
223
249
  ...options.headers
224
- });
250
+ }, options.maxRetries);
225
251
  }
226
252
  async patch(path, entity, options) {
227
253
  const resourceURL = HttpClient.getResourceURL(this.baseURL, path, options.params);
228
- if (HttpClient.isPathRetryable(path)) return await this.fetchRequestWithRetry(resourceURL, "PATCH", HttpClient.getBody(entity), {
229
- ...HttpClient.getContentTypeHeader(entity),
230
- ...options.headers
231
- });
232
- else return await this.fetchRequest(resourceURL, "PATCH", HttpClient.getBody(entity), {
254
+ return await this.fetchRequestWithRetry(resourceURL, "PATCH", HttpClient.getBody(entity), {
233
255
  ...HttpClient.getContentTypeHeader(entity),
234
256
  ...options.headers
235
- });
257
+ }, options.maxRetries);
236
258
  }
237
259
  async delete(path, options) {
238
260
  const resourceURL = HttpClient.getResourceURL(this.baseURL, path, options.params);
239
- if (HttpClient.isPathRetryable(path)) return await this.fetchRequestWithRetry(resourceURL, "DELETE", null, options.headers);
240
- else return await this.fetchRequest(resourceURL, "DELETE", null, options.headers);
261
+ return await this.fetchRequestWithRetry(resourceURL, "DELETE", null, options.headers, options.maxRetries);
241
262
  }
242
263
  async deleteWithBody(path, entity, options) {
243
264
  const resourceURL = HttpClient.getResourceURL(this.baseURL, path, options.params);
244
- if (HttpClient.isPathRetryable(path)) return await this.fetchRequestWithRetry(resourceURL, "DELETE", HttpClient.getBody(entity), {
265
+ return await this.fetchRequestWithRetry(resourceURL, "DELETE", HttpClient.getBody(entity), {
245
266
  ...HttpClient.getContentTypeHeader(entity),
246
267
  ...options.headers
247
- });
248
- else return await this.fetchRequest(resourceURL, "DELETE", HttpClient.getBody(entity), {
249
- ...HttpClient.getContentTypeHeader(entity),
250
- ...options.headers
251
- });
268
+ }, options.maxRetries);
252
269
  }
253
270
  async fetchRequest(url, method, body, headers) {
254
271
  const requestBody = body || (method === "POST" || method === "PUT" || method === "PATCH" ? "" : void 0);
@@ -283,7 +300,8 @@ var FetchHttpClient = class extends HttpClient {
283
300
  message: error.message,
284
301
  rawBody,
285
302
  requestID,
286
- rawStatus: res.status
303
+ rawStatus: res.status,
304
+ rawHeaders: res.headers
287
305
  });
288
306
  throw error;
289
307
  }
@@ -310,19 +328,21 @@ var FetchHttpClient = class extends HttpClient {
310
328
  throw error;
311
329
  }
312
330
  }
313
- async fetchRequestWithRetry(url, method, body, headers) {
331
+ async fetchRequestWithRetry(url, method, body, headers, maxRetries) {
332
+ const maxRetryAttempts = maxRetries ?? this.MAX_RETRY_ATTEMPTS;
333
+ const requestHeaders = FetchHttpClient.withIdempotencyKey(method, headers, maxRetryAttempts);
314
334
  let response;
315
335
  let retryAttempts = 1;
316
336
  const makeRequest = async () => {
317
337
  let requestError = null;
318
338
  try {
319
- response = await this.fetchRequest(url, method, body, headers);
339
+ response = await this.fetchRequest(url, method, body, requestHeaders);
320
340
  } catch (e) {
321
341
  requestError = e;
322
342
  }
323
- if (this.shouldRetryRequest(requestError, retryAttempts)) {
343
+ if (this.shouldRetryRequest(requestError, retryAttempts, maxRetryAttempts)) {
324
344
  retryAttempts++;
325
- await this.sleep(retryAttempts);
345
+ await this.sleep(retryAttempts, FetchHttpClient.getRetryAfterMs(requestError));
326
346
  return makeRequest();
327
347
  }
328
348
  if (requestError != null) throw requestError;
@@ -330,14 +350,37 @@ var FetchHttpClient = class extends HttpClient {
330
350
  };
331
351
  return makeRequest();
332
352
  }
333
- shouldRetryRequest(requestError, retryAttempt) {
334
- if (retryAttempt > this.MAX_RETRY_ATTEMPTS) return false;
353
+ shouldRetryRequest(requestError, retryAttempt, maxRetryAttempts) {
354
+ if (retryAttempt > maxRetryAttempts) return false;
335
355
  if (requestError != null) {
336
356
  if (requestError instanceof TypeError) return true;
337
357
  if (requestError instanceof HttpClientError && this.RETRY_STATUS_CODES.includes(requestError.response.status)) return true;
358
+ if (requestError instanceof ParseError && this.RETRY_STATUS_CODES.includes(requestError.rawStatus)) return true;
338
359
  }
339
360
  return false;
340
361
  }
362
+ static withIdempotencyKey(method, headers, maxRetryAttempts) {
363
+ if (method !== "POST" || maxRetryAttempts <= 0 || FetchHttpClient.hasHeader(headers, "Idempotency-Key")) return headers;
364
+ return {
365
+ ...headers,
366
+ "Idempotency-Key": HttpClient.generateIdempotencyKey()
367
+ };
368
+ }
369
+ static hasHeader(headers, name) {
370
+ if (!headers) return false;
371
+ const target = name.toLowerCase();
372
+ return Object.keys(headers).some((key) => key.toLowerCase() === target);
373
+ }
374
+ static getRetryAfterMs(requestError) {
375
+ let headers;
376
+ if (requestError instanceof HttpClientError) headers = requestError.response?.headers;
377
+ else if (requestError instanceof ParseError) headers = requestError.rawHeaders;
378
+ else return null;
379
+ let value;
380
+ if (headers && typeof headers.get === "function") value = headers.get("Retry-After");
381
+ else if (headers && typeof headers === "object") value = headers["Retry-After"] ?? headers["retry-after"];
382
+ return HttpClient.parseRetryAfter(value);
383
+ }
341
384
  };
342
385
  var FetchHttpClientResponse = class FetchHttpClientResponse extends HttpClientResponse {
343
386
  _res;
@@ -416,7 +459,7 @@ var GenericServerException = class extends Error {
416
459
  };
417
460
  //#endregion
418
461
  //#region src/common/exceptions/authentication.exception.ts
419
- const AUTHENTICATION_ERROR_CODES = new Set([
462
+ const AUTHENTICATION_ERROR_CODES = /* @__PURE__ */ new Set([
420
463
  "email_verification_required",
421
464
  "organization_selection_required",
422
465
  "mfa_enrollment",
@@ -1397,7 +1440,11 @@ function deserializeApiKey(apiKey) {
1397
1440
  return {
1398
1441
  object: apiKey.object,
1399
1442
  id: apiKey.id,
1400
- owner: apiKey.owner,
1443
+ owner: apiKey.owner.type === "user" ? {
1444
+ type: "user",
1445
+ id: apiKey.owner.id,
1446
+ organizationId: apiKey.owner.organization_id
1447
+ } : apiKey.owner,
1401
1448
  name: apiKey.name,
1402
1449
  obfuscatedValue: apiKey.obfuscated_value,
1403
1450
  lastUsedAt: apiKey.last_used_at,
@@ -2013,6 +2060,204 @@ var PKCE = class {
2013
2060
  }
2014
2061
  };
2015
2062
  //#endregion
2063
+ //#region src/utils/jose.ts
2064
+ let _josePromise;
2065
+ /**
2066
+ * Dynamically imports the jose library using import() to support Node.js 20.0-20.18.
2067
+ *
2068
+ * The jose library is ESM-only and cannot be loaded via require() in Node.js versions
2069
+ * before 20.19.0. This wrapper uses dynamic import() which works in both ESM and CJS
2070
+ * across all Node.js 20+ versions.
2071
+ *
2072
+ * This workaround can be removed when Node.js 20 reaches end-of-life (April 2026),
2073
+ * at which point we can bump to Node.js 22+ and use direct imports.
2074
+ *
2075
+ * @returns Promise that resolves to the jose module
2076
+ */
2077
+ function getJose() {
2078
+ return _josePromise ??= import("./webapi-BgpV54gi.mjs");
2079
+ }
2080
+ //#endregion
2081
+ //#region src/agents/serializers/agent-registration.serializer.ts
2082
+ function deserializeAgentRegistration(registration) {
2083
+ return {
2084
+ id: registration.id,
2085
+ agentIdentity: {
2086
+ id: registration.agent_identity.id,
2087
+ userlandUserId: registration.agent_identity.userland_user_id,
2088
+ createdAt: registration.agent_identity.created_at,
2089
+ updatedAt: registration.agent_identity.updated_at
2090
+ },
2091
+ organizationId: registration.organization_id,
2092
+ status: registration.status,
2093
+ kind: registration.kind,
2094
+ claim: registration.claim ? {
2095
+ id: registration.claim.id,
2096
+ claimCompletion: registration.claim.claim_completion ? {
2097
+ id: registration.claim.claim_completion.id,
2098
+ createdAt: registration.claim.claim_completion.created_at,
2099
+ updatedAt: registration.claim.claim_completion.updated_at,
2100
+ expiresAt: registration.claim.claim_completion.expires_at,
2101
+ claimedAt: registration.claim.claim_completion.claimed_at
2102
+ } : null,
2103
+ createdAt: registration.claim.created_at,
2104
+ updatedAt: registration.claim.updated_at,
2105
+ expiresAt: registration.claim.expires_at
2106
+ } : null,
2107
+ createdAt: registration.created_at,
2108
+ updatedAt: registration.updated_at
2109
+ };
2110
+ }
2111
+ //#endregion
2112
+ //#region src/agents/serializers/validate-agent-credential.serializer.ts
2113
+ function serializeValidateAgentCredentialOptions(options) {
2114
+ return {
2115
+ type: options.type,
2116
+ credential: options.credential,
2117
+ ...options.type === "access_token" && options.audience !== void 0 && { audience: options.audience }
2118
+ };
2119
+ }
2120
+ function deserializeAgentCredentialValidation(validation) {
2121
+ if (!validation.valid || validation.registration_id == null) return {
2122
+ valid: false,
2123
+ registrationId: null,
2124
+ expiresAt: null,
2125
+ claims: null
2126
+ };
2127
+ return {
2128
+ valid: true,
2129
+ registrationId: validation.registration_id,
2130
+ expiresAt: validation.expires_at,
2131
+ claims: null
2132
+ };
2133
+ }
2134
+ function deserializeAgentAccessTokenClaims(payload) {
2135
+ return {
2136
+ issuer: payload.iss,
2137
+ audience: payload.aud,
2138
+ registrationId: payload.sub,
2139
+ jti: payload.jti,
2140
+ organizationId: payload.org_id,
2141
+ scope: payload.scope,
2142
+ actor: payload.act,
2143
+ expiresAt: payload.exp,
2144
+ issuedAt: payload.iat
2145
+ };
2146
+ }
2147
+ //#endregion
2148
+ //#region src/agents/agents.ts
2149
+ /**
2150
+ * A decoded JWT payload is only an agent credential if it carries every claim
2151
+ * the SDK guarantees. A token signed by the same JWKS for another purpose
2152
+ * (e.g. a user session) lacks these and is rejected rather than reported valid
2153
+ * with empty identifiers.
2154
+ */
2155
+ function hasRequiredAgentClaims(payload) {
2156
+ return typeof payload.iss === "string" && (typeof payload.aud === "string" || Array.isArray(payload.aud)) && typeof payload.sub === "string" && typeof payload.jti === "string" && typeof payload.org_id === "string" && typeof payload.exp === "number" && typeof payload.iat === "number";
2157
+ }
2158
+ var Agents = class {
2159
+ workos;
2160
+ _jwks;
2161
+ constructor(workos) {
2162
+ this.workos = workos;
2163
+ }
2164
+ /**
2165
+ * Get an agent registration
2166
+ *
2167
+ * Retrieve a single agent registration scoped to the API key's environment.
2168
+ * @param id - Unique identifier of the agent registration.
2169
+ *
2170
+ * @example
2171
+ * "agent_reg_01EHZNVPK3SFK441A1RGBFSHRT"
2172
+ *
2173
+ * @returns {Promise<AgentRegistration>}
2174
+ * @throws {NotFoundException} 404
2175
+ */
2176
+ async getRegistration(id) {
2177
+ const { data } = await this.workos.get(`/agents/registrations/${encodeURIComponent(id)}`);
2178
+ return deserializeAgentRegistration(data);
2179
+ }
2180
+ /**
2181
+ * Validate an agent credential
2182
+ *
2183
+ * For `access_token` credentials, the token is decoded and verified locally
2184
+ * against the environment's JWKS and its claims are returned — no network
2185
+ * request is made unless `checkForRevoked` is set, in which case the WorkOS
2186
+ * API is also called to confirm the token has not been revoked.
2187
+ *
2188
+ * For `api_key` credentials, the WorkOS API is always called to validate the
2189
+ * key against the environment.
2190
+ *
2191
+ * @param options - Object containing the credential type and value.
2192
+ * @returns {Promise<AgentCredentialValidation>}
2193
+ */
2194
+ async validateCredential(options) {
2195
+ if (options.type === "access_token") return this.validateAccessToken(options);
2196
+ return this.validateCredentialRemotely(options);
2197
+ }
2198
+ async validateAccessToken(options) {
2199
+ const claims = await this.verifyAccessTokenClaims(options.credential, options.audience);
2200
+ if (!claims) return {
2201
+ valid: false,
2202
+ registrationId: null,
2203
+ expiresAt: null,
2204
+ claims: null
2205
+ };
2206
+ if (!options.checkForRevoked) return {
2207
+ valid: true,
2208
+ registrationId: claims.registrationId,
2209
+ expiresAt: (/* @__PURE__ */ new Date(claims.expiresAt * 1e3)).toISOString(),
2210
+ claims
2211
+ };
2212
+ const remote = await this.validateCredentialRemotely(options);
2213
+ if (!remote.valid) return remote;
2214
+ if (remote.registrationId !== claims.registrationId) return {
2215
+ valid: false,
2216
+ registrationId: null,
2217
+ expiresAt: null,
2218
+ claims: null
2219
+ };
2220
+ return {
2221
+ ...remote,
2222
+ claims
2223
+ };
2224
+ }
2225
+ async validateCredentialRemotely(options) {
2226
+ const { data } = await this.workos.post("/agents/credentials/validate", serializeValidateAgentCredentialOptions(options));
2227
+ return deserializeAgentCredentialValidation(data);
2228
+ }
2229
+ /**
2230
+ * Verifies an access token's signature, audience, and time claims against the
2231
+ * environment's JWKS and returns its decoded claims, or `null` when the token
2232
+ * is invalid (bad signature, wrong audience, expired, malformed, or missing
2233
+ * the agent identity claims). Errors that are not JWT validation failures
2234
+ * (e.g. network errors fetching the JWKS) propagate.
2235
+ *
2236
+ * The audience defaults to the client ID; resource-scoped tokens carry the
2237
+ * resource as their audience and require it to be passed explicitly.
2238
+ */
2239
+ async verifyAccessTokenClaims(credential, audience) {
2240
+ const { jwtVerify } = await getJose();
2241
+ const jwks = await this.getJWKS();
2242
+ try {
2243
+ const { payload } = await jwtVerify(credential, jwks, { audience: audience ?? this.workos.clientId });
2244
+ if (!hasRequiredAgentClaims(payload)) return null;
2245
+ if (payload.exp * 1e3 <= Date.now()) return null;
2246
+ return deserializeAgentAccessTokenClaims(payload);
2247
+ } catch (e) {
2248
+ if (e instanceof Error && "code" in e && typeof e.code === "string" && (e.code.startsWith("ERR_JWT_") || e.code.startsWith("ERR_JWS_"))) return null;
2249
+ throw e;
2250
+ }
2251
+ }
2252
+ async getJWKS() {
2253
+ const { clientId } = this.workos;
2254
+ if (!clientId) throw new Error("Missing client ID. Did you provide it when initializing WorkOS?");
2255
+ const { createRemoteJWKSet } = await getJose();
2256
+ this._jwks ??= createRemoteJWKSet(new URL(`${this.workos.baseURL}/sso/jwks/${clientId}`), { cooldownDuration: 1e3 * 60 * 5 });
2257
+ return this._jwks;
2258
+ }
2259
+ };
2260
+ //#endregion
2016
2261
  //#region src/api-keys/serializers/create-organization-api-key-options.serializer.ts
2017
2262
  function serializeCreateOrganizationApiKeyOptions(options) {
2018
2263
  return {
@@ -2039,7 +2284,10 @@ function deserializeCreatedApiKey(apiKey) {
2039
2284
  //#endregion
2040
2285
  //#region src/api-keys/serializers/validate-api-key.serializer.ts
2041
2286
  function deserializeValidateApiKeyResponse(response) {
2042
- return { apiKey: response.api_key ? deserializeApiKey(response.api_key) : null };
2287
+ return {
2288
+ apiKey: response.api_key ? deserializeApiKey(response.api_key) : null,
2289
+ ...typeof response.agent_registration_id === "undefined" ? void 0 : { agentRegistrationId: response.agent_registration_id }
2290
+ };
2043
2291
  }
2044
2292
  //#endregion
2045
2293
  //#region src/api-keys/api-keys.ts
@@ -2808,34 +3056,231 @@ var Passwordless = class {
2808
3056
  }
2809
3057
  };
2810
3058
  //#endregion
2811
- //#region src/pipes/serializers/access-token.serializer.ts
2812
- function deserializeAccessToken(serialized) {
2813
- return {
2814
- object: "access_token",
2815
- accessToken: serialized.access_token,
2816
- expiresAt: serialized.expires_at ? new Date(Date.parse(serialized.expires_at)) : null,
2817
- scopes: serialized.scopes,
2818
- missingScopes: serialized.missing_scopes
2819
- };
2820
- }
3059
+ //#region src/pipes/serializers/data-integration-credential.serializer.ts
3060
+ const deserializeDataIntegrationCredential = (response) => ({
3061
+ type: response.type,
3062
+ clientId: response.client_id ?? null,
3063
+ redactedClientSecret: response.redacted_client_secret ?? null
3064
+ });
2821
3065
  //#endregion
2822
- //#region src/pipes/serializers/get-access-token.serializer.ts
2823
- function serializeGetAccessTokenOptions(options) {
2824
- return {
2825
- user_id: options.userId,
2826
- organization_id: options.organizationId
2827
- };
2828
- }
2829
- function deserializeGetAccessTokenResponse(response) {
2830
- if (response.active) return {
2831
- active: true,
2832
- accessToken: deserializeAccessToken(response.access_token)
2833
- };
2834
- return {
2835
- active: false,
2836
- error: response.error
2837
- };
2838
- }
3066
+ //#region src/pipes/serializers/data-integration-custom-provider.serializer.ts
3067
+ const deserializeDataIntegrationCustomProvider = (response) => ({
3068
+ name: response.name,
3069
+ authorizationUrl: response.authorization_url ?? null,
3070
+ tokenUrl: response.token_url ?? null,
3071
+ refreshTokenUrl: response.refresh_token_url ?? null,
3072
+ pkceEnabled: response.pkce_enabled,
3073
+ requestScopeSeparator: response.request_scope_separator,
3074
+ scopesRequired: response.scopes_required,
3075
+ clientSecretRequired: response.client_secret_required,
3076
+ additionalAuthorizationParameters: response.additional_authorization_parameters,
3077
+ tokenBodyContentType: response.token_body_content_type,
3078
+ authenticateVia: response.authenticate_via
3079
+ });
3080
+ //#endregion
3081
+ //#region src/pipes/serializers/data-integration.serializer.ts
3082
+ const deserializeDataIntegration = (response) => ({
3083
+ object: response.object,
3084
+ id: response.id,
3085
+ slug: response.slug,
3086
+ integrationType: response.integration_type,
3087
+ description: response.description ?? null,
3088
+ enabled: response.enabled,
3089
+ state: response.state,
3090
+ scopes: response.scopes ?? null,
3091
+ redirectUri: response.redirect_uri,
3092
+ credentials: deserializeDataIntegrationCredential(response.credentials),
3093
+ customProvider: response.custom_provider != null ? deserializeDataIntegrationCustomProvider(response.custom_provider) : null,
3094
+ createdAt: new Date(response.created_at),
3095
+ updatedAt: new Date(response.updated_at)
3096
+ });
3097
+ //#endregion
3098
+ //#region src/pipes/serializers/connected-account.serializer.ts
3099
+ const deserializeConnectedAccount = (response) => ({
3100
+ object: response.object,
3101
+ id: response.id,
3102
+ userId: response.user_id ?? null,
3103
+ organizationId: response.organization_id ?? null,
3104
+ scopes: response.scopes,
3105
+ authMethod: response.auth_method,
3106
+ apiKeyLast4: response.api_key_last_4 ?? null,
3107
+ state: response.state,
3108
+ createdAt: response.created_at,
3109
+ updatedAt: response.updated_at
3110
+ });
3111
+ //#endregion
3112
+ //#region src/pipes/serializers/data-integration-authorize-url-response.serializer.ts
3113
+ const deserializeDataIntegrationAuthorizeUrlResponse = (response) => ({ url: response.url });
3114
+ //#endregion
3115
+ //#region src/pipes/serializers/data-integration-credentials-response-credential.serializer.ts
3116
+ const deserializeDataIntegrationCredentialsResponseCredential = (response) => ({
3117
+ object: response.object,
3118
+ authMethod: response.auth_method,
3119
+ value: response.value,
3120
+ expiresAt: response.expires_at ?? null,
3121
+ scopes: response.scopes,
3122
+ missingScopes: response.missing_scopes
3123
+ });
3124
+ //#endregion
3125
+ //#region src/pipes/serializers/data-integration-credentials-response.serializer.ts
3126
+ const deserializeDataIntegrationCredentialsResponse = (response) => ({
3127
+ active: response.active,
3128
+ credential: response.credential != null ? deserializeDataIntegrationCredentialsResponseCredential(response.credential) : void 0,
3129
+ error: response.error
3130
+ });
3131
+ //#endregion
3132
+ //#region src/pipes/serializers/data-integration-access-token-response-access-token.serializer.ts
3133
+ const deserializeDataIntegrationAccessTokenResponseAccessToken = (response) => ({
3134
+ object: response.object,
3135
+ accessToken: response.access_token,
3136
+ expiresAt: response.expires_at != null ? new Date(response.expires_at) : null,
3137
+ scopes: response.scopes,
3138
+ missingScopes: response.missing_scopes
3139
+ });
3140
+ //#endregion
3141
+ //#region src/pipes/serializers/data-integration-access-token-response.serializer.ts
3142
+ const deserializeDataIntegrationAccessTokenResponse = (response) => {
3143
+ switch (response.active) {
3144
+ case true: return {
3145
+ active: true,
3146
+ accessToken: deserializeDataIntegrationAccessTokenResponseAccessToken(response.access_token)
3147
+ };
3148
+ case false: return {
3149
+ active: false,
3150
+ error: response.error
3151
+ };
3152
+ default: throw new Error(`Unknown active: ${String(response.active)}`);
3153
+ }
3154
+ };
3155
+ //#endregion
3156
+ //#region src/pipes/serializers/data-integrations-list-response-data-connected-account.serializer.ts
3157
+ const deserializeDataIntegrationsListResponseDataConnectedAccount = (response) => ({
3158
+ object: response.object,
3159
+ id: response.id,
3160
+ userId: response.user_id ?? null,
3161
+ organizationId: response.organization_id ?? null,
3162
+ scopes: response.scopes,
3163
+ authMethod: response.auth_method,
3164
+ apiKeyLast4: response.api_key_last_4 ?? null,
3165
+ state: response.state,
3166
+ createdAt: response.created_at,
3167
+ updatedAt: response.updated_at,
3168
+ userlandUserId: response.userland_user_id ?? null
3169
+ });
3170
+ //#endregion
3171
+ //#region src/pipes/serializers/data-integrations-list-response-data.serializer.ts
3172
+ const deserializeDataIntegrationsListResponseData = (response) => ({
3173
+ object: response.object,
3174
+ id: response.id,
3175
+ name: response.name,
3176
+ description: response.description ?? null,
3177
+ slug: response.slug,
3178
+ integrationType: response.integration_type,
3179
+ credentialsType: response.credentials_type,
3180
+ scopes: response.scopes ?? null,
3181
+ authMethods: response.auth_methods,
3182
+ ownership: response.ownership,
3183
+ createdAt: response.created_at,
3184
+ updatedAt: response.updated_at,
3185
+ connectedAccount: response.connected_account != null ? deserializeDataIntegrationsListResponseDataConnectedAccount(response.connected_account) : null
3186
+ });
3187
+ //#endregion
3188
+ //#region src/pipes/serializers/data-integrations-list-response.serializer.ts
3189
+ const deserializeDataIntegrationsListResponse = (response) => ({
3190
+ object: response.object,
3191
+ data: response.data.map(deserializeDataIntegrationsListResponseData)
3192
+ });
3193
+ //#endregion
3194
+ //#region src/pipes/serializers/data-integration-credentials-dto.serializer.ts
3195
+ const serializeDataIntegrationCredentialsDto = (model) => ({
3196
+ type: model.type,
3197
+ client_id: model.clientId,
3198
+ client_secret: model.clientSecret
3199
+ });
3200
+ //#endregion
3201
+ //#region src/pipes/serializers/custom-provider-definition.serializer.ts
3202
+ const serializeCustomProviderDefinition = (model) => ({
3203
+ name: model.name,
3204
+ authorization_url: model.authorizationUrl,
3205
+ token_url: model.tokenUrl,
3206
+ refresh_token_url: model.refreshTokenUrl,
3207
+ pkce_enabled: model.pkceEnabled,
3208
+ request_scope_separator: model.requestScopeSeparator,
3209
+ scopes_required: model.scopesRequired,
3210
+ client_secret_required: model.clientSecretRequired,
3211
+ additional_authorization_parameters: model.additionalAuthorizationParameters,
3212
+ token_body_content_type: model.tokenBodyContentType,
3213
+ authenticate_via: model.authenticateVia
3214
+ });
3215
+ //#endregion
3216
+ //#region src/pipes/serializers/create-data-integration.serializer.ts
3217
+ const serializeCreateDataIntegration = (model) => ({
3218
+ provider: model.provider,
3219
+ description: model.description,
3220
+ enabled: model.enabled,
3221
+ scopes: model.scopes,
3222
+ credentials: model.credentials != null ? serializeDataIntegrationCredentialsDto(model.credentials) : void 0,
3223
+ custom_provider: model.customProvider != null ? serializeCustomProviderDefinition(model.customProvider) : void 0
3224
+ });
3225
+ //#endregion
3226
+ //#region src/pipes/serializers/update-custom-provider-definition.serializer.ts
3227
+ const serializeUpdateCustomProviderDefinition = (model) => ({
3228
+ name: model.name,
3229
+ authorization_url: model.authorizationUrl,
3230
+ token_url: model.tokenUrl,
3231
+ refresh_token_url: model.refreshTokenUrl,
3232
+ pkce_enabled: model.pkceEnabled,
3233
+ request_scope_separator: model.requestScopeSeparator,
3234
+ scopes_required: model.scopesRequired,
3235
+ client_secret_required: model.clientSecretRequired,
3236
+ additional_authorization_parameters: model.additionalAuthorizationParameters,
3237
+ token_body_content_type: model.tokenBodyContentType,
3238
+ authenticate_via: model.authenticateVia
3239
+ });
3240
+ //#endregion
3241
+ //#region src/pipes/serializers/update-data-integration.serializer.ts
3242
+ const serializeUpdateDataIntegration = (model) => ({
3243
+ description: model.description,
3244
+ enabled: model.enabled,
3245
+ scopes: model.scopes,
3246
+ credentials: model.credentials != null ? serializeDataIntegrationCredentialsDto(model.credentials) : void 0,
3247
+ custom_provider: model.customProvider != null ? serializeUpdateCustomProviderDefinition(model.customProvider) : void 0
3248
+ });
3249
+ //#endregion
3250
+ //#region src/pipes/serializers/data-integrations-upsert-api-key-request.serializer.ts
3251
+ const serializeDataIntegrationsUpsertApiKeyRequest = (model) => ({
3252
+ user_id: model.userId,
3253
+ organization_id: model.organizationId,
3254
+ secret: model.secret
3255
+ });
3256
+ //#endregion
3257
+ //#region src/pipes/serializers/data-integrations-get-data-integration-authorize-url-request.serializer.ts
3258
+ const serializeDataIntegrationsGetDataIntegrationAuthorizeUrlRequest = (model) => ({
3259
+ user_id: model.userId,
3260
+ organization_id: model.organizationId,
3261
+ return_to: model.returnTo
3262
+ });
3263
+ //#endregion
3264
+ //#region src/pipes/serializers/data-integrations-vend-credentials-request.serializer.ts
3265
+ const serializeDataIntegrationsVendCredentialsRequest = (model) => ({
3266
+ user_id: model.userId,
3267
+ organization_id: model.organizationId
3268
+ });
3269
+ //#endregion
3270
+ //#region src/pipes/serializers/data-integrations-get-user-token-request.serializer.ts
3271
+ const serializeDataIntegrationsGetUserTokenRequest = (model) => ({
3272
+ user_id: model.userId,
3273
+ organization_id: model.organizationId
3274
+ });
3275
+ //#endregion
3276
+ //#region src/pipes/serializers/connected-account-dto.serializer.ts
3277
+ const serializeConnectedAccountDto = (model) => ({
3278
+ access_token: model.accessToken,
3279
+ refresh_token: model.refreshToken,
3280
+ expires_at: model.expiresAt != null ? model.expiresAt.toISOString() : void 0,
3281
+ scopes: model.scopes,
3282
+ state: model.state
3283
+ });
2839
3284
  //#endregion
2840
3285
  //#region src/pipes/pipes.ts
2841
3286
  var Pipes = class {
@@ -2843,9 +3288,311 @@ var Pipes = class {
2843
3288
  constructor(workos) {
2844
3289
  this.workos = workos;
2845
3290
  }
2846
- async getAccessToken({ provider, ...options }) {
2847
- const { data } = await this.workos.post(`data-integrations/${provider}/token`, serializeGetAccessTokenOptions(options));
2848
- return deserializeGetAccessTokenResponse(data);
3291
+ /**
3292
+ * List data integrations
3293
+ *
3294
+ * Lists the environment's data integrations configured with `custom` or `organization` credentials, including custom providers.
3295
+ * @param options - Pagination and filter options.
3296
+ * @returns {Promise<AutoPaginatable<DataIntegration, PaginationOptions>>}
3297
+ * @throws {UnauthorizedException} 401
3298
+ */
3299
+ async listDataIntegrations(options) {
3300
+ const paginationOptions = options;
3301
+ return new AutoPaginatable(await fetchAndDeserialize(this.workos, "/data-integrations", deserializeDataIntegration, paginationOptions), (params) => fetchAndDeserialize(this.workos, "/data-integrations", deserializeDataIntegration, params), paginationOptions);
3302
+ }
3303
+ /**
3304
+ * Create a data integration
3305
+ *
3306
+ * Creates a data integration for a provider. Set `credentials.type` to `custom` to use your own OAuth app credentials, or `organization` to have each organization supply its own. For a built-in provider, pass its slug as `provider`. For a custom provider, pass a new slug plus a `custom_provider` definition.
3307
+ * @param options - Object containing provider.
3308
+ * @param options.provider - The provider to create a Data Integration for. For a built-in provider use its slug (e.g. `github`, `slack`). For a custom provider, this is the new provider slug and `custom_provider` must be supplied. A custom provider slug cannot shadow an existing global provider slug.
3309
+ * @example "github"
3310
+ * @param options.description - An optional description of the Data Integration.
3311
+ * @example "Production GitHub app"
3312
+ * @param options.enabled - Whether the Data Integration is enabled. Defaults to `false`.
3313
+ * @example true
3314
+ * @param options.scopes - The OAuth scopes to request for the Data Integration. Defaults to the provider's configured scopes when omitted.
3315
+ * @example ["repo","read:org"]
3316
+ * @param options.credentials - The credentials to configure for the Data Integration. Required for both built-in and custom providers.
3317
+ * @param options.customProvider - The OAuth definition for a custom provider. Supply this to define a custom provider; omit it to create an integration for a built-in provider.
3318
+ * @returns {Promise<DataIntegration>}
3319
+ * @throws {BadRequestException} 400
3320
+ * @throws {UnauthorizedException} 401
3321
+ * @throws {NotFoundException} 404
3322
+ * @throws {UnprocessableEntityException} 422
3323
+ */
3324
+ async createDataIntegration(options) {
3325
+ const payload = options;
3326
+ const { data } = await this.workos.post("/data-integrations", serializeCreateDataIntegration(payload));
3327
+ return deserializeDataIntegration(data);
3328
+ }
3329
+ /**
3330
+ * Get a data integration
3331
+ *
3332
+ * Retrieves a data integration by its slug.
3333
+ * @param options - The request options.
3334
+ * @param options.slug - The slug identifier of the data integration.
3335
+ * @example "github"
3336
+ * @returns {Promise<DataIntegration>}
3337
+ * @throws {UnauthorizedException} 401
3338
+ * @throws {NotFoundException} 404
3339
+ */
3340
+ async getDataIntegration(options) {
3341
+ const { slug } = options;
3342
+ const { data } = await this.workos.get(`/data-integrations/${encodeURIComponent(slug)}`);
3343
+ return deserializeDataIntegration(data);
3344
+ }
3345
+ /**
3346
+ * Update a data integration
3347
+ *
3348
+ * Updates the description, enabled state, or custom credentials of a data integration. For custom providers, `custom_provider` updates the OAuth definition.
3349
+ * @param options - The request body.
3350
+ * @param options.slug - The slug identifier of the data integration.
3351
+ * @example "github"
3352
+ * @param options.description - An optional description of the Data Integration.
3353
+ * @example "Production GitHub app"
3354
+ * @param options.enabled - Whether the Data Integration is enabled.
3355
+ * @example true
3356
+ * @param options.scopes - The OAuth scopes to request for the Data Integration. Pass `null` to reset to the provider's configured scopes.
3357
+ * @example ["repo","read:org"]
3358
+ * @param options.credentials - New credentials for the Data Integration. When provided, rotates the stored client secret.
3359
+ * @param options.customProvider - Updates to a custom provider's OAuth definition. Only valid for custom-provider integrations.
3360
+ * @returns {Promise<DataIntegration>}
3361
+ * @throws {BadRequestException} 400
3362
+ * @throws {UnauthorizedException} 401
3363
+ * @throws {NotFoundException} 404
3364
+ * @throws {UnprocessableEntityException} 422
3365
+ */
3366
+ async updateDataIntegration(options) {
3367
+ const { slug, ...payload } = options;
3368
+ const { data } = await this.workos.put(`/data-integrations/${encodeURIComponent(slug)}`, serializeUpdateDataIntegration(payload));
3369
+ return deserializeDataIntegration(data);
3370
+ }
3371
+ /**
3372
+ * Delete a data integration
3373
+ *
3374
+ * Deletes a data integration and all of its connected installations. For a custom provider, also deletes the custom provider definition.
3375
+ * @param options - The request options.
3376
+ * @param options.slug - The slug identifier of the data integration.
3377
+ * @example "github"
3378
+ * @returns {Promise<void>}
3379
+ * @throws {UnauthorizedException} 401
3380
+ * @throws {NotFoundException} 404
3381
+ */
3382
+ async deleteDataIntegration(options) {
3383
+ const { slug } = options;
3384
+ await this.workos.delete(`/data-integrations/${encodeURIComponent(slug)}`);
3385
+ }
3386
+ /**
3387
+ * Upsert an API key for a connected account
3388
+ *
3389
+ * Creates or updates an API-key-based installation for the specified integration and user. If an installation already exists, the stored API key is rotated to the new value.
3390
+ * @param options - Object containing userId, secret.
3391
+ * @param options.slug - The identifier of the integration.
3392
+ * @example "github"
3393
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier.
3394
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3395
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter to scope the connection to a specific organization.
3396
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3397
+ * @param options.secret - The API key secret to store for this integration.
3398
+ * @example "sk-1234567890abcdef"
3399
+ * @returns {Promise<ConnectedAccount>}
3400
+ * @throws {BadRequestException} 400
3401
+ * @throws {UnauthorizedException} 401
3402
+ * @throws {AuthorizationException} 403
3403
+ * @throws {NotFoundException} 404
3404
+ * @throws {UnprocessableEntityException} 422
3405
+ */
3406
+ async updateDataIntegrationApiKey(options) {
3407
+ const { slug, ...payload } = options;
3408
+ const { data } = await this.workos.put(`/data-integrations/${encodeURIComponent(slug)}/api-key`, serializeDataIntegrationsUpsertApiKeyRequest(payload));
3409
+ return deserializeConnectedAccount(data);
3410
+ }
3411
+ /**
3412
+ * Get authorization URL
3413
+ *
3414
+ * Generates an OAuth authorization URL to initiate the connection flow for a user. Redirect the user to the returned URL to begin the OAuth flow with the third-party provider.
3415
+ * @param options - Object containing userId.
3416
+ * @param options.slug - The slug identifier of the provider (e.g., `github`, `slack`, `notion`).
3417
+ * @example "github"
3418
+ * @param options.userId - The ID of the user to authorize.
3419
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3420
+ * @param options.organizationId - An organization ID to scope the authorization to a specific organization.
3421
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3422
+ * @param options.returnTo - The URL to redirect the user to after authorization.
3423
+ * @example "https://example.com/callback"
3424
+ * @returns {Promise<DataIntegrationAuthorizeUrlResponse>}
3425
+ * @throws {BadRequestException} 400
3426
+ * @throws {UnauthorizedException} 401
3427
+ * @throws {AuthorizationException} 403
3428
+ * @throws {NotFoundException} 404
3429
+ */
3430
+ async authorizeDataIntegration(options) {
3431
+ const { slug, ...payload } = options;
3432
+ const { data } = await this.workos.post(`/data-integrations/${encodeURIComponent(slug)}/authorize`, serializeDataIntegrationsGetDataIntegrationAuthorizeUrlRequest(payload));
3433
+ return deserializeDataIntegrationAuthorizeUrlResponse(data);
3434
+ }
3435
+ /**
3436
+ * Vend credentials for a connected account
3437
+ *
3438
+ * Returns credentials for a user's connected account. Branches on the installation's `auth_method`: OAuth installations return an access token (refreshed if needed); API-key installations return the stored secret.
3439
+ * @param options - Object containing userId.
3440
+ * @param options.slug - The identifier of the integration.
3441
+ * @example "github"
3442
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier.
3443
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3444
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter to scope the connection to a specific organization.
3445
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3446
+ * @returns {Promise<DataIntegrationCredentialsResponse>}
3447
+ * @throws {BadRequestException} 400
3448
+ * @throws {UnauthorizedException} 401
3449
+ * @throws {NotFoundException} 404
3450
+ */
3451
+ async createDataIntegrationCredential(options) {
3452
+ const { slug, ...payload } = options;
3453
+ const { data } = await this.workos.post(`/data-integrations/${encodeURIComponent(slug)}/credentials`, serializeDataIntegrationsVendCredentialsRequest(payload));
3454
+ return deserializeDataIntegrationCredentialsResponse(data);
3455
+ }
3456
+ /**
3457
+ * Get an access token for a connected account
3458
+ *
3459
+ * Fetches a valid OAuth access token for a user's connected account. WorkOS automatically handles token refresh, ensuring you always receive a valid, non-expired token.
3460
+ * @param options - Object containing userId.
3461
+ * @param options.provider - The identifier of the integration.
3462
+ * @example "github"
3463
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier.
3464
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3465
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter to scope the connection to a specific organization.
3466
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3467
+ * @returns {Promise<DataIntegrationAccessTokenResponse>}
3468
+ * @throws {BadRequestException} 400
3469
+ * @throws {UnauthorizedException} 401
3470
+ * @throws {NotFoundException} 404
3471
+ * @throws {UnprocessableEntityException} 422
3472
+ */
3473
+ async getAccessToken(options) {
3474
+ const { provider, ...payload } = options;
3475
+ const { data } = await this.workos.post(`/data-integrations/${encodeURIComponent(provider)}/token`, serializeDataIntegrationsGetUserTokenRequest(payload));
3476
+ return deserializeDataIntegrationAccessTokenResponse(data);
3477
+ }
3478
+ /**
3479
+ * Get a connected account
3480
+ *
3481
+ * Retrieves a user's [connected account](https://workos.com/docs/reference/pipes/connected-account) for a specific provider.
3482
+ * @param options - Additional query options.
3483
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier.
3484
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3485
+ * @param options.slug - The slug identifier of the provider (e.g., `github`, `slack`, `notion`).
3486
+ * @example "github"
3487
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter if the connection is scoped to an organization.
3488
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3489
+ * @returns {Promise<ConnectedAccount>}
3490
+ * @throws {UnauthorizedException} 401
3491
+ * @throws {NotFoundException} 404
3492
+ */
3493
+ async getUserConnectedAccount(options) {
3494
+ const { userId, slug } = options;
3495
+ const { data } = await this.workos.get(`/user_management/users/${encodeURIComponent(userId)}/connected_accounts/${encodeURIComponent(slug)}`, { query: { ...options.organizationId !== void 0 && { organization_id: options.organizationId } } });
3496
+ return deserializeConnectedAccount(data);
3497
+ }
3498
+ /**
3499
+ * Import a connected account
3500
+ *
3501
+ * Imports a [connected account](https://workos.com/docs/reference/pipes/connected-account) for a user by providing OAuth tokens directly. Use this to migrate existing connections or set up connections without going through the OAuth flow.
3502
+ * @param options - The request body.
3503
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier.
3504
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3505
+ * @param options.slug - The slug identifier of the provider (e.g., `github`, `slack`, `notion`).
3506
+ * @example "github"
3507
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter if the connection is scoped to an organization.
3508
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3509
+ * @param options.accessToken - The OAuth access token for the connected account.
3510
+ * @example "gho_16C7e42F292c6912E7710c838347Ae178B4a"
3511
+ * @param options.refreshToken - The OAuth refresh token for the connected account.
3512
+ * @example "ghr_xxxxxxxxxxxxxxxxxxxx"
3513
+ * @param options.expiresAt - The ISO-8601 timestamp when the access token expires. Required when `access_token` is provided for tokens that expire.
3514
+ * @example "2025-12-31T23:59:59.000Z"
3515
+ * @param options.scopes - The OAuth scopes granted for this connection.
3516
+ * @example ["repo","user:email"]
3517
+ * @param options.state - Explicitly set the state of the connected account. When omitted, the state is derived from the token combination provided.
3518
+ * @example "connected"
3519
+ * @returns {Promise<ConnectedAccount>}
3520
+ * @throws {UnauthorizedException} 401
3521
+ * @throws {NotFoundException} 404
3522
+ * @throws {ConflictException} 409
3523
+ * @throws {UnprocessableEntityException} 422
3524
+ */
3525
+ async createUserConnectedAccount(options) {
3526
+ const { userId, slug, organizationId, ...payload } = options;
3527
+ const { data } = await this.workos.post(`/user_management/users/${encodeURIComponent(userId)}/connected_accounts/${encodeURIComponent(slug)}`, serializeConnectedAccountDto(payload), { query: { ...options.organizationId !== void 0 && { organization_id: options.organizationId } } });
3528
+ return deserializeConnectedAccount(data);
3529
+ }
3530
+ /**
3531
+ * Update a connected account
3532
+ *
3533
+ * Updates a user's [connected account](https://workos.com/docs/reference/pipes/connected-account) tokens, scopes, or state for a specific provider.
3534
+ * @param options - The request body.
3535
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier.
3536
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3537
+ * @param options.slug - The slug identifier of the provider (e.g., `github`, `slack`, `notion`).
3538
+ * @example "github"
3539
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter if the connection is scoped to an organization.
3540
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3541
+ * @param options.accessToken - The OAuth access token for the connected account.
3542
+ * @example "gho_16C7e42F292c6912E7710c838347Ae178B4a"
3543
+ * @param options.refreshToken - The OAuth refresh token for the connected account.
3544
+ * @example "ghr_xxxxxxxxxxxxxxxxxxxx"
3545
+ * @param options.expiresAt - The ISO-8601 timestamp when the access token expires. Required when `access_token` is provided for tokens that expire.
3546
+ * @example "2025-12-31T23:59:59.000Z"
3547
+ * @param options.scopes - The OAuth scopes granted for this connection.
3548
+ * @example ["repo","user:email"]
3549
+ * @param options.state - Explicitly set the state of the connected account. When omitted, the state is derived from the token combination provided.
3550
+ * @example "connected"
3551
+ * @returns {Promise<ConnectedAccount>}
3552
+ * @throws {UnauthorizedException} 401
3553
+ * @throws {NotFoundException} 404
3554
+ */
3555
+ async updateUserConnectedAccount(options) {
3556
+ const { userId, slug, organizationId, ...payload } = options;
3557
+ const { data } = await this.workos.put(`/user_management/users/${encodeURIComponent(userId)}/connected_accounts/${encodeURIComponent(slug)}`, serializeConnectedAccountDto(payload), { query: { ...options.organizationId !== void 0 && { organization_id: options.organizationId } } });
3558
+ return deserializeConnectedAccount(data);
3559
+ }
3560
+ /**
3561
+ * Delete a connected account
3562
+ *
3563
+ * Disconnects WorkOS's account for the user, including removing any stored access and refresh tokens. The user will need to reauthorize if they want to reconnect. This does not revoke access on the provider side.
3564
+ * @param options - Additional query options.
3565
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier.
3566
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3567
+ * @param options.slug - The slug identifier of the provider (e.g., `github`, `slack`, `notion`).
3568
+ * @example "github"
3569
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter if the connection is scoped to an organization.
3570
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3571
+ * @returns {Promise<void>}
3572
+ * @throws {UnauthorizedException} 401
3573
+ * @throws {NotFoundException} 404
3574
+ */
3575
+ async deleteUserConnectedAccount(options) {
3576
+ const { userId, slug } = options;
3577
+ await this.workos.delete(`/user_management/users/${encodeURIComponent(userId)}/connected_accounts/${encodeURIComponent(slug)}`, { query: { ...options.organizationId !== void 0 && { organization_id: options.organizationId } } });
3578
+ }
3579
+ /**
3580
+ * List providers for a user
3581
+ *
3582
+ * Retrieves a list of available providers and the user's connection status for each. Returns all providers configured for your environment, along with the user's [connected account](https://workos.com/docs/reference/pipes/connected-account) information where applicable.
3583
+ * @param options - Additional query options.
3584
+ * @param options.userId - A [User](https://workos.com/docs/reference/authkit/user) identifier to list providers and connected accounts for.
3585
+ * @example "user_01EHZNVPK3SFK441A1RGBFSHRT"
3586
+ * @param options.organizationId - An [Organization](https://workos.com/docs/reference/organization) identifier. Optional parameter to filter connections for a specific organization.
3587
+ * @example "org_01EHZNVPK3SFK441A1RGBFSHRT"
3588
+ * @returns {Promise<DataIntegrationsListResponse>}
3589
+ * @throws {UnauthorizedException} 401
3590
+ * @throws {NotFoundException} 404
3591
+ */
3592
+ async listUserDataProviders(options) {
3593
+ const { userId } = options;
3594
+ const { data } = await this.workos.get(`/user_management/users/${encodeURIComponent(userId)}/data_providers`, { query: { ...options.organizationId !== void 0 && { organization_id: options.organizationId } } });
3595
+ return deserializeDataIntegrationsListResponse(data);
2849
3596
  }
2850
3597
  };
2851
3598
  //#endregion
@@ -3606,7 +4353,9 @@ function isJson(val) {
3606
4353
  }
3607
4354
  return !0;
3608
4355
  }
3609
- const enc = /* @__PURE__ */ new TextEncoder(), dec = /* @__PURE__ */ new TextDecoder(), jsBase64Enabled = /* @__PURE__ */ (() => typeof Uint8Array.fromBase64 == "function" && typeof Uint8Array.prototype.toBase64 == "function" && typeof Uint8Array.prototype.toHex == "function")();
4356
+ const enc = /* @__PURE__ */ new TextEncoder();
4357
+ const dec = /* @__PURE__ */ new TextDecoder();
4358
+ const jsBase64Enabled = /* @__PURE__ */ (() => typeof Uint8Array.fromBase64 == "function" && typeof Uint8Array.prototype.toBase64 == "function" && typeof Uint8Array.prototype.toHex == "function")();
3610
4359
  function b64ToU8(str) {
3611
4360
  return jsBase64Enabled ? Uint8Array.fromBase64(str, { alphabet: "base64url" }) : base64ToUint8Array$1(str);
3612
4361
  }
@@ -3635,7 +4384,8 @@ const defaults = /* @__PURE__ */ Object.freeze({
3635
4384
  ttl: 0,
3636
4385
  timestampSkewSec: 60,
3637
4386
  localtimeOffsetMsec: 0
3638
- }), algorithms = /* @__PURE__ */ Object.freeze({
4387
+ });
4388
+ const algorithms = /* @__PURE__ */ Object.freeze({
3639
4389
  "aes-128-ctr": /* @__PURE__ */ Object.freeze({
3640
4390
  keyBits: 128,
3641
4391
  ivBits: 128,
@@ -3978,24 +4728,6 @@ const serializeUpdateOrganizationMembershipOptions = (options) => ({
3978
4728
  role_slugs: options.roleSlugs
3979
4729
  });
3980
4730
  //#endregion
3981
- //#region src/utils/jose.ts
3982
- let _josePromise;
3983
- /**
3984
- * Dynamically imports the jose library using import() to support Node.js 20.0-20.18.
3985
- *
3986
- * The jose library is ESM-only and cannot be loaded via require() in Node.js versions
3987
- * before 20.19.0. This wrapper uses dynamic import() which works in both ESM and CJS
3988
- * across all Node.js 20+ versions.
3989
- *
3990
- * This workaround can be removed when Node.js 20 reaches end-of-life (April 2026),
3991
- * at which point we can bump to Node.js 22+ and use direct imports.
3992
- *
3993
- * @returns Promise that resolves to the jose module
3994
- */
3995
- function getJose() {
3996
- return _josePromise ??= import("./webapi-S8D5YgJz.mjs");
3997
- }
3998
- //#endregion
3999
4731
  //#region src/user-management/session.ts
4000
4732
  var CookieSession = class {
4001
4733
  userManagement;
@@ -5222,7 +5954,7 @@ var FeatureFlagsRuntimeClient = class extends EventEmitter {
5222
5954
  }
5223
5955
  emitChanges(previous, current) {
5224
5956
  if (!previous || !current) return;
5225
- const allKeys = new Set([...Object.keys(previous), ...Object.keys(current)]);
5957
+ const allKeys = /* @__PURE__ */ new Set([...Object.keys(previous), ...Object.keys(current)]);
5226
5958
  for (const key of allKeys) {
5227
5959
  const prev = previous[key];
5228
5960
  const curr = current[key];
@@ -7154,7 +7886,7 @@ var Vault = class {
7154
7886
  };
7155
7887
  //#endregion
7156
7888
  //#region package.json
7157
- var version = "10.7.0";
7889
+ var version = "10.8.0";
7158
7890
  //#endregion
7159
7891
  //#region src/workos.ts
7160
7892
  const DEFAULT_HOSTNAME = "api.workos.com";
@@ -7171,6 +7903,7 @@ var WorkOS = class {
7171
7903
  pkce;
7172
7904
  hasApiKey;
7173
7905
  actions;
7906
+ agents = new Agents(this);
7174
7907
  apiKeys = new ApiKeys(this);
7175
7908
  auditLogs = new AuditLogs(this);
7176
7909
  authorization = new Authorization(this);
@@ -7255,6 +7988,7 @@ var WorkOS = class {
7255
7988
  return new FetchHttpClient(this.baseURL, {
7256
7989
  ...options.config,
7257
7990
  timeout: options.timeout,
7991
+ maxRetries: options.maxRetries,
7258
7992
  headers
7259
7993
  });
7260
7994
  }
@@ -7278,7 +8012,8 @@ var WorkOS = class {
7278
8012
  try {
7279
8013
  res = await this.client.post(path, entity, {
7280
8014
  params: options.query,
7281
- headers: requestHeaders
8015
+ headers: requestHeaders,
8016
+ maxRetries: options.maxRetries
7282
8017
  });
7283
8018
  } catch (error) {
7284
8019
  this.handleHttpError({
@@ -7298,7 +8033,8 @@ var WorkOS = class {
7298
8033
  try {
7299
8034
  res = await this.client.get(path, {
7300
8035
  params: options.query,
7301
- headers: requestHeaders
8036
+ headers: requestHeaders,
8037
+ maxRetries: options.maxRetries
7302
8038
  });
7303
8039
  } catch (error) {
7304
8040
  this.handleHttpError({
@@ -7317,7 +8053,8 @@ var WorkOS = class {
7317
8053
  try {
7318
8054
  res = await this.client.put(path, entity, {
7319
8055
  params: options.query,
7320
- headers: requestHeaders
8056
+ headers: requestHeaders,
8057
+ maxRetries: options.maxRetries
7321
8058
  });
7322
8059
  } catch (error) {
7323
8060
  this.handleHttpError({
@@ -7336,7 +8073,8 @@ var WorkOS = class {
7336
8073
  try {
7337
8074
  res = await this.client.patch(path, entity, {
7338
8075
  params: options.query,
7339
- headers: requestHeaders
8076
+ headers: requestHeaders,
8077
+ maxRetries: options.maxRetries
7340
8078
  });
7341
8079
  } catch (error) {
7342
8080
  this.handleHttpError({
@@ -7500,4 +8238,4 @@ function createWorkOS(options) {
7500
8238
  //#endregion
7501
8239
  export { FetchHttpClient as A, NoApiKeyProvidedException as C, isAuthenticationErrorData as D, AuthenticationException as E, GenericServerException as O, NotFoundException as S, BadRequestException as T, UnprocessableEntityException as _, DomainDataState as a, RateLimitExceededException as b, FeatureFlagsRuntimeClient as c, serializeRevokeSessionOptions as d, AuthenticateWithSessionCookieFailureReason as f, Actions as g, AutoPaginatable as h, OrganizationDomainVerificationStrategy as i, SubtleCryptoProvider as j, ApiKeyRequiredException as k, CookieSession as l, Webhooks as m, ConnectionType as n, GenerateLinkIntent as o, PKCE as p, OrganizationDomainState as r, WorkOS as s, createWorkOS as t, RefreshSessionFailureReason as u, UnauthorizedException as v, ConflictException as w, OauthException as x, SignatureVerificationException as y };
7502
8240
 
7503
- //# sourceMappingURL=factory-BjWO1KkE.mjs.map
8241
+ //# sourceMappingURL=factory-MKPb5Egh.mjs.map