@vuevox/sdk 0.6.0 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -32,6 +32,8 @@ spaces:read
32
32
  agents:read
33
33
  calls:read
34
34
  leads:read
35
+ leads:write
36
+ lead_custom_fields:manage
35
37
  ```
36
38
 
37
39
  The token request can only request scopes that were granted to that API client.
@@ -105,7 +107,12 @@ vuevox.calls.get("call-id");
105
107
  vuevox.calls.paginate();
106
108
  vuevox.leads.list();
107
109
  vuevox.leads.get("lead-id");
110
+ vuevox.leads.update("lead-id", { customFields: { crm_stage: "qualified" } });
111
+ vuevox.leads.upsertByExternalId("crm-lead-id", { firstName: "Ada", lastName: "Lovelace" });
108
112
  vuevox.leads.paginate();
113
+ vuevox.leadCustomFields.list();
114
+ vuevox.leadCustomFields.create({ key: "crm_stage", label: "CRM Stage", type: "select", options: ["new", "qualified"] });
115
+ vuevox.leadCustomFields.update("crm_stage", { label: "CRM Stage" });
109
116
  vuevox.raw.GET("/v1/hello", { headers: { Authorization: `Bearer ${await vuevox.getAccessToken()}` } });
110
117
  ```
111
118
 
@@ -273,12 +280,16 @@ Options: `ListCallsOptions`
273
280
  | `agentId` | `string` | Optional agent ID filter. |
274
281
  | `createdAfter` | `string` | Optional ISO 8601 lower bound for call creation time. |
275
282
  | `createdBefore` | `string` | Optional ISO 8601 upper bound for call creation time. |
283
+ | `leadCustomFields` | `Record<string, CustomFieldFilterValue>` | Optional filters on lead custom fields attached to calls. |
276
284
 
277
285
  ```ts
278
286
  const response = await vuevox.calls.list({
279
287
  limit: 50,
280
288
  spaceId: "space-id",
281
289
  createdAfter: "2026-01-01T00:00:00.000Z",
290
+ leadCustomFields: {
291
+ crm_stage: "qualified",
292
+ },
282
293
  });
283
294
 
284
295
  for (const call of response.data.data) {
@@ -321,7 +332,7 @@ Returns: `AsyncGenerator<CallSummary>`.
321
332
 
322
333
  Lists organization leads. The `leads:read` scope includes lead email and phone contact details.
323
334
 
324
- Lead records include nullable `externalId` when you store an ID from another system.
335
+ Lead records include nullable `externalId` when you store an ID from another system, and a `customFields` object for organization-defined CRM fields.
325
336
 
326
337
  Required scope: `leads:read`.
327
338
 
@@ -334,12 +345,20 @@ Options: `ListLeadsOptions`
334
345
  | `spaceId` | `string` | Optional space ID filter. |
335
346
  | `createdAfter` | `string` | Optional ISO 8601 lower bound for lead creation time. |
336
347
  | `createdBefore` | `string` | Optional ISO 8601 upper bound for lead creation time. |
348
+ | `customFields` | `Record<string, CustomFieldFilterValue>` | Optional filters on lead custom fields. |
337
349
 
338
350
  ```ts
339
- const response = await vuevox.leads.list({ limit: 50, spaceId: "space-id" });
351
+ const response = await vuevox.leads.list({
352
+ limit: 50,
353
+ spaceId: "space-id",
354
+ customFields: {
355
+ crm_stage: "qualified",
356
+ deal_value: { gte: 10000 },
357
+ },
358
+ });
340
359
 
341
360
  for (const lead of response.data.data) {
342
- console.log(lead.id, lead.externalId, lead.email, lead.phone);
361
+ console.log(lead.id, lead.externalId, lead.email, lead.phone, lead.customFields);
343
362
  }
344
363
  ```
345
364
 
@@ -353,7 +372,53 @@ Required scope: `leads:read`.
353
372
 
354
373
  ```ts
355
374
  const response = await vuevox.leads.get("lead-id");
356
- console.log(response.data.externalId, response.data.email, response.data.phone);
375
+ console.log(response.data.data.externalId, response.data.data.email, response.data.data.phone, response.data.data.customFields);
376
+ ```
377
+
378
+ Returns: `Promise<VueVoxApiResponse<LeadDetailResponse>>`.
379
+
380
+ ### `vuevox.leads.update(leadId, input)`
381
+
382
+ Updates a lead and/or its custom fields.
383
+
384
+ Required scope: `leads:write`.
385
+
386
+ Input: `LeadUpdateRequest`
387
+
388
+ ```ts
389
+ const response = await vuevox.leads.update("lead-id", {
390
+ email: "ada@example.com",
391
+ customFields: {
392
+ crm_stage: "qualified",
393
+ renewal_date: "2026-09-01",
394
+ },
395
+ });
396
+
397
+ console.log(response.data.data.customFields);
398
+ ```
399
+
400
+ Returns: `Promise<VueVoxApiResponse<LeadDetailResponse>>`.
401
+
402
+ ### `vuevox.leads.upsertByExternalId(externalId, input)`
403
+
404
+ Creates or updates a lead by the integrating CRM/system ID. This is the preferred write method for CRM integrations because callers can use their own stable lead ID.
405
+
406
+ Required scope: `leads:write`.
407
+
408
+ Input: `LeadUpsertRequest`
409
+
410
+ ```ts
411
+ const response = await vuevox.leads.upsertByExternalId("hubspot_123", {
412
+ firstName: "Ada",
413
+ lastName: "Lovelace",
414
+ email: "ada@example.com",
415
+ customFields: {
416
+ crm_stage: "qualified",
417
+ deal_value: 12000,
418
+ },
419
+ });
420
+
421
+ console.log(response.data.data.id, response.data.data.customFields);
357
422
  ```
358
423
 
359
424
  Returns: `Promise<VueVoxApiResponse<LeadDetailResponse>>`.
@@ -374,6 +439,64 @@ for await (const lead of vuevox.leads.paginate({ createdAfter: "2026-01-01T00:00
374
439
 
375
440
  Returns: `AsyncGenerator<Lead>`.
376
441
 
442
+ ### `vuevox.leadCustomFields.list(options?)`
443
+
444
+ Lists organization lead custom field definitions.
445
+
446
+ Required scope: `leads:read`.
447
+
448
+ Options: `ListLeadCustomFieldsOptions`
449
+
450
+ | Option | Type | Description |
451
+ | --- | --- | --- |
452
+ | `includeArchived` | `boolean` | Include archived definitions. Defaults to `false`. |
453
+
454
+ ```ts
455
+ const response = await vuevox.leadCustomFields.list();
456
+ console.log(response.data.data);
457
+ ```
458
+
459
+ Returns: `Promise<VueVoxApiResponse<LeadCustomFieldsListResponse>>`.
460
+
461
+ ### `vuevox.leadCustomFields.create(input)`
462
+
463
+ Creates a lead custom field definition. Supported types are `text`, `number`, `boolean`, `date`, `datetime`, `select`, and `multi_select`.
464
+
465
+ Required scope: `lead_custom_fields:manage`.
466
+
467
+ Input: `LeadCustomFieldCreateRequest`
468
+
469
+ ```ts
470
+ const response = await vuevox.leadCustomFields.create({
471
+ key: "crm_stage",
472
+ label: "CRM Stage",
473
+ type: "select",
474
+ options: ["new", "qualified", "customer"],
475
+ isFilterable: true,
476
+ });
477
+
478
+ console.log(response.data.data.key);
479
+ ```
480
+
481
+ Returns: `Promise<VueVoxApiResponse<LeadCustomFieldResponse>>`.
482
+
483
+ ### `vuevox.leadCustomFields.update(key, input)`
484
+
485
+ Updates mutable metadata for a lead custom field definition. Field keys and types are immutable.
486
+
487
+ Required scope: `lead_custom_fields:manage`.
488
+
489
+ Input: `LeadCustomFieldUpdateRequest`
490
+
491
+ ```ts
492
+ await vuevox.leadCustomFields.update("crm_stage", {
493
+ label: "CRM Pipeline Stage",
494
+ archived: false,
495
+ });
496
+ ```
497
+
498
+ Returns: `Promise<VueVoxApiResponse<LeadCustomFieldResponse>>`.
499
+
377
500
  ## Lower-Level Calls
378
501
 
379
502
  For advanced integrations, `raw` exposes a typed lower-level OpenAPI client. You must attach authorization yourself.
@@ -429,6 +552,8 @@ rate_limited
429
552
  invalid_request
430
553
  call_not_found
431
554
  lead_not_found
555
+ custom_field_not_found
556
+ custom_field_conflict
432
557
  ```
433
558
 
434
559
  ## Retries
@@ -485,12 +610,22 @@ import type {
485
610
  CallDetailResponse,
486
611
  CallsListResponse,
487
612
  CallSummary,
613
+ CustomFieldFilters,
614
+ CustomFieldFilterValue,
488
615
  HelloResponse,
489
616
  Lead,
617
+ LeadCustomField,
618
+ LeadCustomFieldCreateRequest,
619
+ LeadCustomFieldResponse,
620
+ LeadCustomFieldUpdateRequest,
621
+ LeadCustomFieldsListResponse,
490
622
  LeadDetailResponse,
623
+ LeadUpdateRequest,
624
+ LeadUpsertRequest,
491
625
  LeadsListResponse,
492
626
  ListAgentsOptions,
493
627
  ListCallsOptions,
628
+ ListLeadCustomFieldsOptions,
494
629
  ListLeadsOptions,
495
630
  ListSpacesOptions,
496
631
  Space,
package/dist/client.d.ts CHANGED
@@ -1,15 +1,33 @@
1
1
  import type { components, paths } from "./generated/schema.js";
2
- type HelloResponse = components["schemas"]["HelloResponse"];
3
- type SpacesListResponse = components["schemas"]["SpacesListResponse"];
4
- type AgentsListResponse = components["schemas"]["AgentsListResponse"];
5
- type CallsListResponse = components["schemas"]["CallsListResponse"];
6
- type CallDetailResponse = components["schemas"]["CallDetailResponse"];
7
- type LeadsListResponse = components["schemas"]["LeadsListResponse"];
8
- type LeadDetailResponse = components["schemas"]["LeadDetailResponse"];
9
- type Space = components["schemas"]["Space"];
10
- type Agent = components["schemas"]["Agent"];
11
- type CallSummary = components["schemas"]["CallSummary"];
12
- type Lead = components["schemas"]["Lead"];
2
+ export type HelloResponse = components["schemas"]["HelloResponse"];
3
+ export type SpacesListResponse = components["schemas"]["SpacesListResponse"];
4
+ export type AgentsListResponse = components["schemas"]["AgentsListResponse"];
5
+ export type CallsListResponse = components["schemas"]["CallsListResponse"];
6
+ export type CallDetailResponse = components["schemas"]["CallDetailResponse"];
7
+ export type LeadsListResponse = components["schemas"]["LeadsListResponse"];
8
+ export type LeadDetailResponse = components["schemas"]["LeadDetailResponse"];
9
+ export type LeadCustomFieldsListResponse = components["schemas"]["LeadCustomFieldsListResponse"];
10
+ export type LeadCustomFieldResponse = components["schemas"]["LeadCustomFieldResponse"];
11
+ export type LeadCustomFieldCreateRequest = components["schemas"]["LeadCustomFieldCreateRequest"];
12
+ export type LeadCustomFieldUpdateRequest = components["schemas"]["LeadCustomFieldUpdateRequest"];
13
+ export type LeadUpsertRequest = components["schemas"]["LeadUpsertRequest"];
14
+ export type LeadUpdateRequest = components["schemas"]["LeadUpdateRequest"];
15
+ export type Space = components["schemas"]["Space"];
16
+ export type Agent = components["schemas"]["Agent"];
17
+ export type CallSummary = components["schemas"]["CallSummary"];
18
+ export type Lead = components["schemas"]["Lead"];
19
+ export type LeadCustomField = components["schemas"]["LeadCustomField"];
20
+ export type CustomFieldFilterValue = string | number | boolean | {
21
+ eq?: string | number | boolean;
22
+ gt?: string | number;
23
+ gte?: string | number;
24
+ lt?: string | number;
25
+ lte?: string | number;
26
+ before?: string;
27
+ after?: string;
28
+ contains?: string;
29
+ };
30
+ export type CustomFieldFilters = Record<string, CustomFieldFilterValue>;
13
31
  export interface ListSpacesOptions {
14
32
  limit?: number;
15
33
  cursor?: string;
@@ -20,6 +38,7 @@ export interface ListCallsOptions extends ListSpacesOptions {
20
38
  agentId?: string;
21
39
  createdAfter?: string;
22
40
  createdBefore?: string;
41
+ leadCustomFields?: CustomFieldFilters;
23
42
  }
24
43
  export interface ListAgentsOptions extends ListSpacesOptions {
25
44
  spaceId?: string;
@@ -28,6 +47,10 @@ export interface ListLeadsOptions extends ListSpacesOptions {
28
47
  spaceId?: string;
29
48
  createdAfter?: string;
30
49
  createdBefore?: string;
50
+ customFields?: CustomFieldFilters;
51
+ }
52
+ export interface ListLeadCustomFieldsOptions {
53
+ includeArchived?: boolean;
31
54
  }
32
55
  export interface VueVoxResponseMetadata {
33
56
  requestId?: string;
@@ -98,6 +121,8 @@ export declare function createVueVoxClient(options: VueVoxClientOptions): {
98
121
  leads: {
99
122
  list: (listOptions?: ListLeadsOptions) => Promise<VueVoxApiResponse<LeadsListResponse>>;
100
123
  get: (leadId: string) => Promise<VueVoxApiResponse<LeadDetailResponse>>;
124
+ update: (leadId: string, input: LeadUpdateRequest) => Promise<VueVoxApiResponse<LeadDetailResponse>>;
125
+ upsertByExternalId: (externalId: string, input: LeadUpsertRequest) => Promise<VueVoxApiResponse<LeadDetailResponse>>;
101
126
  paginate: (listOptions?: ListLeadsOptions) => AsyncGenerator<{
102
127
  id: string;
103
128
  externalId: string | null;
@@ -105,11 +130,16 @@ export declare function createVueVoxClient(options: VueVoxClientOptions): {
105
130
  lastName: string;
106
131
  email: string | null;
107
132
  phone: string | null;
133
+ customFields: components["schemas"]["CustomFields"];
108
134
  space: components["schemas"]["ResourceSummary"];
109
135
  createdAt: string;
110
136
  updatedAt: string;
111
137
  }, any, any>;
112
138
  };
139
+ leadCustomFields: {
140
+ list: (listOptions?: ListLeadCustomFieldsOptions) => Promise<VueVoxApiResponse<LeadCustomFieldsListResponse>>;
141
+ create: (input: LeadCustomFieldCreateRequest) => Promise<VueVoxApiResponse<LeadCustomFieldResponse>>;
142
+ update: (key: string, input: LeadCustomFieldUpdateRequest) => Promise<VueVoxApiResponse<LeadCustomFieldResponse>>;
143
+ };
113
144
  raw: import("openapi-fetch").Client<paths, `${string}/${string}`>;
114
145
  };
115
- export type { Agent, AgentsListResponse, CallDetailResponse, CallsListResponse, CallSummary, HelloResponse, Lead, LeadDetailResponse, LeadsListResponse, Space, SpacesListResponse };
package/dist/client.js CHANGED
@@ -52,6 +52,21 @@ export function createVueVoxClient(options) {
52
52
  async function getLead(leadId) {
53
53
  return apiGet(`/v1/leads/${encodeURIComponent(leadId)}`);
54
54
  }
55
+ async function updateLead(leadId, input) {
56
+ return apiJson("PATCH", `/v1/leads/${encodeURIComponent(leadId)}`, input);
57
+ }
58
+ async function upsertLeadByExternalId(externalId, input) {
59
+ return apiJson("PUT", `/v1/leads/by-external-id/${encodeURIComponent(externalId)}`, input);
60
+ }
61
+ async function listLeadCustomFields(listOptions = {}) {
62
+ return apiGet("/v1/lead-custom-fields", listOptions);
63
+ }
64
+ async function createLeadCustomField(input) {
65
+ return apiJson("POST", "/v1/lead-custom-fields", input);
66
+ }
67
+ async function updateLeadCustomField(key, input) {
68
+ return apiJson("PATCH", `/v1/lead-custom-fields/${encodeURIComponent(key)}`, input);
69
+ }
55
70
  async function apiGet(path, query) {
56
71
  const accessToken = await getAccessToken();
57
72
  const result = await requestJson("GET", path, {
@@ -63,6 +78,18 @@ export function createVueVoxClient(options) {
63
78
  });
64
79
  return withMetadata(result.data, result.response, result.requestId);
65
80
  }
81
+ async function apiJson(method, path, body) {
82
+ const accessToken = await getAccessToken();
83
+ const result = await requestJson(method, path, {
84
+ method,
85
+ headers: {
86
+ Authorization: `Bearer ${accessToken}`,
87
+ "Content-Type": "application/json",
88
+ },
89
+ body: JSON.stringify(body),
90
+ });
91
+ return withMetadata(result.data, result.response, result.requestId);
92
+ }
66
93
  async function requestJson(method, path, init) {
67
94
  for (let attempt = 0;; attempt++) {
68
95
  const response = await fetchFn(buildUrl(baseUrl, path, init.query), init);
@@ -76,7 +103,7 @@ export function createVueVoxClient(options) {
76
103
  }
77
104
  return { data: body, requestId, response };
78
105
  }
79
- if (attempt < retries && shouldRetry(response.status)) {
106
+ if (attempt < retries && (method === "GET" || path === "/oauth/token") && shouldRetry(response.status)) {
80
107
  await sleep(retryDelayMs(attempt, retryAfter));
81
108
  continue;
82
109
  }
@@ -111,8 +138,15 @@ export function createVueVoxClient(options) {
111
138
  leads: {
112
139
  list: listLeads,
113
140
  get: getLead,
141
+ update: updateLead,
142
+ upsertByExternalId: upsertLeadByExternalId,
114
143
  paginate: (listOptions = {}) => paginate(listLeads, listOptions),
115
144
  },
145
+ leadCustomFields: {
146
+ list: listLeadCustomFields,
147
+ create: createLeadCustomField,
148
+ update: updateLeadCustomField,
149
+ },
116
150
  raw,
117
151
  };
118
152
  }
@@ -127,12 +161,27 @@ function trimTrailingSlash(value) {
127
161
  }
128
162
  function buildUrl(baseUrl, path, query) {
129
163
  const url = new URL(`${baseUrl}${path}`);
130
- for (const [key, value] of Object.entries(query ?? {})) {
131
- if ((typeof value === "string" || typeof value === "number") && value !== "") {
132
- url.searchParams.set(key, String(value));
164
+ appendQueryParams(url.searchParams, query ?? {});
165
+ return url.toString();
166
+ }
167
+ function appendQueryParams(searchParams, query, prefix) {
168
+ for (const [rawKey, value] of Object.entries(query)) {
169
+ if (value === undefined || value === null || value === "") {
170
+ continue;
171
+ }
172
+ const key = queryKey(rawKey, prefix);
173
+ if (typeof value === "string" || typeof value === "number" || typeof value === "boolean") {
174
+ searchParams.set(key, String(value));
175
+ continue;
176
+ }
177
+ if (typeof value === "object" && !Array.isArray(value)) {
178
+ appendQueryParams(searchParams, value, key);
133
179
  }
134
180
  }
135
- return url.toString();
181
+ }
182
+ function queryKey(key, prefix) {
183
+ const publicKey = key === "customFields" ? "custom" : key === "leadCustomFields" ? "leadCustom" : key;
184
+ return prefix ? `${prefix}[${publicKey}]` : publicKey;
136
185
  }
137
186
  async function parseJson(response) {
138
187
  try {
@@ -161,9 +161,77 @@ export interface paths {
161
161
  delete?: never;
162
162
  options?: never;
163
163
  head?: never;
164
+ /**
165
+ * Update a lead
166
+ * @description Updates an organization-scoped lead and its custom fields.
167
+ */
168
+ patch: operations["updateLead"];
169
+ trace?: never;
170
+ };
171
+ "/v1/leads/by-external-id/{externalId}": {
172
+ parameters: {
173
+ query?: never;
174
+ header?: never;
175
+ path?: never;
176
+ cookie?: never;
177
+ };
178
+ get?: never;
179
+ /**
180
+ * Upsert a lead by external ID
181
+ * @description Creates or updates a lead identified by the CRM/system external ID.
182
+ */
183
+ put: operations["upsertLeadByExternalId"];
184
+ post?: never;
185
+ delete?: never;
186
+ options?: never;
187
+ head?: never;
188
+ patch?: never;
189
+ trace?: never;
190
+ };
191
+ "/v1/lead-custom-fields": {
192
+ parameters: {
193
+ query?: never;
194
+ header?: never;
195
+ path?: never;
196
+ cookie?: never;
197
+ };
198
+ /**
199
+ * List lead custom field definitions
200
+ * @description Returns lead custom field definitions for the API client's organization.
201
+ */
202
+ get: operations["listLeadCustomFields"];
203
+ put?: never;
204
+ /**
205
+ * Create a lead custom field definition
206
+ * @description Creates a typed lead custom field definition for CRM integrations and platform filters.
207
+ */
208
+ post: operations["createLeadCustomField"];
209
+ delete?: never;
210
+ options?: never;
211
+ head?: never;
164
212
  patch?: never;
165
213
  trace?: never;
166
214
  };
215
+ "/v1/lead-custom-fields/{key}": {
216
+ parameters: {
217
+ query?: never;
218
+ header?: never;
219
+ path?: never;
220
+ cookie?: never;
221
+ };
222
+ get?: never;
223
+ put?: never;
224
+ post?: never;
225
+ delete?: never;
226
+ options?: never;
227
+ head?: never;
228
+ /**
229
+ * Update a lead custom field definition
230
+ * @description Updates mutable metadata for a lead custom field definition. Keys and types are immutable.
231
+ */
232
+ patch: operations["updateLeadCustomField"];
233
+ trace?: never;
234
+ };
167
235
  }
168
236
  export type webhooks = Record<string, never>;
169
237
  export interface components {
@@ -175,7 +243,7 @@ export interface components {
175
243
  client_secret: string;
176
244
  /**
177
245
  * @description Space-separated scopes requested for the access token.
178
- * @example hello:read spaces:read agents:read calls:read leads:read
246
+ * @example hello:read spaces:read agents:read calls:read leads:read leads:write lead_custom_fields:manage
179
247
  */
180
248
  scope?: string;
181
249
  };
@@ -185,7 +253,7 @@ export interface components {
185
253
  token_type: "Bearer";
186
254
  /** @example 3600 */
187
255
  expires_in: number;
188
- /** @example hello:read spaces:read agents:read calls:read leads:read */
256
+ /** @example hello:read spaces:read agents:read calls:read leads:read leads:write lead_custom_fields:manage */
189
257
  scope: string;
190
258
  };
191
259
  HelloResponse: {
@@ -237,6 +305,7 @@ export interface components {
237
305
  externalId: string | null;
238
306
  firstName: string;
239
307
  lastName: string;
308
+ customFields: components["schemas"]["CustomFields"];
240
309
  } | null;
241
310
  AgentSummary: {
242
311
  /** Format: uuid */
@@ -298,6 +367,7 @@ export interface components {
298
367
  /** Format: email */
299
368
  email: string | null;
300
369
  phone: string | null;
370
+ customFields: components["schemas"]["CustomFields"];
301
371
  space: components["schemas"]["ResourceSummary"];
302
372
  /** Format: date-time */
303
373
  createdAt: string;
@@ -311,6 +381,72 @@ export interface components {
311
381
  LeadDetailResponse: {
312
382
  data: components["schemas"]["Lead"];
313
383
  };
384
+ LeadUpsertRequest: {
385
+ firstName: string;
386
+ lastName: string;
387
+ /** Format: email */
388
+ email?: string | null;
389
+ phone?: string | null;
390
+ /** Format: uuid */
391
+ spaceId?: string | null;
392
+ customFields?: components["schemas"]["CustomFields"];
393
+ };
394
+ LeadUpdateRequest: {
395
+ firstName?: string;
396
+ lastName?: string;
397
+ /** Format: email */
398
+ email?: string | null;
399
+ phone?: string | null;
400
+ /** Format: uuid */
401
+ spaceId?: string | null;
402
+ customFields?: components["schemas"]["CustomFields"];
403
+ };
404
+ /** @description Lead custom field values keyed by custom field key. */
405
+ CustomFields: {
406
+ [key: string]: string | number | boolean | string[] | null;
407
+ };
408
+ /** @description Custom field filters keyed by custom field key. Scalar values use equality; objects specify one operator. */
409
+ CustomFieldFilters: {
410
+ [key: string]: string | number | boolean | {
411
+ [key: string]: string | number | boolean;
412
+ };
413
+ };
414
+ LeadCustomField: {
415
+ /** @example crm_stage */
416
+ key: string;
417
+ /** @example CRM Stage */
418
+ label: string;
419
+ /** @enum {string} */
420
+ type: "text" | "number" | "boolean" | "date" | "datetime" | "select" | "multi_select";
421
+ options: string[];
422
+ isFilterable: boolean;
423
+ archived: boolean;
424
+ /** Format: date-time */
425
+ createdAt: string;
426
+ /** Format: date-time */
427
+ updatedAt: string;
428
+ };
429
+ LeadCustomFieldsListResponse: {
430
+ data: components["schemas"]["LeadCustomField"][];
431
+ };
432
+ LeadCustomFieldResponse: {
433
+ data: components["schemas"]["LeadCustomField"];
434
+ };
435
+ LeadCustomFieldCreateRequest: {
436
+ key: string;
437
+ label: string;
438
+ /** @enum {string} */
439
+ type: "text" | "number" | "boolean" | "date" | "datetime" | "select" | "multi_select";
440
+ options?: string[];
441
+ /** @default true */
442
+ isFilterable: boolean;
443
+ };
444
+ LeadCustomFieldUpdateRequest: {
445
+ label?: string;
446
+ options?: string[];
447
+ isFilterable?: boolean;
448
+ archived?: boolean;
449
+ };
314
450
  CursorPagination: {
315
451
  /** @example 50 */
316
452
  limit: number;
@@ -593,6 +729,8 @@ export interface operations {
593
729
  createdAfter?: string;
594
730
  /** @description Return calls created at or before this timestamp. */
595
731
  createdBefore?: string;
732
+ /** @description Filter calls by lead custom fields. Use equality by default, or one operator such as gte, lte, contains, before, or after. */
733
+ leadCustom?: components["schemas"]["CustomFieldFilters"];
596
734
  };
597
735
  header?: never;
598
736
  path?: never;
@@ -727,6 +865,8 @@ export interface operations {
727
865
  createdAfter?: string;
728
866
  /** @description Return leads created at or before this timestamp. */
729
867
  createdBefore?: string;
868
+ /** @description Filter leads by custom fields. Use equality by default, or one operator such as gte, lte, contains, before, or after. */
869
+ custom?: components["schemas"]["CustomFieldFilters"];
730
870
  };
731
871
  header?: never;
732
872
  path?: never;
@@ -848,4 +988,294 @@ export interface operations {
848
988
  };
849
989
  };
850
990
  };
991
+ updateLead: {
992
+ parameters: {
993
+ query?: never;
994
+ header?: never;
995
+ path: {
996
+ /** @description Lead ID. */
997
+ leadId: string;
998
+ };
999
+ cookie?: never;
1000
+ };
1001
+ requestBody: {
1002
+ content: {
1003
+ "application/json": components["schemas"]["LeadUpdateRequest"];
1004
+ };
1005
+ };
1006
+ responses: {
1007
+ /** @description Lead updated. */
1008
+ 200: {
1009
+ headers: {
1010
+ [name: string]: unknown;
1011
+ };
1012
+ content: {
1013
+ "application/json": components["schemas"]["LeadDetailResponse"];
1014
+ };
1015
+ };
1016
+ /** @description Bearer token is missing, invalid, or expired. */
1017
+ 401: {
1018
+ headers: {
1019
+ [name: string]: unknown;
1020
+ };
1021
+ content: {
1022
+ "application/json": components["schemas"]["ErrorResponse"];
1023
+ };
1024
+ };
1025
+ /** @description Bearer token does not include the required scope. */
1026
+ 403: {
1027
+ headers: {
1028
+ [name: string]: unknown;
1029
+ };
1030
+ content: {
1031
+ "application/json": components["schemas"]["ErrorResponse"];
1032
+ };
1033
+ };
1034
+ /** @description Lead was not found in the API client's organization. */
1035
+ 404: {
1036
+ headers: {
1037
+ [name: string]: unknown;
1038
+ };
1039
+ content: {
1040
+ "application/json": components["schemas"]["ErrorResponse"];
1041
+ };
1042
+ };
1043
+ /** @description Request body failed validation. */
1044
+ 422: {
1045
+ headers: {
1046
+ [name: string]: unknown;
1047
+ };
1048
+ content: {
1049
+ "application/json": components["schemas"]["ErrorResponse"];
1050
+ };
1051
+ };
1052
+ };
1053
+ };
1054
+ upsertLeadByExternalId: {
1055
+ parameters: {
1056
+ query?: never;
1057
+ header?: never;
1058
+ path: {
1059
+ /** @description External lead ID from the integrating system. */
1060
+ externalId: string;
1061
+ };
1062
+ cookie?: never;
1063
+ };
1064
+ requestBody: {
1065
+ content: {
1066
+ "application/json": components["schemas"]["LeadUpsertRequest"];
1067
+ };
1068
+ };
1069
+ responses: {
1070
+ /** @description Existing lead updated. */
1071
+ 200: {
1072
+ headers: {
1073
+ [name: string]: unknown;
1074
+ };
1075
+ content: {
1076
+ "application/json": components["schemas"]["LeadDetailResponse"];
1077
+ };
1078
+ };
1079
+ /** @description New lead created. */
1080
+ 201: {
1081
+ headers: {
1082
+ [name: string]: unknown;
1083
+ };
1084
+ content: {
1085
+ "application/json": components["schemas"]["LeadDetailResponse"];
1086
+ };
1087
+ };
1088
+ /** @description Bearer token is missing, invalid, or expired. */
1089
+ 401: {
1090
+ headers: {
1091
+ [name: string]: unknown;
1092
+ };
1093
+ content: {
1094
+ "application/json": components["schemas"]["ErrorResponse"];
1095
+ };
1096
+ };
1097
+ /** @description Bearer token does not include the required scope. */
1098
+ 403: {
1099
+ headers: {
1100
+ [name: string]: unknown;
1101
+ };
1102
+ content: {
1103
+ "application/json": components["schemas"]["ErrorResponse"];
1104
+ };
1105
+ };
1106
+ /** @description Request body failed validation. */
1107
+ 422: {
1108
+ headers: {
1109
+ [name: string]: unknown;
1110
+ };
1111
+ content: {
1112
+ "application/json": components["schemas"]["ErrorResponse"];
1113
+ };
1114
+ };
1115
+ };
1116
+ };
1117
+ listLeadCustomFields: {
1118
+ parameters: {
1119
+ query?: {
1120
+ /** @description Include archived field definitions. */
1121
+ includeArchived?: boolean;
1122
+ };
1123
+ header?: never;
1124
+ path?: never;
1125
+ cookie?: never;
1126
+ };
1127
+ requestBody?: never;
1128
+ responses: {
1129
+ /** @description Lead custom field definitions. */
1130
+ 200: {
1131
+ headers: {
1132
+ [name: string]: unknown;
1133
+ };
1134
+ content: {
1135
+ "application/json": components["schemas"]["LeadCustomFieldsListResponse"];
1136
+ };
1137
+ };
1138
+ /** @description Bearer token is missing, invalid, or expired. */
1139
+ 401: {
1140
+ headers: {
1141
+ [name: string]: unknown;
1142
+ };
1143
+ content: {
1144
+ "application/json": components["schemas"]["ErrorResponse"];
1145
+ };
1146
+ };
1147
+ /** @description Bearer token does not include the required scope. */
1148
+ 403: {
1149
+ headers: {
1150
+ [name: string]: unknown;
1151
+ };
1152
+ content: {
1153
+ "application/json": components["schemas"]["ErrorResponse"];
1154
+ };
1155
+ };
1156
+ };
1157
+ };
1158
+ createLeadCustomField: {
1159
+ parameters: {
1160
+ query?: never;
1161
+ header?: never;
1162
+ path?: never;
1163
+ cookie?: never;
1164
+ };
1165
+ requestBody: {
1166
+ content: {
1167
+ "application/json": components["schemas"]["LeadCustomFieldCreateRequest"];
1168
+ };
1169
+ };
1170
+ responses: {
1171
+ /** @description Lead custom field created. */
1172
+ 201: {
1173
+ headers: {
1174
+ [name: string]: unknown;
1175
+ };
1176
+ content: {
1177
+ "application/json": components["schemas"]["LeadCustomFieldResponse"];
1178
+ };
1179
+ };
1180
+ /** @description Bearer token is missing, invalid, or expired. */
1181
+ 401: {
1182
+ headers: {
1183
+ [name: string]: unknown;
1184
+ };
1185
+ content: {
1186
+ "application/json": components["schemas"]["ErrorResponse"];
1187
+ };
1188
+ };
1189
+ /** @description Bearer token does not include the required scope. */
1190
+ 403: {
1191
+ headers: {
1192
+ [name: string]: unknown;
1193
+ };
1194
+ content: {
1195
+ "application/json": components["schemas"]["ErrorResponse"];
1196
+ };
1197
+ };
1198
+ /** @description A custom field with this key already exists. */
1199
+ 409: {
1200
+ headers: {
1201
+ [name: string]: unknown;
1202
+ };
1203
+ content: {
1204
+ "application/json": components["schemas"]["ErrorResponse"];
1205
+ };
1206
+ };
1207
+ /** @description Request body failed validation. */
1208
+ 422: {
1209
+ headers: {
1210
+ [name: string]: unknown;
1211
+ };
1212
+ content: {
1213
+ "application/json": components["schemas"]["ErrorResponse"];
1214
+ };
1215
+ };
1216
+ };
1217
+ };
1218
+ updateLeadCustomField: {
1219
+ parameters: {
1220
+ query?: never;
1221
+ header?: never;
1222
+ path: {
1223
+ /** @description Custom field key. */
1224
+ key: string;
1225
+ };
1226
+ cookie?: never;
1227
+ };
1228
+ requestBody: {
1229
+ content: {
1230
+ "application/json": components["schemas"]["LeadCustomFieldUpdateRequest"];
1231
+ };
1232
+ };
1233
+ responses: {
1234
+ /** @description Lead custom field updated. */
1235
+ 200: {
1236
+ headers: {
1237
+ [name: string]: unknown;
1238
+ };
1239
+ content: {
1240
+ "application/json": components["schemas"]["LeadCustomFieldResponse"];
1241
+ };
1242
+ };
1243
+ /** @description Bearer token is missing, invalid, or expired. */
1244
+ 401: {
1245
+ headers: {
1246
+ [name: string]: unknown;
1247
+ };
1248
+ content: {
1249
+ "application/json": components["schemas"]["ErrorResponse"];
1250
+ };
1251
+ };
1252
+ /** @description Bearer token does not include the required scope. */
1253
+ 403: {
1254
+ headers: {
1255
+ [name: string]: unknown;
1256
+ };
1257
+ content: {
1258
+ "application/json": components["schemas"]["ErrorResponse"];
1259
+ };
1260
+ };
1261
+ /** @description Custom field was not found in the API client's organization. */
1262
+ 404: {
1263
+ headers: {
1264
+ [name: string]: unknown;
1265
+ };
1266
+ content: {
1267
+ "application/json": components["schemas"]["ErrorResponse"];
1268
+ };
1269
+ };
1270
+ /** @description Request body failed validation. */
1271
+ 422: {
1272
+ headers: {
1273
+ [name: string]: unknown;
1274
+ };
1275
+ content: {
1276
+ "application/json": components["schemas"]["ErrorResponse"];
1277
+ };
1278
+ };
1279
+ };
1280
+ };
851
1281
  }
package/dist/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
1
  export { createVueVoxClient } from "./client.js";
2
- export type { Agent, AgentsListResponse, CallDetailResponse, CallsListResponse, CallSummary, HelloResponse, Lead, LeadDetailResponse, LeadsListResponse, ListAgentsOptions, ListCallsOptions, ListLeadsOptions, ListSpacesOptions, Space, SpacesListResponse, VueVoxApiResponse, VueVoxClientOptions, VueVoxResponseEvent, VueVoxResponseMetadata, } from "./client.js";
2
+ export type { Agent, AgentsListResponse, CallDetailResponse, CallsListResponse, CallSummary, CustomFieldFilters, CustomFieldFilterValue, HelloResponse, Lead, LeadCustomField, LeadCustomFieldCreateRequest, LeadCustomFieldResponse, LeadCustomFieldUpdateRequest, LeadCustomFieldsListResponse, LeadDetailResponse, LeadUpdateRequest, LeadUpsertRequest, LeadsListResponse, ListAgentsOptions, ListCallsOptions, ListLeadCustomFieldsOptions, ListLeadsOptions, ListSpacesOptions, Space, SpacesListResponse, VueVoxApiResponse, VueVoxClientOptions, VueVoxResponseEvent, VueVoxResponseMetadata, } from "./client.js";
3
3
  export { VueVoxApiError } from "./errors.js";
4
4
  export type { VueVoxErrorResponse } from "./errors.js";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vuevox/sdk",
3
- "version": "0.6.0",
3
+ "version": "0.7.0",
4
4
  "description": "TypeScript SDK for the VueVox Developer API.",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",