@squadbase/vite-server 0.1.17-dev.24af54e → 0.1.17-dev.3b633bb

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (73) hide show
  1. package/dist/cli/index.js +1681 -449
  2. package/dist/connectors/airtable-oauth.js +28 -3
  3. package/dist/connectors/airtable.js +28 -3
  4. package/dist/connectors/amplitude.js +28 -3
  5. package/dist/connectors/asana.js +28 -3
  6. package/dist/connectors/attio.js +28 -3
  7. package/dist/connectors/aws-billing.js +28 -3
  8. package/dist/connectors/azure-sql.js +31 -6
  9. package/dist/connectors/backlog-api-key.js +28 -3
  10. package/dist/connectors/clickup.js +28 -3
  11. package/dist/connectors/cosmosdb.js +28 -3
  12. package/dist/connectors/customerio.js +29 -4
  13. package/dist/connectors/dbt.js +28 -3
  14. package/dist/connectors/freshdesk.js +28 -3
  15. package/dist/connectors/freshsales.js +28 -3
  16. package/dist/connectors/freshservice.js +28 -3
  17. package/dist/connectors/gamma.js +30 -5
  18. package/dist/connectors/github.js +28 -3
  19. package/dist/connectors/gmail-oauth.js +28 -3
  20. package/dist/connectors/gmail.js +28 -3
  21. package/dist/connectors/google-ads.js +28 -3
  22. package/dist/connectors/google-analytics-oauth.js +28 -3
  23. package/dist/connectors/google-analytics.js +227 -105
  24. package/dist/connectors/google-audit-log.js +28 -3
  25. package/dist/connectors/google-calendar-oauth.js +28 -3
  26. package/dist/connectors/google-calendar.js +28 -3
  27. package/dist/connectors/google-docs.js +28 -3
  28. package/dist/connectors/google-drive.js +28 -3
  29. package/dist/connectors/google-search-console-oauth.js +28 -3
  30. package/dist/connectors/google-sheets.js +28 -3
  31. package/dist/connectors/google-slides.js +28 -3
  32. package/dist/connectors/grafana.js +28 -3
  33. package/dist/connectors/hubspot-oauth.js +28 -3
  34. package/dist/connectors/hubspot.js +28 -3
  35. package/dist/connectors/influxdb.js +28 -3
  36. package/dist/connectors/intercom-oauth.js +28 -3
  37. package/dist/connectors/intercom.js +28 -3
  38. package/dist/connectors/jdbc.js +28 -3
  39. package/dist/connectors/jira-api-key.js +28 -3
  40. package/dist/connectors/kintone-api-token.js +28 -3
  41. package/dist/connectors/kintone.js +28 -3
  42. package/dist/connectors/linear.js +28 -3
  43. package/dist/connectors/linkedin-ads.js +28 -3
  44. package/dist/connectors/mailchimp-oauth.js +28 -3
  45. package/dist/connectors/mailchimp.js +28 -3
  46. package/dist/connectors/meta-ads-oauth.js +28 -3
  47. package/dist/connectors/meta-ads.js +28 -3
  48. package/dist/connectors/mixpanel.js +28 -3
  49. package/dist/connectors/monday.js +28 -3
  50. package/dist/connectors/mongodb.js +28 -3
  51. package/dist/connectors/notion-oauth.js +28 -3
  52. package/dist/connectors/notion.js +28 -3
  53. package/dist/connectors/oracle.js +54 -14
  54. package/dist/connectors/outlook-oauth.js +28 -3
  55. package/dist/connectors/powerbi-oauth.js +309 -37
  56. package/dist/connectors/salesforce.js +28 -3
  57. package/dist/connectors/semrush.js +366 -46
  58. package/dist/connectors/sentry.js +28 -3
  59. package/dist/connectors/shopify-oauth.js +28 -3
  60. package/dist/connectors/shopify.js +28 -3
  61. package/dist/connectors/sqlserver.js +31 -6
  62. package/dist/connectors/stripe-api-key.js +28 -3
  63. package/dist/connectors/stripe-oauth.js +28 -3
  64. package/dist/connectors/supabase.js +31 -6
  65. package/dist/connectors/tableau.js +246 -78
  66. package/dist/connectors/tiktok-ads.js +28 -3
  67. package/dist/connectors/wix-store.js +28 -3
  68. package/dist/connectors/zendesk-oauth.js +28 -3
  69. package/dist/connectors/zendesk.js +28 -3
  70. package/dist/index.js +1681 -449
  71. package/dist/main.js +1681 -449
  72. package/dist/vite-plugin.js +1681 -449
  73. package/package.json +1 -1
@@ -339,19 +339,34 @@ async function runSetupFlow(flow, params, ctx, config) {
339
339
  };
340
340
  let state = flow.initialState();
341
341
  let answerIdx = 0;
342
+ const pendingParameterUpdates = [];
342
343
  for (const step of flow.steps) {
343
344
  const ans = ctx.answers[answerIdx];
344
345
  if (ans && ans.questionSlug === step.slug) {
345
346
  state = step.applyAnswer(state, ans.answer);
347
+ if (step.toParameterUpdates) {
348
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
349
+ }
346
350
  answerIdx += 1;
347
351
  continue;
348
352
  }
353
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
349
354
  if (step.type === "text") {
355
+ if (step.fetchOptions) {
356
+ const options2 = await step.fetchOptions(state, runtime);
357
+ if (options2.length === 0) {
358
+ continue;
359
+ }
360
+ }
350
361
  return {
351
362
  type: "nextQuestion",
352
363
  questionSlug: step.slug,
353
364
  question: step.question[ctx.language],
354
- questionType: "text"
365
+ questionType: "text",
366
+ allowFreeText: resolvedAllowFreeText,
367
+ ...pendingParameterUpdates.length > 0 && {
368
+ parameterUpdates: pendingParameterUpdates
369
+ }
355
370
  };
356
371
  }
357
372
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -363,11 +378,21 @@ async function runSetupFlow(flow, params, ctx, config) {
363
378
  questionSlug: step.slug,
364
379
  question: step.question[ctx.language],
365
380
  questionType: step.type,
366
- options
381
+ options,
382
+ allowFreeText: resolvedAllowFreeText,
383
+ ...pendingParameterUpdates.length > 0 && {
384
+ parameterUpdates: pendingParameterUpdates
385
+ }
367
386
  };
368
387
  }
369
388
  const dataInvestigationResult = await flow.finalize(state, runtime);
370
- return { type: "fulfilled", dataInvestigationResult };
389
+ return {
390
+ type: "fulfilled",
391
+ dataInvestigationResult,
392
+ ...pendingParameterUpdates.length > 0 && {
393
+ parameterUpdates: pendingParameterUpdates
394
+ }
395
+ };
371
396
  }
372
397
  async function resolveSetupSelection(params) {
373
398
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -1087,19 +1087,34 @@ async function runSetupFlow(flow, params, ctx, config) {
1087
1087
  };
1088
1088
  let state = flow.initialState();
1089
1089
  let answerIdx = 0;
1090
+ const pendingParameterUpdates = [];
1090
1091
  for (const step of flow.steps) {
1091
1092
  const ans = ctx.answers[answerIdx];
1092
1093
  if (ans && ans.questionSlug === step.slug) {
1093
1094
  state = step.applyAnswer(state, ans.answer);
1095
+ if (step.toParameterUpdates) {
1096
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
1097
+ }
1094
1098
  answerIdx += 1;
1095
1099
  continue;
1096
1100
  }
1101
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
1097
1102
  if (step.type === "text") {
1103
+ if (step.fetchOptions) {
1104
+ const options2 = await step.fetchOptions(state, runtime);
1105
+ if (options2.length === 0) {
1106
+ continue;
1107
+ }
1108
+ }
1098
1109
  return {
1099
1110
  type: "nextQuestion",
1100
1111
  questionSlug: step.slug,
1101
1112
  question: step.question[ctx.language],
1102
- questionType: "text"
1113
+ questionType: "text",
1114
+ allowFreeText: resolvedAllowFreeText,
1115
+ ...pendingParameterUpdates.length > 0 && {
1116
+ parameterUpdates: pendingParameterUpdates
1117
+ }
1103
1118
  };
1104
1119
  }
1105
1120
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -1111,11 +1126,21 @@ async function runSetupFlow(flow, params, ctx, config) {
1111
1126
  questionSlug: step.slug,
1112
1127
  question: step.question[ctx.language],
1113
1128
  questionType: step.type,
1114
- options
1129
+ options,
1130
+ allowFreeText: resolvedAllowFreeText,
1131
+ ...pendingParameterUpdates.length > 0 && {
1132
+ parameterUpdates: pendingParameterUpdates
1133
+ }
1115
1134
  };
1116
1135
  }
1117
1136
  const dataInvestigationResult = await flow.finalize(state, runtime);
1118
- return { type: "fulfilled", dataInvestigationResult };
1137
+ return {
1138
+ type: "fulfilled",
1139
+ dataInvestigationResult,
1140
+ ...pendingParameterUpdates.length > 0 && {
1141
+ parameterUpdates: pendingParameterUpdates
1142
+ }
1143
+ };
1119
1144
  }
1120
1145
  async function resolveSetupSelection(params) {
1121
1146
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -288,19 +288,34 @@ async function runSetupFlow(flow, params, ctx, config) {
288
288
  };
289
289
  let state = flow.initialState();
290
290
  let answerIdx = 0;
291
+ const pendingParameterUpdates = [];
291
292
  for (const step of flow.steps) {
292
293
  const ans = ctx.answers[answerIdx];
293
294
  if (ans && ans.questionSlug === step.slug) {
294
295
  state = step.applyAnswer(state, ans.answer);
296
+ if (step.toParameterUpdates) {
297
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
298
+ }
295
299
  answerIdx += 1;
296
300
  continue;
297
301
  }
302
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
298
303
  if (step.type === "text") {
304
+ if (step.fetchOptions) {
305
+ const options2 = await step.fetchOptions(state, runtime);
306
+ if (options2.length === 0) {
307
+ continue;
308
+ }
309
+ }
299
310
  return {
300
311
  type: "nextQuestion",
301
312
  questionSlug: step.slug,
302
313
  question: step.question[ctx.language],
303
- questionType: "text"
314
+ questionType: "text",
315
+ allowFreeText: resolvedAllowFreeText,
316
+ ...pendingParameterUpdates.length > 0 && {
317
+ parameterUpdates: pendingParameterUpdates
318
+ }
304
319
  };
305
320
  }
306
321
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -312,11 +327,21 @@ async function runSetupFlow(flow, params, ctx, config) {
312
327
  questionSlug: step.slug,
313
328
  question: step.question[ctx.language],
314
329
  questionType: step.type,
315
- options
330
+ options,
331
+ allowFreeText: resolvedAllowFreeText,
332
+ ...pendingParameterUpdates.length > 0 && {
333
+ parameterUpdates: pendingParameterUpdates
334
+ }
316
335
  };
317
336
  }
318
337
  const dataInvestigationResult = await flow.finalize(state, runtime);
319
- return { type: "fulfilled", dataInvestigationResult };
338
+ return {
339
+ type: "fulfilled",
340
+ dataInvestigationResult,
341
+ ...pendingParameterUpdates.length > 0 && {
342
+ parameterUpdates: pendingParameterUpdates
343
+ }
344
+ };
320
345
  }
321
346
  async function resolveSetupSelection(params) {
322
347
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -317,19 +317,34 @@ async function runSetupFlow(flow, params, ctx, config) {
317
317
  };
318
318
  let state = flow.initialState();
319
319
  let answerIdx = 0;
320
+ const pendingParameterUpdates = [];
320
321
  for (const step of flow.steps) {
321
322
  const ans = ctx.answers[answerIdx];
322
323
  if (ans && ans.questionSlug === step.slug) {
323
324
  state = step.applyAnswer(state, ans.answer);
325
+ if (step.toParameterUpdates) {
326
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
327
+ }
324
328
  answerIdx += 1;
325
329
  continue;
326
330
  }
331
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
327
332
  if (step.type === "text") {
333
+ if (step.fetchOptions) {
334
+ const options2 = await step.fetchOptions(state, runtime);
335
+ if (options2.length === 0) {
336
+ continue;
337
+ }
338
+ }
328
339
  return {
329
340
  type: "nextQuestion",
330
341
  questionSlug: step.slug,
331
342
  question: step.question[ctx.language],
332
- questionType: "text"
343
+ questionType: "text",
344
+ allowFreeText: resolvedAllowFreeText,
345
+ ...pendingParameterUpdates.length > 0 && {
346
+ parameterUpdates: pendingParameterUpdates
347
+ }
333
348
  };
334
349
  }
335
350
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -341,11 +356,21 @@ async function runSetupFlow(flow, params, ctx, config) {
341
356
  questionSlug: step.slug,
342
357
  question: step.question[ctx.language],
343
358
  questionType: step.type,
344
- options
359
+ options,
360
+ allowFreeText: resolvedAllowFreeText,
361
+ ...pendingParameterUpdates.length > 0 && {
362
+ parameterUpdates: pendingParameterUpdates
363
+ }
345
364
  };
346
365
  }
347
366
  const dataInvestigationResult = await flow.finalize(state, runtime);
348
- return { type: "fulfilled", dataInvestigationResult };
367
+ return {
368
+ type: "fulfilled",
369
+ dataInvestigationResult,
370
+ ...pendingParameterUpdates.length > 0 && {
371
+ parameterUpdates: pendingParameterUpdates
372
+ }
373
+ };
349
374
  }
350
375
 
351
376
  // ../connectors/src/auth-types.ts
@@ -326,19 +326,34 @@ async function runSetupFlow(flow, params, ctx, config) {
326
326
  };
327
327
  let state = flow.initialState();
328
328
  let answerIdx = 0;
329
+ const pendingParameterUpdates = [];
329
330
  for (const step of flow.steps) {
330
331
  const ans = ctx.answers[answerIdx];
331
332
  if (ans && ans.questionSlug === step.slug) {
332
333
  state = step.applyAnswer(state, ans.answer);
334
+ if (step.toParameterUpdates) {
335
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
336
+ }
333
337
  answerIdx += 1;
334
338
  continue;
335
339
  }
340
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
336
341
  if (step.type === "text") {
342
+ if (step.fetchOptions) {
343
+ const options2 = await step.fetchOptions(state, runtime);
344
+ if (options2.length === 0) {
345
+ continue;
346
+ }
347
+ }
337
348
  return {
338
349
  type: "nextQuestion",
339
350
  questionSlug: step.slug,
340
351
  question: step.question[ctx.language],
341
- questionType: "text"
352
+ questionType: "text",
353
+ allowFreeText: resolvedAllowFreeText,
354
+ ...pendingParameterUpdates.length > 0 && {
355
+ parameterUpdates: pendingParameterUpdates
356
+ }
342
357
  };
343
358
  }
344
359
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -350,11 +365,21 @@ async function runSetupFlow(flow, params, ctx, config) {
350
365
  questionSlug: step.slug,
351
366
  question: step.question[ctx.language],
352
367
  questionType: step.type,
353
- options
368
+ options,
369
+ allowFreeText: resolvedAllowFreeText,
370
+ ...pendingParameterUpdates.length > 0 && {
371
+ parameterUpdates: pendingParameterUpdates
372
+ }
354
373
  };
355
374
  }
356
375
  const dataInvestigationResult = await flow.finalize(state, runtime);
357
- return { type: "fulfilled", dataInvestigationResult };
376
+ return {
377
+ type: "fulfilled",
378
+ dataInvestigationResult,
379
+ ...pendingParameterUpdates.length > 0 && {
380
+ parameterUpdates: pendingParameterUpdates
381
+ }
382
+ };
358
383
  }
359
384
  async function resolveSetupSelection(params) {
360
385
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -332,19 +332,34 @@ async function runSetupFlow(flow, params, ctx, config) {
332
332
  };
333
333
  let state = flow.initialState();
334
334
  let answerIdx = 0;
335
+ const pendingParameterUpdates = [];
335
336
  for (const step of flow.steps) {
336
337
  const ans = ctx.answers[answerIdx];
337
338
  if (ans && ans.questionSlug === step.slug) {
338
339
  state = step.applyAnswer(state, ans.answer);
340
+ if (step.toParameterUpdates) {
341
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
342
+ }
339
343
  answerIdx += 1;
340
344
  continue;
341
345
  }
346
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
342
347
  if (step.type === "text") {
348
+ if (step.fetchOptions) {
349
+ const options2 = await step.fetchOptions(state, runtime);
350
+ if (options2.length === 0) {
351
+ continue;
352
+ }
353
+ }
343
354
  return {
344
355
  type: "nextQuestion",
345
356
  questionSlug: step.slug,
346
357
  question: step.question[ctx.language],
347
- questionType: "text"
358
+ questionType: "text",
359
+ allowFreeText: resolvedAllowFreeText,
360
+ ...pendingParameterUpdates.length > 0 && {
361
+ parameterUpdates: pendingParameterUpdates
362
+ }
348
363
  };
349
364
  }
350
365
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -356,11 +371,21 @@ async function runSetupFlow(flow, params, ctx, config) {
356
371
  questionSlug: step.slug,
357
372
  question: step.question[ctx.language],
358
373
  questionType: step.type,
359
- options
374
+ options,
375
+ allowFreeText: resolvedAllowFreeText,
376
+ ...pendingParameterUpdates.length > 0 && {
377
+ parameterUpdates: pendingParameterUpdates
378
+ }
360
379
  };
361
380
  }
362
381
  const dataInvestigationResult = await flow.finalize(state, runtime);
363
- return { type: "fulfilled", dataInvestigationResult };
382
+ return {
383
+ type: "fulfilled",
384
+ dataInvestigationResult,
385
+ ...pendingParameterUpdates.length > 0 && {
386
+ parameterUpdates: pendingParameterUpdates
387
+ }
388
+ };
364
389
  }
365
390
  async function resolveSetupSelection(params) {
366
391
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -235,19 +235,34 @@ async function runSetupFlow(flow, params, ctx, config) {
235
235
  };
236
236
  let state = flow.initialState();
237
237
  let answerIdx = 0;
238
+ const pendingParameterUpdates = [];
238
239
  for (const step of flow.steps) {
239
240
  const ans = ctx.answers[answerIdx];
240
241
  if (ans && ans.questionSlug === step.slug) {
241
242
  state = step.applyAnswer(state, ans.answer);
243
+ if (step.toParameterUpdates) {
244
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
245
+ }
242
246
  answerIdx += 1;
243
247
  continue;
244
248
  }
249
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
245
250
  if (step.type === "text") {
251
+ if (step.fetchOptions) {
252
+ const options2 = await step.fetchOptions(state, runtime);
253
+ if (options2.length === 0) {
254
+ continue;
255
+ }
256
+ }
246
257
  return {
247
258
  type: "nextQuestion",
248
259
  questionSlug: step.slug,
249
260
  question: step.question[ctx.language],
250
- questionType: "text"
261
+ questionType: "text",
262
+ allowFreeText: resolvedAllowFreeText,
263
+ ...pendingParameterUpdates.length > 0 && {
264
+ parameterUpdates: pendingParameterUpdates
265
+ }
251
266
  };
252
267
  }
253
268
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -259,11 +274,21 @@ async function runSetupFlow(flow, params, ctx, config) {
259
274
  questionSlug: step.slug,
260
275
  question: step.question[ctx.language],
261
276
  questionType: step.type,
262
- options
277
+ options,
278
+ allowFreeText: resolvedAllowFreeText,
279
+ ...pendingParameterUpdates.length > 0 && {
280
+ parameterUpdates: pendingParameterUpdates
281
+ }
263
282
  };
264
283
  }
265
284
  const dataInvestigationResult = await flow.finalize(state, runtime);
266
- return { type: "fulfilled", dataInvestigationResult };
285
+ return {
286
+ type: "fulfilled",
287
+ dataInvestigationResult,
288
+ ...pendingParameterUpdates.length > 0 && {
289
+ parameterUpdates: pendingParameterUpdates
290
+ }
291
+ };
267
292
  }
268
293
  async function resolveSetupSelection(params) {
269
294
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -241,19 +241,34 @@ async function runSetupFlow(flow, params, ctx, config) {
241
241
  };
242
242
  let state = flow.initialState();
243
243
  let answerIdx = 0;
244
+ const pendingParameterUpdates = [];
244
245
  for (const step of flow.steps) {
245
246
  const ans = ctx.answers[answerIdx];
246
247
  if (ans && ans.questionSlug === step.slug) {
247
248
  state = step.applyAnswer(state, ans.answer);
249
+ if (step.toParameterUpdates) {
250
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
251
+ }
248
252
  answerIdx += 1;
249
253
  continue;
250
254
  }
255
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
251
256
  if (step.type === "text") {
257
+ if (step.fetchOptions) {
258
+ const options2 = await step.fetchOptions(state, runtime);
259
+ if (options2.length === 0) {
260
+ continue;
261
+ }
262
+ }
252
263
  return {
253
264
  type: "nextQuestion",
254
265
  questionSlug: step.slug,
255
266
  question: step.question[ctx.language],
256
- questionType: "text"
267
+ questionType: "text",
268
+ allowFreeText: resolvedAllowFreeText,
269
+ ...pendingParameterUpdates.length > 0 && {
270
+ parameterUpdates: pendingParameterUpdates
271
+ }
257
272
  };
258
273
  }
259
274
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -265,11 +280,21 @@ async function runSetupFlow(flow, params, ctx, config) {
265
280
  questionSlug: step.slug,
266
281
  question: step.question[ctx.language],
267
282
  questionType: step.type,
268
- options
283
+ options,
284
+ allowFreeText: resolvedAllowFreeText,
285
+ ...pendingParameterUpdates.length > 0 && {
286
+ parameterUpdates: pendingParameterUpdates
287
+ }
269
288
  };
270
289
  }
271
290
  const dataInvestigationResult = await flow.finalize(state, runtime);
272
- return { type: "fulfilled", dataInvestigationResult };
291
+ return {
292
+ type: "fulfilled",
293
+ dataInvestigationResult,
294
+ ...pendingParameterUpdates.length > 0 && {
295
+ parameterUpdates: pendingParameterUpdates
296
+ }
297
+ };
273
298
  }
274
299
  async function resolveSetupSelection(params) {
275
300
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -346,19 +346,34 @@ async function runSetupFlow(flow, params, ctx, config) {
346
346
  };
347
347
  let state = flow.initialState();
348
348
  let answerIdx = 0;
349
+ const pendingParameterUpdates = [];
349
350
  for (const step of flow.steps) {
350
351
  const ans = ctx.answers[answerIdx];
351
352
  if (ans && ans.questionSlug === step.slug) {
352
353
  state = step.applyAnswer(state, ans.answer);
354
+ if (step.toParameterUpdates) {
355
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
356
+ }
353
357
  answerIdx += 1;
354
358
  continue;
355
359
  }
360
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
356
361
  if (step.type === "text") {
362
+ if (step.fetchOptions) {
363
+ const options2 = await step.fetchOptions(state, runtime);
364
+ if (options2.length === 0) {
365
+ continue;
366
+ }
367
+ }
357
368
  return {
358
369
  type: "nextQuestion",
359
370
  questionSlug: step.slug,
360
371
  question: step.question[ctx.language],
361
- questionType: "text"
372
+ questionType: "text",
373
+ allowFreeText: resolvedAllowFreeText,
374
+ ...pendingParameterUpdates.length > 0 && {
375
+ parameterUpdates: pendingParameterUpdates
376
+ }
362
377
  };
363
378
  }
364
379
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -370,11 +385,21 @@ async function runSetupFlow(flow, params, ctx, config) {
370
385
  questionSlug: step.slug,
371
386
  question: step.question[ctx.language],
372
387
  questionType: step.type,
373
- options
388
+ options,
389
+ allowFreeText: resolvedAllowFreeText,
390
+ ...pendingParameterUpdates.length > 0 && {
391
+ parameterUpdates: pendingParameterUpdates
392
+ }
374
393
  };
375
394
  }
376
395
  const dataInvestigationResult = await flow.finalize(state, runtime);
377
- return { type: "fulfilled", dataInvestigationResult };
396
+ return {
397
+ type: "fulfilled",
398
+ dataInvestigationResult,
399
+ ...pendingParameterUpdates.length > 0 && {
400
+ parameterUpdates: pendingParameterUpdates
401
+ }
402
+ };
378
403
  }
379
404
  async function resolveSetupSelection(params) {
380
405
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -235,19 +235,34 @@ async function runSetupFlow(flow, params, ctx, config) {
235
235
  };
236
236
  let state = flow.initialState();
237
237
  let answerIdx = 0;
238
+ const pendingParameterUpdates = [];
238
239
  for (const step of flow.steps) {
239
240
  const ans = ctx.answers[answerIdx];
240
241
  if (ans && ans.questionSlug === step.slug) {
241
242
  state = step.applyAnswer(state, ans.answer);
243
+ if (step.toParameterUpdates) {
244
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
245
+ }
242
246
  answerIdx += 1;
243
247
  continue;
244
248
  }
249
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
245
250
  if (step.type === "text") {
251
+ if (step.fetchOptions) {
252
+ const options2 = await step.fetchOptions(state, runtime);
253
+ if (options2.length === 0) {
254
+ continue;
255
+ }
256
+ }
246
257
  return {
247
258
  type: "nextQuestion",
248
259
  questionSlug: step.slug,
249
260
  question: step.question[ctx.language],
250
- questionType: "text"
261
+ questionType: "text",
262
+ allowFreeText: resolvedAllowFreeText,
263
+ ...pendingParameterUpdates.length > 0 && {
264
+ parameterUpdates: pendingParameterUpdates
265
+ }
251
266
  };
252
267
  }
253
268
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -259,11 +274,21 @@ async function runSetupFlow(flow, params, ctx, config) {
259
274
  questionSlug: step.slug,
260
275
  question: step.question[ctx.language],
261
276
  questionType: step.type,
262
- options
277
+ options,
278
+ allowFreeText: resolvedAllowFreeText,
279
+ ...pendingParameterUpdates.length > 0 && {
280
+ parameterUpdates: pendingParameterUpdates
281
+ }
263
282
  };
264
283
  }
265
284
  const dataInvestigationResult = await flow.finalize(state, runtime);
266
- return { type: "fulfilled", dataInvestigationResult };
285
+ return {
286
+ type: "fulfilled",
287
+ dataInvestigationResult,
288
+ ...pendingParameterUpdates.length > 0 && {
289
+ parameterUpdates: pendingParameterUpdates
290
+ }
291
+ };
267
292
  }
268
293
  async function resolveSetupSelection(params) {
269
294
  const { selected, allSentinel, fetchAll, limit } = params;
@@ -306,19 +306,34 @@ async function runSetupFlow(flow, params, ctx, config) {
306
306
  };
307
307
  let state = flow.initialState();
308
308
  let answerIdx = 0;
309
+ const pendingParameterUpdates = [];
309
310
  for (const step of flow.steps) {
310
311
  const ans = ctx.answers[answerIdx];
311
312
  if (ans && ans.questionSlug === step.slug) {
312
313
  state = step.applyAnswer(state, ans.answer);
314
+ if (step.toParameterUpdates) {
315
+ pendingParameterUpdates.push(...step.toParameterUpdates(state));
316
+ }
313
317
  answerIdx += 1;
314
318
  continue;
315
319
  }
320
+ const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
316
321
  if (step.type === "text") {
322
+ if (step.fetchOptions) {
323
+ const options2 = await step.fetchOptions(state, runtime);
324
+ if (options2.length === 0) {
325
+ continue;
326
+ }
327
+ }
317
328
  return {
318
329
  type: "nextQuestion",
319
330
  questionSlug: step.slug,
320
331
  question: step.question[ctx.language],
321
- questionType: "text"
332
+ questionType: "text",
333
+ allowFreeText: resolvedAllowFreeText,
334
+ ...pendingParameterUpdates.length > 0 && {
335
+ parameterUpdates: pendingParameterUpdates
336
+ }
322
337
  };
323
338
  }
324
339
  const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
@@ -330,11 +345,21 @@ async function runSetupFlow(flow, params, ctx, config) {
330
345
  questionSlug: step.slug,
331
346
  question: step.question[ctx.language],
332
347
  questionType: step.type,
333
- options
348
+ options,
349
+ allowFreeText: resolvedAllowFreeText,
350
+ ...pendingParameterUpdates.length > 0 && {
351
+ parameterUpdates: pendingParameterUpdates
352
+ }
334
353
  };
335
354
  }
336
355
  const dataInvestigationResult = await flow.finalize(state, runtime);
337
- return { type: "fulfilled", dataInvestigationResult };
356
+ return {
357
+ type: "fulfilled",
358
+ dataInvestigationResult,
359
+ ...pendingParameterUpdates.length > 0 && {
360
+ parameterUpdates: pendingParameterUpdates
361
+ }
362
+ };
338
363
  }
339
364
  async function resolveSetupSelection(params) {
340
365
  const { selected, allSentinel, fetchAll, limit } = params;