@sanity/assist 1.2.16 → 2.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (52) hide show
  1. package/LICENSE +1 -1
  2. package/README.md +551 -30
  3. package/dist/index.cjs.mjs +1 -0
  4. package/dist/index.d.ts +333 -9
  5. package/dist/index.esm.js +2463 -390
  6. package/dist/index.esm.js.map +1 -1
  7. package/dist/index.js +2457 -383
  8. package/dist/index.js.map +1 -1
  9. package/package.json +12 -11
  10. package/src/_lib/form/DocumentForm.tsx +2 -1
  11. package/src/_lib/form/constants.ts +1 -0
  12. package/src/assistDocument/AssistDocumentInput.tsx +24 -4
  13. package/src/assistDocument/RequestRunInstructionProvider.tsx +37 -21
  14. package/src/assistDocument/components/AssistDocumentForm.tsx +65 -21
  15. package/src/assistDocument/components/instruction/InstructionInput.tsx +5 -4
  16. package/src/assistDocument/components/instruction/InstructionOutputField.tsx +45 -0
  17. package/src/assistDocument/components/instruction/InstructionOutputInput.tsx +205 -0
  18. package/src/assistDocument/hooks/useStudioAssistDocument.ts +5 -32
  19. package/src/assistFormComponents/AssistField.tsx +11 -5
  20. package/src/assistFormComponents/AssistFormBlock.tsx +2 -3
  21. package/src/assistFormComponents/validation/listItem.tsx +2 -2
  22. package/src/assistInspector/AssistInspector.tsx +6 -0
  23. package/src/assistInspector/FieldAutocomplete.tsx +1 -0
  24. package/src/assistInspector/helpers.ts +9 -11
  25. package/src/assistLayout/AssistLayout.tsx +9 -9
  26. package/src/components/ImageContext.tsx +30 -13
  27. package/src/components/SafeValueInput.tsx +4 -1
  28. package/src/fieldActions/assistFieldActions.tsx +42 -13
  29. package/src/fieldActions/generateCaptionActions.tsx +17 -6
  30. package/src/fieldActions/generateImageActions.tsx +57 -0
  31. package/src/helpers/assistSupported.ts +10 -16
  32. package/src/helpers/conditionalMembers.test.ts +200 -0
  33. package/src/helpers/conditionalMembers.ts +127 -0
  34. package/src/helpers/misc.ts +8 -4
  35. package/src/helpers/typeUtils.ts +19 -5
  36. package/src/index.ts +3 -0
  37. package/src/plugin.tsx +18 -4
  38. package/src/schemas/assistDocumentSchema.tsx +40 -1
  39. package/src/schemas/serialize/serializeSchema.test.ts +239 -8
  40. package/src/schemas/serialize/serializeSchema.ts +77 -10
  41. package/src/schemas/typeDefExtensions.ts +89 -5
  42. package/src/translate/FieldTranslationProvider.tsx +360 -0
  43. package/src/translate/getLanguageParams.ts +26 -0
  44. package/src/translate/languageStore.ts +18 -0
  45. package/src/translate/paths.test.ts +133 -0
  46. package/src/translate/paths.ts +175 -0
  47. package/src/translate/translateActions.tsx +188 -0
  48. package/src/translate/types.ts +160 -0
  49. package/src/types.ts +67 -15
  50. package/src/useApiClient.ts +134 -2
  51. package/src/assistLayout/AlphaMigration.tsx +0 -310
  52. package/src/legacy-types.ts +0 -72
package/dist/index.js CHANGED
@@ -12,8 +12,8 @@ var operators = require('rxjs/operators');
12
12
  var isEqual = require('react-fast-compare');
13
13
  var rxjs = require('rxjs');
14
14
  var rxjsExhaustmapWithTrailing = require('rxjs-exhaustmap-with-trailing');
15
- var desk = require('sanity/desk');
16
15
  var mutator = require('@sanity/mutator');
16
+ var desk = require('sanity/desk');
17
17
  var styled = require('styled-components');
18
18
  var dateFns = require('date-fns');
19
19
  var formatDistanceToNow = require('date-fns/formatDistanceToNow');
@@ -41,6 +41,8 @@ const instructionTaskTypeName = "sanity.assist.instructionTask";
41
41
  const fieldPresenceTypeName = "sanity.assist.instructionTask.presence";
42
42
  const assistSerializedTypeName = "sanity.assist.serialized.type";
43
43
  const assistSerializedFieldTypeName = "sanity.assist.serialized.field";
44
+ const outputFieldTypeName = "sanity.assist.output.field";
45
+ const outputTypeTypeName = "sanity.assist.output.type";
44
46
  const fieldPathParam = "pathKey";
45
47
  const instructionParam = "instruction";
46
48
  const documentRootKey = "<document>";
@@ -137,49 +139,59 @@ function isType(schemaType, typeName) {
137
139
  function isImage(schemaType) {
138
140
  return isType(schemaType, "image");
139
141
  }
140
- function getCaptionFieldOption(schemaType) {
141
- var _a;
142
+ function getDescriptionFieldOption(schemaType) {
143
+ var _a, _b;
144
+ if (!schemaType) {
145
+ return void 0;
146
+ }
147
+ const descriptionField = (_b = (_a = schemaType.options) == null ? void 0 : _a.aiAssist) == null ? void 0 : _b.imageDescriptionField;
148
+ if (descriptionField) {
149
+ return descriptionField;
150
+ }
151
+ return getDescriptionFieldOption(schemaType.type);
152
+ }
153
+ function getImageInstructionFieldOption(schemaType) {
154
+ var _a, _b;
142
155
  if (!schemaType) {
143
156
  return void 0;
144
157
  }
145
- const captionField = (_a = schemaType.options) == null ? void 0 : _a.captionField;
146
- if (captionField) {
147
- return captionField;
158
+ const imageInstructionField = (_b = (_a = schemaType.options) == null ? void 0 : _a.aiAssist) == null ? void 0 : _b.imageInstructionField;
159
+ if (imageInstructionField) {
160
+ return imageInstructionField;
148
161
  }
149
- return getCaptionFieldOption(schemaType.type);
162
+ return getImageInstructionFieldOption(schemaType.type);
150
163
  }
151
164
  function isSchemaAssistEnabled(type) {
152
165
  var _a, _b;
153
- return !((_b = (_a = type.options) == null ? void 0 : _a.aiWritingAssistance) == null ? void 0 : _b.exclude);
166
+ return !((_b = (_a = type.options) == null ? void 0 : _a.aiAssist) == null ? void 0 : _b.exclude);
154
167
  }
155
168
  function isAssistSupported(type) {
156
- let allowReadonlyHidden = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
157
169
  if (!isSchemaAssistEnabled(type)) {
158
170
  return false;
159
171
  }
160
- if (isDisabled(type, allowReadonlyHidden)) {
172
+ if (isDisabled(type)) {
161
173
  return false;
162
174
  }
163
175
  if (type.jsonType === "array") {
164
- const unsupportedArray = type.of.every(t => isDisabled(t, allowReadonlyHidden));
176
+ const unsupportedArray = type.of.every(t => isDisabled(t));
165
177
  return !unsupportedArray;
166
178
  }
167
179
  if (type.jsonType === "object") {
168
- const unsupportedObject = type.fields.every(field => isDisabled(field.type, allowReadonlyHidden));
180
+ const unsupportedObject = type.fields.every(field => isDisabled(field.type));
169
181
  return !unsupportedObject;
170
182
  }
171
183
  return true;
172
184
  }
173
- function isDisabled(type, allowReadonlyHidden) {
174
- const readonlyHidden = !!type.readOnly || !!type.hidden;
175
- return !isSchemaAssistEnabled(type) || isUnsupportedType(type) || !allowReadonlyHidden && readonlyHidden;
185
+ function isDisabled(type) {
186
+ return !isSchemaAssistEnabled(type) || isUnsupportedType(type);
176
187
  }
177
188
  function isUnsupportedType(type) {
178
- return type.jsonType === "number" || type.name === "sanity.imageCrop" || type.name === "sanity.imageHotspot" || isType(type, "reference") || isType(type, "crossDatasetReference") || isType(type, "slug") || isType(type, "url") || isType(type, "date") || isType(type, "datetime") || isType(type, "file");
189
+ var _a, _b;
190
+ return type.jsonType === "number" || type.name === "sanity.imageCrop" || type.name === "sanity.imageHotspot" || isType(type, "reference") && !((_b = (_a = type == null ? void 0 : type.options) == null ? void 0 : _a.aiAssist) == null ? void 0 : _b.embeddingsIndex) || isType(type, "crossDatasetReference") || isType(type, "slug") || isType(type, "url") || isType(type, "date") || isType(type, "datetime") || isType(type, "file");
179
191
  }
180
192
  const inlineTypes = ["document", "object", "image", "file"];
181
193
  function serializeSchema(schema, options) {
182
- const list = schema.getTypeNames().filter(t => !(hiddenTypes.includes(t) || t.startsWith("sanity."))).map(t => schema.get(t)).filter(t => !!t).filter(t => !t.hidden && !t.readOnly).map(t => getSchemaStub(t, schema, options)).filter(t => {
194
+ const list = schema.getTypeNames().filter(t => !(hiddenTypes.includes(t) || t.startsWith("sanity."))).map(t => schema.get(t)).filter(t => !!t).map(t => getSchemaStub(t, schema, options)).filter(t => {
183
195
  if ("to" in t && t.to && !t.to.length) {
184
196
  return false;
185
197
  }
@@ -217,26 +229,41 @@ function getSchemaStub(schemaType, schema, options) {
217
229
  return removeUndef(baseSchema);
218
230
  }
219
231
  function getBaseFields(schema, type, typeName, options) {
220
- var _a, _b, _c;
221
- const imagePromptField = (_a = type.options) == null ? void 0 : _a.imagePromptField;
232
+ var _a, _b, _c, _d, _e, _f;
233
+ const schemaOptions = removeUndef({
234
+ imagePromptField: (_b = (_a = type.options) == null ? void 0 : _a.aiAssist) == null ? void 0 : _b.imageInstructionField,
235
+ embeddingsIndex: (_d = (_c = type.options) == null ? void 0 : _c.aiAssist) == null ? void 0 : _d.embeddingsIndex
236
+ });
222
237
  return removeUndef({
223
- options: imagePromptField ? {
224
- imagePromptField
225
- } : void 0,
226
- values: Array.isArray((_b = type == null ? void 0 : type.options) == null ? void 0 : _b.list) ? (_c = type == null ? void 0 : type.options) == null ? void 0 : _c.list.map(v => {
238
+ options: Object.keys(schemaOptions).length ? schemaOptions : void 0,
239
+ values: Array.isArray((_e = type == null ? void 0 : type.options) == null ? void 0 : _e.list) ? (_f = type == null ? void 0 : type.options) == null ? void 0 : _f.list.map(v => {
227
240
  var _a2;
228
241
  return typeof v === "string" ? v : (_a2 = v.value) != null ? _a2 : "".concat(v.title);
229
242
  }) : void 0,
230
243
  of: "of" in type && typeName === "array" ? arrayOf(type, schema, options) : void 0,
231
244
  to: "to" in type && typeName === "reference" ? refToTypeNames(type) : void 0,
232
- fields: "fields" in type && inlineTypes.includes(typeName) ? serializeFields(schema, type, options) : void 0
245
+ fields: "fields" in type && inlineTypes.includes(typeName) ? serializeFields(schema, type, options) : void 0,
246
+ annotations: typeName === "block" && "fields" in type ? serializeAnnotations(type, schema, options) : void 0,
247
+ inlineOf: typeName === "block" && "fields" in type ? serializeInlineOf(type, schema, options) : void 0,
248
+ hidden: typeof type.hidden === "function" ? "function" : type.hidden ? true : void 0,
249
+ readOnly: typeof type.readOnly === "function" ? "function" : type.readOnly ? true : void 0
233
250
  });
234
251
  }
235
252
  function serializeFields(schema, schemaType, options) {
236
- return schemaType.fields.filter(f => {
253
+ const fields = schemaType.fieldsets ? schemaType.fieldsets.flatMap(fs => fs.single ? fs.field : fs.fields.map(f => ({
254
+ ...f,
255
+ type: {
256
+ ...f.type,
257
+ // if fieldset is (conditionally) hidden, the field must be considered the same way
258
+ // ie, if the field does not show up in conditionalMembers, it is hidden
259
+ // regardless of weather or not it is the field function or the fieldset function that hides it
260
+ hidden: typeof fs.hidden === "function" ? fs.hidden : fs.hidden ? true : f.type.hidden
261
+ }
262
+ }))) : schemaType.fields;
263
+ return fields.filter(f => {
237
264
  var _a, _b;
238
265
  return !["sanity.imageHotspot", "sanity.imageCrop"].includes((_b = (_a = f.type) == null ? void 0 : _a.name) != null ? _b : "");
239
- }).filter(f => isAssistSupported(f.type)).filter(f => !f.type.hidden && !f.type.readOnly).map(field => serializeMember(schema, field.type, field.name, options));
266
+ }).filter(f => isAssistSupported(f.type)).map(field => serializeMember(schema, field.type, field.name, options));
240
267
  }
241
268
  function serializeMember(schema, type, name, options) {
242
269
  var _a, _b;
@@ -252,6 +279,25 @@ function serializeMember(schema, type, name, options) {
252
279
  ...getBaseFields(schema, type, typeName, options)
253
280
  });
254
281
  }
282
+ function serializeInlineOf(blockSchemaType, schema, options) {
283
+ const childrenField = blockSchemaType.fields.find(f => f.name === "children");
284
+ const childrenType = childrenField == null ? void 0 : childrenField.type;
285
+ if (!childrenType || !sanity.isArraySchemaType(childrenType)) {
286
+ return void 0;
287
+ }
288
+ return arrayOf({
289
+ ...childrenType,
290
+ of: childrenType.of.filter(t => !isType(t, "span"))
291
+ }, schema, options);
292
+ }
293
+ function serializeAnnotations(blockSchemaType, schema, options) {
294
+ const markDefs = blockSchemaType.fields.find(f => f.name === "markDefs");
295
+ const marksType = markDefs == null ? void 0 : markDefs.type;
296
+ if (!marksType || !sanity.isArraySchemaType(marksType)) {
297
+ return void 0;
298
+ }
299
+ return arrayOf(marksType, schema, options);
300
+ }
255
301
  function arrayOf(arrayType, schema, options) {
256
302
  return arrayType.of.filter(type => isAssistSupported(type)).map(t => {
257
303
  return serializeMember(schema, t, t.name, options);
@@ -370,7 +416,111 @@ function SchemaEntry(_ref) {
370
416
  children: out
371
417
  });
372
418
  }
419
+ const MAX_DEPTH$1 = 6;
420
+ function getDocumentMembersFlat(doc, schemaType) {
421
+ if (!sanity.isDocumentSchemaType(schemaType)) {
422
+ console.error("Schema type is not a document");
423
+ return [];
424
+ }
425
+ return extractPaths(doc, schemaType, [], MAX_DEPTH$1);
426
+ }
427
+ function extractPaths(doc, schemaType, path, maxDepth) {
428
+ if (path.length >= maxDepth) {
429
+ return [];
430
+ }
431
+ return schemaType.fields.reduce((acc, field) => {
432
+ var _a, _b;
433
+ const fieldPath = [...path, field.name];
434
+ const fieldSchema = field.type;
435
+ const {
436
+ value
437
+ } = (_a = mutator.extractWithPath(sanity.pathToString(fieldPath), doc)[0]) != null ? _a : {};
438
+ if (!value) {
439
+ return acc;
440
+ }
441
+ const thisFieldWithPath = {
442
+ path: fieldPath,
443
+ name: field.name,
444
+ schemaType: fieldSchema,
445
+ value
446
+ };
447
+ if (fieldSchema.jsonType === "object") {
448
+ const innerFields = extractPaths(doc, fieldSchema, fieldPath, maxDepth);
449
+ return [...acc, thisFieldWithPath, ...innerFields];
450
+ } else if (fieldSchema.jsonType === "array" && fieldSchema.of.length && fieldSchema.of.some(item => "fields" in item)) {
451
+ const {
452
+ value: arrayValue
453
+ } = (_b = mutator.extractWithPath(sanity.pathToString(fieldPath), doc)[0]) != null ? _b : {};
454
+ let arrayPaths = [];
455
+ if (arrayValue == null ? void 0 : arrayValue.length) {
456
+ for (const item of arrayValue) {
457
+ const itemPath = [...fieldPath, {
458
+ _key: item._key
459
+ }];
460
+ let itemSchema = fieldSchema.of.find(t => t.name === item._type);
461
+ if (!item._type) {
462
+ itemSchema = fieldSchema.of[0];
463
+ console.warn("Array item is missing _type - using the first defined type in the array.of schema", {
464
+ itemPath,
465
+ item,
466
+ itemSchema
467
+ });
468
+ }
469
+ if (item._key && itemSchema) {
470
+ const innerFields = extractPaths(doc, itemSchema, itemPath, maxDepth);
471
+ const arrayMember = {
472
+ path: itemPath,
473
+ name: item._key,
474
+ schemaType: itemSchema,
475
+ value: item
476
+ };
477
+ arrayPaths = [...arrayPaths, arrayMember, ...innerFields];
478
+ }
479
+ }
480
+ }
481
+ return [...acc, thisFieldWithPath, ...arrayPaths];
482
+ }
483
+ return [...acc, thisFieldWithPath];
484
+ }, []);
485
+ }
486
+ const defaultLanguageOutputs = function (member, enclosingType, translateFromLanguageId, translateToLanguageIds) {
487
+ if (member.schemaType.jsonType === "object" && member.schemaType.name.startsWith("internationalizedArray")) {
488
+ const pathEnd = member.path.slice(-1);
489
+ const language = sanity.isKeySegment(pathEnd[0]) ? pathEnd[0]._key : null;
490
+ return language === translateFromLanguageId ? translateToLanguageIds.map(translateToId => ({
491
+ id: translateToId,
492
+ outputPath: [...member.path.slice(0, -1), {
493
+ _key: translateToId
494
+ }]
495
+ })) : void 0;
496
+ }
497
+ if (enclosingType.jsonType === "object" && enclosingType.name.startsWith("locale")) {
498
+ return translateFromLanguageId === member.name ? translateToLanguageIds.map(translateToId => ({
499
+ id: translateToId,
500
+ outputPath: [...member.path.slice(0, -1), translateToId]
501
+ })) : void 0;
502
+ }
503
+ return void 0;
504
+ };
505
+ function getFieldLanguageMap(documentSchema, documentMembers, translateFromLanguageId, outputLanguageIds, langFn) {
506
+ var _a, _b, _c;
507
+ const translationMaps = [];
508
+ for (const member of documentMembers) {
509
+ const parentPath = member.path.slice(0, -1);
510
+ const enclosingType = (_b = (_a = documentMembers.find(m => sanity.pathToString(m.path) === sanity.pathToString(parentPath))) == null ? void 0 : _a.schemaType) != null ? _b : documentSchema;
511
+ const translations = (_c = langFn(member, enclosingType, translateFromLanguageId, outputLanguageIds)) == null ? void 0 : _c.filter(translation => translation.id !== translateFromLanguageId);
512
+ if (translations) {
513
+ translationMaps.push({
514
+ inputLanguageId: translateFromLanguageId,
515
+ inputPath: member.path,
516
+ outputs: translations
517
+ });
518
+ }
519
+ }
520
+ return translationMaps;
521
+ }
373
522
  const aiInspectorId = "ai-assistance";
523
+ const assistFormId = "assist";
374
524
  const preventDefault = ev => ev.preventDefault();
375
525
  function DocumentForm(props) {
376
526
  var _a;
@@ -466,7 +616,7 @@ function DocumentForm(props) {
466
616
  changed: formState.changed,
467
617
  focused: formState.focused,
468
618
  groups: formState.groups,
469
- id: "root",
619
+ id: assistFormId,
470
620
  members: formState.members,
471
621
  onChange,
472
622
  onFieldGroupSelect: onSetActiveFieldGroup,
@@ -564,7 +714,7 @@ function getFieldRefs(schemaType, parent) {
564
714
  };
565
715
  const fields = field.type.jsonType === "object" ? getFieldRefs(field.type, fieldRef, depth + 1) : [];
566
716
  const syntheticFields = field.type.jsonType === "array" ? getSyntheticFields(field.type, fieldRef, depth + 1) : [];
567
- if (!isAssistSupported(field.type, true)) {
717
+ if (!isAssistSupported(field.type)) {
568
718
  return [...fields, ...syntheticFields];
569
719
  }
570
720
  return [fieldRef, ...fields, ...syntheticFields];
@@ -591,7 +741,7 @@ function getSyntheticFields(schemaType, parent) {
591
741
  synthetic: true
592
742
  };
593
743
  const fields = itemType.jsonType === "object" ? getFieldRefs(itemType, fieldRef, depth + 1) : [];
594
- if (!isAssistSupported(itemType, true)) {
744
+ if (!isAssistSupported(itemType)) {
595
745
  return fields;
596
746
  }
597
747
  return [fieldRef, ...fields];
@@ -680,7 +830,6 @@ function useStudioAssistDocument(_ref2) {
680
830
  } = _ref2;
681
831
  const documentTypeName = schemaType.name;
682
832
  const currentUser = sanity.useCurrentUser();
683
- const validation = sanity.useValidationStatus(publicId(documentId), schemaType.name).validation;
684
833
  const assistDocument = useDocumentState(assistDocumentId(documentTypeName), assistDocumentTypeName);
685
834
  const assistTasksStatus = useDocumentState(assistTasksStatusId(documentId != null ? documentId : ""), assistTasksStatusTypeName);
686
835
  const client = sanity.useClient({
@@ -705,7 +854,7 @@ function useStudioAssistDocument(_ref2) {
705
854
  return {
706
855
  ...assistField,
707
856
  tasks: tasks.filter(task => task.path === assistField.path),
708
- instructions: (_a2 = assistField.instructions) == null ? void 0 : _a2.filter(p => !p.userId || p.userId === (currentUser == null ? void 0 : currentUser.id)).map(instruction => asStudioInstruction(instruction, tasks, validation))
857
+ instructions: (_a2 = assistField.instructions) == null ? void 0 : _a2.filter(p => !p.userId || p.userId === (currentUser == null ? void 0 : currentUser.id)).map(instruction => asStudioInstruction(instruction, tasks))
709
858
  };
710
859
  });
711
860
  return sanity.typed({
@@ -720,21 +869,12 @@ function useStudioAssistDocument(_ref2) {
720
869
  }),
721
870
  fields
722
871
  });
723
- }, [assistDocument, assistTasksStatus, currentUser, validation]);
872
+ }, [assistDocument, assistTasksStatus, currentUser]);
724
873
  }
725
- function asStudioInstruction(instruction, run, validation) {
726
- var _a;
727
- const errors = validation.filter(marker => marker.level === "error");
728
- const fieldRefs = ((_a = instruction == null ? void 0 : instruction.prompt) != null ? _a : []).flatMap(block => {
729
- if (block._type === "block") {
730
- return block.children.filter(c => c._type === fieldReferenceTypeName);
731
- }
732
- return [];
733
- });
874
+ function asStudioInstruction(instruction, run) {
734
875
  return {
735
876
  ...instruction,
736
- tasks: run.filter(task => task.instructionKey === instruction._key).filter(task => task.started && ( /* @__PURE__ */new Date()).getTime() - new Date(task.started).getTime() < maxHistoryVisibilityMs),
737
- validation: errors.filter(marker => fieldRefs.map(r => r.path).filter(p => !!p).find(path => sanity.pathToString(marker.path) === path))
877
+ tasks: run.filter(task => task.instructionKey === instruction._key).filter(task => task.started && ( /* @__PURE__ */new Date()).getTime() - new Date(task.started).getTime() < maxHistoryVisibilityMs)
738
878
  };
739
879
  }
740
880
  function useInterval(ms) {
@@ -758,12 +898,15 @@ function TimeAgo(_ref3) {
758
898
  }
759
899
  function usePathKey(path) {
760
900
  return react.useMemo(() => {
761
- if (path.length) {
762
- return Array.isArray(path) ? sanity.pathToString(path) : path;
763
- }
764
- return documentRootKey;
901
+ return getPathKey(path);
765
902
  }, [path]);
766
903
  }
904
+ function getPathKey(path) {
905
+ if (path.length) {
906
+ return Array.isArray(path) ? sanity.pathToString(path) : path;
907
+ }
908
+ return documentRootKey;
909
+ }
767
910
  function getInstructionTitle(instruction) {
768
911
  var _a;
769
912
  return (_a = instruction == null ? void 0 : instruction.title) != null ? _a : "Untitled";
@@ -972,12 +1115,63 @@ function TaskItem(props) {
972
1115
  });
973
1116
  }
974
1117
  const basePath = "/assist/tasks/instruction";
1118
+ function canUseAssist(status) {
1119
+ return (status == null ? void 0 : status.enabled) && status.initialized && status.validToken;
1120
+ }
975
1121
  function useApiClient(customApiClient) {
976
1122
  const client = sanity.useClient({
977
1123
  apiVersion: "2023-06-05"
978
1124
  });
979
1125
  return react.useMemo(() => customApiClient ? customApiClient(client) : client, [client, customApiClient]);
980
1126
  }
1127
+ function useTranslate(apiClient) {
1128
+ const [loading, setLoading] = react.useState(false);
1129
+ const user = sanity.useCurrentUser();
1130
+ const schema = sanity.useSchema();
1131
+ const types = react.useMemo(() => serializeSchema(schema, {
1132
+ leanFormat: true
1133
+ }), [schema]);
1134
+ const toast = ui.useToast();
1135
+ const translate = react.useCallback(_ref4 => {
1136
+ let {
1137
+ documentId,
1138
+ languagePath,
1139
+ translatePath,
1140
+ fieldLanguageMap,
1141
+ conditionalMembers
1142
+ } = _ref4;
1143
+ setLoading(true);
1144
+ return apiClient.request({
1145
+ method: "POST",
1146
+ url: "/assist/tasks/translate/".concat(apiClient.config().dataset, "?projectId=").concat(apiClient.config().projectId),
1147
+ body: {
1148
+ documentId,
1149
+ types,
1150
+ languagePath,
1151
+ fieldLanguageMap,
1152
+ conditionalMembers,
1153
+ translatePath: translatePath.length === 0 ? documentRootKey : sanity.pathToString(translatePath),
1154
+ userId: user == null ? void 0 : user.id
1155
+ }
1156
+ }).catch(e => {
1157
+ toast.push({
1158
+ status: "error",
1159
+ title: "Translate failed",
1160
+ description: e.message
1161
+ });
1162
+ setLoading(false);
1163
+ throw e;
1164
+ }).finally(() => {
1165
+ setTimeout(() => {
1166
+ setLoading(false);
1167
+ }, 2e3);
1168
+ });
1169
+ }, [setLoading, apiClient, toast, user, types]);
1170
+ return react.useMemo(() => ({
1171
+ translate,
1172
+ loading
1173
+ }), [translate, loading]);
1174
+ }
981
1175
  function useGenerateCaption(apiClient) {
982
1176
  const [loading, setLoading] = react.useState(false);
983
1177
  const user = sanity.useCurrentUser();
@@ -986,11 +1180,11 @@ function useGenerateCaption(apiClient) {
986
1180
  leanFormat: true
987
1181
  }), [schema]);
988
1182
  const toast = ui.useToast();
989
- const generateCaption = react.useCallback(_ref4 => {
1183
+ const generateCaption = react.useCallback(_ref5 => {
990
1184
  let {
991
1185
  path,
992
1186
  documentId
993
- } = _ref4;
1187
+ } = _ref5;
994
1188
  setLoading(true);
995
1189
  return apiClient.request({
996
1190
  method: "POST",
@@ -1004,7 +1198,7 @@ function useGenerateCaption(apiClient) {
1004
1198
  }).catch(e => {
1005
1199
  toast.push({
1006
1200
  status: "error",
1007
- title: "Generate caption failed",
1201
+ title: "Generate image description failed",
1008
1202
  description: e.message
1009
1203
  });
1010
1204
  setLoading(false);
@@ -1020,6 +1214,48 @@ function useGenerateCaption(apiClient) {
1020
1214
  loading
1021
1215
  }), [generateCaption, loading]);
1022
1216
  }
1217
+ function useGenerateImage(apiClient) {
1218
+ const [loading, setLoading] = react.useState(false);
1219
+ const user = sanity.useCurrentUser();
1220
+ const schema = sanity.useSchema();
1221
+ const types = react.useMemo(() => serializeSchema(schema, {
1222
+ leanFormat: true
1223
+ }), [schema]);
1224
+ const toast = ui.useToast();
1225
+ const generateImage = react.useCallback(_ref6 => {
1226
+ let {
1227
+ path,
1228
+ documentId
1229
+ } = _ref6;
1230
+ setLoading(true);
1231
+ return apiClient.request({
1232
+ method: "POST",
1233
+ url: "/assist/tasks/generate-image/".concat(apiClient.config().dataset, "?projectId=").concat(apiClient.config().projectId),
1234
+ body: {
1235
+ path,
1236
+ documentId,
1237
+ types,
1238
+ userId: user == null ? void 0 : user.id
1239
+ }
1240
+ }).catch(e => {
1241
+ toast.push({
1242
+ status: "error",
1243
+ title: "Generate image from prompt failed",
1244
+ description: e.message
1245
+ });
1246
+ setLoading(false);
1247
+ throw e;
1248
+ }).finally(() => {
1249
+ setTimeout(() => {
1250
+ setLoading(false);
1251
+ }, 2e3);
1252
+ });
1253
+ }, [setLoading, apiClient, toast, user, types]);
1254
+ return react.useMemo(() => ({
1255
+ generateImage,
1256
+ loading
1257
+ }), [generateImage, loading]);
1258
+ }
1023
1259
  function useGetInstructStatus(apiClient) {
1024
1260
  const [loading, setLoading] = react.useState(true);
1025
1261
  const getInstructStatus = react.useCallback(async () => {
@@ -1209,8 +1445,8 @@ function RunInstructionProvider(props) {
1209
1445
  runInstructionRequest({
1210
1446
  ...request,
1211
1447
  instructionKey: instruction._key,
1212
- userTexts: Object.entries(inputs).map(_ref5 => {
1213
- let [key, value] = _ref5;
1448
+ userTexts: Object.entries(inputs).map(_ref7 => {
1449
+ let [key, value] = _ref7;
1214
1450
  return {
1215
1451
  blockKey: key,
1216
1452
  userInput: value
@@ -1223,8 +1459,8 @@ function RunInstructionProvider(props) {
1223
1459
  const open = !!runRequest;
1224
1460
  const runDisabled = react.useMemo(() => {
1225
1461
  var _a2, _b;
1226
- return ((_b = (_a2 = runRequest == null ? void 0 : runRequest.userInputBlocks) == null ? void 0 : _a2.length) != null ? _b : 0) > Object.entries(inputs).filter(_ref6 => {
1227
- let [, value] = _ref6;
1462
+ return ((_b = (_a2 = runRequest == null ? void 0 : runRequest.userInputBlocks) == null ? void 0 : _a2.length) != null ? _b : 0) > Object.entries(inputs).filter(_ref8 => {
1463
+ let [, value] = _ref8;
1228
1464
  return !!value;
1229
1465
  }).length;
1230
1466
  }, [runRequest == null ? void 0 : runRequest.userInputBlocks, inputs]);
@@ -1335,29 +1571,37 @@ function getAssistableDocId(documentSchemaType, documentId) {
1335
1571
  return documentSchemaType.liveEdit ? baseId : "drafts.".concat(baseId);
1336
1572
  }
1337
1573
  function useRequestRunInstruction(args) {
1338
- const {
1339
- documentOnChange,
1340
- isDocAssistable: isDocAssistable2
1341
- } = args;
1342
1574
  const {
1343
1575
  runInstruction,
1344
1576
  instructionLoading
1345
1577
  } = useRunInstruction();
1346
- const [queuedTask, setQueuedTask] = react.useState(void 0);
1347
- react.useEffect(() => {
1348
- if (queuedTask && isDocAssistable2) {
1349
- runInstruction(queuedTask);
1350
- setQueuedTask(void 0);
1351
- }
1352
- }, [queuedTask, isDocAssistable2, runInstruction]);
1578
+ const requestRunInstruction = useDraftDelayedTask({
1579
+ ...args,
1580
+ task: runInstruction
1581
+ });
1353
1582
  return {
1354
1583
  instructionLoading,
1355
- requestRunInstruction: react.useCallback(task => {
1356
- documentOnChange(sanity.PatchEvent.from([sanity.unset(["_force_document_creation"])]));
1357
- setQueuedTask(task);
1358
- }, [setQueuedTask, documentOnChange])
1584
+ requestRunInstruction
1359
1585
  };
1360
1586
  }
1587
+ function useDraftDelayedTask(args) {
1588
+ const {
1589
+ documentOnChange,
1590
+ isDocAssistable: isDocAssistable2,
1591
+ task
1592
+ } = args;
1593
+ const [queuedArgs, setQueuedArgs] = react.useState(void 0);
1594
+ react.useEffect(() => {
1595
+ if (queuedArgs && isDocAssistable2) {
1596
+ task(queuedArgs);
1597
+ setQueuedArgs(void 0);
1598
+ }
1599
+ }, [queuedArgs, isDocAssistable2, task]);
1600
+ return react.useCallback(taskArgs => {
1601
+ documentOnChange(sanity.PatchEvent.from([sanity.unset(["_force_document_creation"])]));
1602
+ setQueuedArgs(taskArgs);
1603
+ }, [setQueuedArgs, documentOnChange]);
1604
+ }
1361
1605
  const SparklesIllustration = styled__default.default(icons.SparklesIcon)({
1362
1606
  fontSize: "3.125em",
1363
1607
  "& path": {
@@ -1532,7 +1776,6 @@ function AssistDocumentFormEditable(props) {
1532
1776
  onChange(sanity.set((_a = documentSchema.title) != null ? _a : documentSchema.name, ["title"]));
1533
1777
  }
1534
1778
  }, [title, documentSchema, onChange, id]);
1535
- const fieldExists = !!(fields == null ? void 0 : fields.some(f => f._key === typePath));
1536
1779
  const {
1537
1780
  onPathOpen,
1538
1781
  ...formCallbacks
@@ -1564,7 +1807,8 @@ function AssistDocumentFormEditable(props) {
1564
1807
  children: [/* @__PURE__ */jsxRuntime.jsx(FieldsInitializer, {
1565
1808
  pathKey: typePath,
1566
1809
  activePath,
1567
- fieldExists,
1810
+ fields,
1811
+ documentSchema,
1568
1812
  onChange
1569
1813
  }, typePath), instruction && /* @__PURE__ */jsxRuntime.jsx(BackToInstructionListLink, {}), activePath && /* @__PURE__ */jsxRuntime.jsx(sanity.FormCallbacksProvider, {
1570
1814
  ...newCallbacks,
@@ -1608,25 +1852,64 @@ function useSelectedSchema(fieldPath, documentSchema) {
1608
1852
  return currentSchema;
1609
1853
  }, [documentSchema, fieldPath]);
1610
1854
  }
1611
- function FieldsInitializer(_ref7) {
1855
+ function FieldsInitializer(_ref9) {
1612
1856
  let {
1613
1857
  pathKey,
1614
1858
  activePath,
1615
- fieldExists,
1859
+ fields,
1860
+ documentSchema,
1616
1861
  onChange
1617
- } = _ref7;
1862
+ } = _ref9;
1863
+ const {
1864
+ config: {
1865
+ __presets: presets
1866
+ }
1867
+ } = useAiAssistanceConfig();
1868
+ const existingField = fields == null ? void 0 : fields.find(f => f._key === pathKey);
1869
+ const documentPresets = !!(documentSchema == null ? void 0 : documentSchema.name) && (presets == null ? void 0 : presets[documentSchema == null ? void 0 : documentSchema.name]);
1870
+ const missingPresetInstructions = react.useMemo(() => {
1871
+ var _a, _b;
1872
+ if (!documentPresets || !pathKey) {
1873
+ return void 0;
1874
+ }
1875
+ const existingInstructions = existingField == null ? void 0 : existingField.instructions;
1876
+ const presetField = (_a = documentPresets.fields) == null ? void 0 : _a.find(f => f.path === pathKey);
1877
+ return (_b = presetField == null ? void 0 : presetField.instructions) == null ? void 0 : _b.filter(i => !(existingInstructions == null ? void 0 : existingInstructions.some(ei => ei._key === i._key)));
1878
+ }, [documentPresets, pathKey, existingField]);
1618
1879
  const initialized = react.useRef(false);
1619
1880
  react.useEffect(() => {
1620
- if (initialized.current || fieldExists || activePath || !pathKey) {
1881
+ if (initialized.current || !pathKey) {
1882
+ return;
1883
+ }
1884
+ if (existingField && !(missingPresetInstructions == null ? void 0 : missingPresetInstructions.length)) {
1621
1885
  return;
1622
1886
  }
1623
- onChange([sanity.setIfMissing([], ["fields"]), sanity.insert([sanity.typed({
1624
- _key: pathKey,
1625
- _type: assistFieldTypeName,
1626
- path: pathKey
1627
- })], "after", ["fields", -1])]);
1887
+ let event = sanity.PatchEvent.from([sanity.setIfMissing([], ["fields"])]);
1888
+ if (!existingField) {
1889
+ event = event.append(sanity.insert([sanity.typed({
1890
+ _key: pathKey,
1891
+ _type: assistFieldTypeName,
1892
+ path: pathKey
1893
+ })], "after", ["fields", -1]));
1894
+ }
1895
+ if (missingPresetInstructions == null ? void 0 : missingPresetInstructions.length) {
1896
+ event = event.append(sanity.insert(missingPresetInstructions.map(preset => {
1897
+ var _a;
1898
+ return {
1899
+ ...preset,
1900
+ _type: "sanity.assist.instruction",
1901
+ prompt: (_a = preset.prompt) == null ? void 0 : _a.map(p => ({
1902
+ markDefs: [],
1903
+ ...p
1904
+ }))
1905
+ };
1906
+ }), "after", ["fields", {
1907
+ _key: pathKey
1908
+ }, "instructions", -1]));
1909
+ }
1910
+ onChange(event);
1628
1911
  initialized.current = true;
1629
- }, [activePath, onChange, pathKey, fieldExists]);
1912
+ }, [activePath, onChange, pathKey, existingField, missingPresetInstructions]);
1630
1913
  return null;
1631
1914
  }
1632
1915
  function FieldAutocomplete(props) {
@@ -1645,7 +1928,7 @@ function FieldAutocomplete(props) {
1645
1928
  return getFieldRefs(schemaType);
1646
1929
  }, [schemaType, includeDocument]);
1647
1930
  const currentField = react.useMemo(() => fieldRefs.find(f => f.key === fieldPath), [fieldPath, fieldRefs]);
1648
- const autocompleteOptions = react.useMemo(() => fieldRefs.filter(field => filter ? filter(field) : true).map(field => ({
1931
+ const autocompleteOptions = react.useMemo(() => fieldRefs.filter(field => filter ? filter(field) : true).filter(f => !isType(f.schemaType, "reference")).map(field => ({
1649
1932
  value: field.key,
1650
1933
  field
1651
1934
  })), [fieldRefs, filter]);
@@ -1758,6 +2041,78 @@ function FieldTitle(props) {
1758
2041
  })
1759
2042
  });
1760
2043
  }
2044
+ const MAX_DEPTH = 8;
2045
+ function getConditionalMembers(docState) {
2046
+ const doc = {
2047
+ path: "",
2048
+ hidden: false,
2049
+ readOnly: !!docState.readOnly,
2050
+ conditional: typeof docState.schemaType.hidden === "function"
2051
+ };
2052
+ return [doc, ...extractConditionalPaths(docState, MAX_DEPTH)].filter(v => v.conditional).map(_ref10 => {
2053
+ let {
2054
+ conditional,
2055
+ ...state
2056
+ } = _ref10;
2057
+ return {
2058
+ ...state
2059
+ };
2060
+ });
2061
+ }
2062
+ function isConditional(schemaType) {
2063
+ return typeof schemaType.hidden === "function" || typeof schemaType.readOnly === "function";
2064
+ }
2065
+ function conditionalState(memberState) {
2066
+ return {
2067
+ path: sanity.pathToString(memberState.path),
2068
+ readOnly: !!memberState.readOnly,
2069
+ hidden: false,
2070
+ // if its in members, its not hidden
2071
+ conditional: isConditional(memberState.schemaType)
2072
+ };
2073
+ }
2074
+ function extractConditionalPaths(node, maxDepth) {
2075
+ if (node.path.length >= maxDepth) {
2076
+ return [];
2077
+ }
2078
+ return node.members.reduce((acc, member) => {
2079
+ var _a, _b;
2080
+ if (member.kind === "error") {
2081
+ return acc;
2082
+ }
2083
+ if (member.kind === "field") {
2084
+ const schemaType = member.field.schemaType;
2085
+ if (schemaType.jsonType === "object") {
2086
+ const innerFields = member.field.readOnly ? [] : extractConditionalPaths(member.field, maxDepth);
2087
+ return [...acc, conditionalState(member.field), ...innerFields];
2088
+ } else if (schemaType.jsonType === "array") {
2089
+ const array = member.field;
2090
+ let arrayPaths = [];
2091
+ const isObjectsArray = array.members.some(m => m.kind === "item" && sanity.isObjectSchemaType(m.item.schemaType));
2092
+ if (!array.readOnly) {
2093
+ for (const arrayMember of array.members) {
2094
+ if (arrayMember.kind === "error") {
2095
+ continue;
2096
+ }
2097
+ const innerFields = isObjectsArray && !arrayMember.item.readOnly ? extractConditionalPaths(arrayMember.item, maxDepth) : [];
2098
+ arrayPaths = [...arrayPaths, conditionalState(arrayMember.item), ...innerFields];
2099
+ }
2100
+ }
2101
+ return [...acc, conditionalState(array), ...arrayPaths];
2102
+ }
2103
+ return [...acc, conditionalState(member.field)];
2104
+ } else if (member.kind === "fieldSet") {
2105
+ const conditionalFieldset = !!((_b = (_a = node.schemaType) == null ? void 0 : _a.fieldsets) == null ? void 0 : _b.some(f => !f.single && f.name === member.fieldSet.name && typeof f.hidden === "function"));
2106
+ const innerFields = extractConditionalPaths(member.fieldSet, maxDepth).map(f => ({
2107
+ ...f,
2108
+ // if fieldset is conditional, visible fields must also be considered conditional
2109
+ conditional: conditionalFieldset != null ? conditionalFieldset : f.conditional
2110
+ }));
2111
+ return [...acc, ...innerFields];
2112
+ }
2113
+ return acc;
2114
+ }, []);
2115
+ }
1761
2116
  var __freeze$4 = Object.freeze;
1762
2117
  var __defProp$4 = Object.defineProperty;
1763
2118
  var __template$4 = (cooked, raw) => __freeze$4(__defProp$4(cooked, "raw", {
@@ -1897,12 +2252,15 @@ function AssistInspector(props) {
1897
2252
  documentType,
1898
2253
  value: docValue,
1899
2254
  schemaType,
1900
- onChange: documentOnChange
2255
+ onChange: documentOnChange,
2256
+ formState
1901
2257
  } = documentPane;
1902
2258
  const {
1903
2259
  published,
1904
2260
  draft
1905
2261
  } = sanity.useEditState(documentId, documentType, "low");
2262
+ const formStateRef = react.useRef(formState);
2263
+ formStateRef.current = formState;
1906
2264
  const assistableDocId = getAssistableDocId(schemaType, documentId);
1907
2265
  const {
1908
2266
  instructionLoading,
@@ -1956,7 +2314,8 @@ function AssistInspector(props) {
1956
2314
  path: pathKey,
1957
2315
  typePath,
1958
2316
  assistDocumentId: assistDocumentId(documentType),
1959
- instruction
2317
+ instruction,
2318
+ conditionalMembers: formStateRef.current ? getConditionalMembers(formStateRef.current) : []
1960
2319
  }), [pathKey, instruction, typePath, documentType, assistableDocId, requestRunInstruction]);
1961
2320
  const Region = react.useCallback(_props => {
1962
2321
  return /* @__PURE__ */jsxRuntime.jsx("div", {
@@ -2142,10 +2501,10 @@ const assistInspector = {
2142
2501
  showAsAction: false
2143
2502
  }),
2144
2503
  component: AssistInspectorWrapper,
2145
- onClose(_ref8) {
2504
+ onClose(_ref11) {
2146
2505
  let {
2147
2506
  params
2148
- } = _ref8;
2507
+ } = _ref11;
2149
2508
  return {
2150
2509
  params: sanity.typed({
2151
2510
  ...params,
@@ -2218,11 +2577,11 @@ var __template$3 = (cooked, raw) => __freeze$3(__defProp$3(cooked, "raw", {
2218
2577
  var _a$3, _b$1;
2219
2578
  const fadeIn = styled.keyframes(_a$3 || (_a$3 = __template$3(["\n 0% {\n opacity: 0;\n transform: scale(0.75);\n }\n 40% {\n opacity: 0;\n transform: scale(0.75);\n }\n 100% {\n opacity: 1;\n transform: scale(1);\n }\n"])));
2220
2579
  const FadeInDiv = styled__default.default.div(_b$1 || (_b$1 = __template$3(["\n animation-name: ", ";\n animation-timing-function: ease-in-out;\n"])), fadeIn);
2221
- const FadeInContent = react.forwardRef(function FadeInContent2(_ref9, ref) {
2580
+ const FadeInContent = react.forwardRef(function FadeInContent2(_ref12, ref) {
2222
2581
  let {
2223
2582
  children,
2224
2583
  durationMs = 250
2225
- } = _ref9;
2584
+ } = _ref12;
2226
2585
  return /* @__PURE__ */jsxRuntime.jsx(FadeInDiv, {
2227
2586
  ref,
2228
2587
  style: {
@@ -2475,7 +2834,7 @@ function AssistFieldWrapper(props) {
2475
2834
  if (!isSupported || schemaType.name.startsWith("sanity.") || schemaType.name === contextDocumentTypeName) {
2476
2835
  return props.renderDefault(props);
2477
2836
  }
2478
- if (!isType(props.schemaType, "document") && props.inputId !== "root") {
2837
+ if (!isType(props.schemaType, "document") && props.inputId !== "root" && props.inputId !== assistFormId) {
2479
2838
  return /* @__PURE__ */jsxRuntime.jsx(AssistField, {
2480
2839
  ...props,
2481
2840
  children: props.children
@@ -2495,15 +2854,16 @@ function AssistField(props) {
2495
2854
  showOnboarding,
2496
2855
  dismissOnboarding
2497
2856
  } = useOnboardingFeature(fieldOnboardingKey);
2857
+ const singlePresence = presence[0];
2498
2858
  const actions = /* @__PURE__ */jsxRuntime.jsxs(ui.Flex, {
2499
2859
  gap: 2,
2500
2860
  align: "center",
2501
2861
  justify: "space-between",
2502
- children: [presence.map(pre => /* @__PURE__ */jsxRuntime.jsx(ui.Box, {
2862
+ children: [singlePresence && /* @__PURE__ */jsxRuntime.jsx(ui.Box, {
2503
2863
  children: /* @__PURE__ */jsxRuntime.jsx(AiFieldPresence, {
2504
- presence: pre
2505
- }, pre.lastActiveAt)
2506
- }, pre.user.id)), isFirstAssisted && showOnboarding && /* @__PURE__ */jsxRuntime.jsx(AssistOnboardingPopover, {
2864
+ presence: singlePresence
2865
+ })
2866
+ }), isFirstAssisted && showOnboarding && /* @__PURE__ */jsxRuntime.jsx(AssistOnboardingPopover, {
2507
2867
  dismiss: dismissOnboarding
2508
2868
  })]
2509
2869
  });
@@ -2983,253 +3343,1500 @@ function AssistConnectorsOverlay(props) {
2983
3343
  }), DEBUG]
2984
3344
  });
2985
3345
  }
2986
- const legacyAssistDocumentIdPrefix = "sanity.ai.";
2987
- const legacyAssistDocumentTypeName = "sanity.ai.docType";
2988
- const legacyContextDocumentTypeName = "ai.instruction.context";
2989
- const legacyAssistStatusDocumentTypeName = "sanity.ai.instructionStatus";
2990
- const NO_ASSIST_DOCS = [];
2991
- const NO_CONTEXT_DOCS = [];
2992
- const NO_IDS = [];
2993
- function AlphaMigration() {
2994
- const [alphaAssistDocs, setAlphaAssistDocs] = react.useState(NO_ASSIST_DOCS);
2995
- const [contextDocs, setContextDocs] = react.useState(NO_CONTEXT_DOCS);
2996
- const [staleStatusDocIds, setStaleStatusDocs] = react.useState(NO_IDS);
2997
- const [error, setError] = react.useState(void 0);
2998
- const [progress, setProgress] = react.useState(void 0);
2999
- const toast = ui.useToast();
3000
- const client = sanity.useClient({
3001
- apiVersion: "2023-06-01"
3002
- });
3003
- react.useEffect(() => {
3004
- let canUpdate = true;
3005
- client.fetch('\n {\n "assistDocs": *[_type=="'.concat(legacyAssistDocumentTypeName, '"],\n "staleStatusDocIds": *[_type=="').concat(legacyAssistStatusDocumentTypeName, '"]._id,\n "contextDocs": *[_type=="').concat(legacyContextDocumentTypeName, '"],\n }\n ')).then(result => {
3006
- var _a, _b, _c;
3007
- if (!canUpdate || !result) {
3008
- return;
3009
- }
3010
- setAlphaAssistDocs((_a = result == null ? void 0 : result.assistDocs) != null ? _a : NO_ASSIST_DOCS);
3011
- setStaleStatusDocs((_b = result == null ? void 0 : result.staleStatusDocIds) != null ? _b : NO_IDS);
3012
- setContextDocs((_c = result == null ? void 0 : result.contextDocs) != null ? _c : NO_CONTEXT_DOCS);
3013
- });
3014
- return () => {
3015
- canUpdate = false;
3016
- };
3017
- }, [client, setAlphaAssistDocs, setStaleStatusDocs, setContextDocs]);
3018
- const convert = react.useCallback(async () => {
3019
- try {
3020
- setProgress(1e-4);
3021
- const tasks = [() => convertContextDocs(client, contextDocs), subtaskProgress => deleteDocs(client, staleStatusDocIds, subtaskProgress), subtaskProgress => convertDocs(client, alphaAssistDocs, subtaskProgress), subtaskProgress => deleteDocs(client, contextDocs.map(d => d._id), subtaskProgress)];
3022
- const taskSize = 1 / tasks.length;
3023
- for (let i = 0; i < tasks.length; i++) {
3024
- const startProgress = i / tasks.length;
3025
- await tasks[i](subProgress => setProgress(startProgress + subProgress * taskSize));
3026
- setProgress((i + 1) / tasks.length);
3027
- }
3028
- setProgress(1);
3029
- setAlphaAssistDocs(NO_ASSIST_DOCS);
3030
- setContextDocs(NO_CONTEXT_DOCS);
3031
- setStaleStatusDocs(NO_IDS);
3032
- toast.push({
3033
- title: "Converted instructions to new format.",
3034
- status: "success",
3035
- closable: true
3036
- });
3037
- } catch (e) {
3038
- console.error(e);
3039
- toast.push({
3040
- title: "An error occurred",
3041
- status: "error",
3042
- closable: true
3043
- });
3044
- setError(e);
3045
- setProgress(void 0);
3346
+ var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
3347
+ function getDefaultExportFromCjs(x) {
3348
+ return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x;
3349
+ }
3350
+
3351
+ /**
3352
+ * Checks if `value` is classified as an `Array` object.
3353
+ *
3354
+ * @static
3355
+ * @memberOf _
3356
+ * @since 0.1.0
3357
+ * @category Lang
3358
+ * @param {*} value The value to check.
3359
+ * @returns {boolean} Returns `true` if `value` is an array, else `false`.
3360
+ * @example
3361
+ *
3362
+ * _.isArray([1, 2, 3]);
3363
+ * // => true
3364
+ *
3365
+ * _.isArray(document.body.children);
3366
+ * // => false
3367
+ *
3368
+ * _.isArray('abc');
3369
+ * // => false
3370
+ *
3371
+ * _.isArray(_.noop);
3372
+ * // => false
3373
+ */
3374
+
3375
+ var isArray$3 = Array.isArray;
3376
+ var isArray_1 = isArray$3;
3377
+
3378
+ /** Detect free variable `global` from Node.js. */
3379
+
3380
+ var freeGlobal$1 = typeof commonjsGlobal == 'object' && commonjsGlobal && commonjsGlobal.Object === Object && commonjsGlobal;
3381
+ var _freeGlobal = freeGlobal$1;
3382
+ var freeGlobal = _freeGlobal;
3383
+
3384
+ /** Detect free variable `self`. */
3385
+ var freeSelf = typeof self == 'object' && self && self.Object === Object && self;
3386
+
3387
+ /** Used as a reference to the global object. */
3388
+ var root$3 = freeGlobal || freeSelf || Function('return this')();
3389
+ var _root = root$3;
3390
+ var root$2 = _root;
3391
+
3392
+ /** Built-in value references. */
3393
+ var Symbol$3 = root$2.Symbol;
3394
+ var _Symbol = Symbol$3;
3395
+ var Symbol$2 = _Symbol;
3396
+
3397
+ /** Used for built-in method references. */
3398
+ var objectProto$4 = Object.prototype;
3399
+
3400
+ /** Used to check objects for own properties. */
3401
+ var hasOwnProperty$3 = objectProto$4.hasOwnProperty;
3402
+
3403
+ /**
3404
+ * Used to resolve the
3405
+ * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
3406
+ * of values.
3407
+ */
3408
+ var nativeObjectToString$1 = objectProto$4.toString;
3409
+
3410
+ /** Built-in value references. */
3411
+ var symToStringTag$1 = Symbol$2 ? Symbol$2.toStringTag : undefined;
3412
+
3413
+ /**
3414
+ * A specialized version of `baseGetTag` which ignores `Symbol.toStringTag` values.
3415
+ *
3416
+ * @private
3417
+ * @param {*} value The value to query.
3418
+ * @returns {string} Returns the raw `toStringTag`.
3419
+ */
3420
+ function getRawTag$1(value) {
3421
+ var isOwn = hasOwnProperty$3.call(value, symToStringTag$1),
3422
+ tag = value[symToStringTag$1];
3423
+ try {
3424
+ value[symToStringTag$1] = undefined;
3425
+ var unmasked = true;
3426
+ } catch (e) {}
3427
+ var result = nativeObjectToString$1.call(value);
3428
+ if (unmasked) {
3429
+ if (isOwn) {
3430
+ value[symToStringTag$1] = tag;
3431
+ } else {
3432
+ delete value[symToStringTag$1];
3046
3433
  }
3047
- }, [contextDocs, client, alphaAssistDocs, staleStatusDocIds, setProgress, toast]);
3048
- if ((alphaAssistDocs.length || staleStatusDocIds.length || contextDocs.length) && (!progress || progress < 1)) {
3049
- return /* @__PURE__ */jsxRuntime.jsx(ui.Dialog, {
3050
- id: "outdated-assist-docs",
3051
- header: pluginTitle,
3052
- children: /* @__PURE__ */jsxRuntime.jsx(ui.Card, {
3053
- padding: 3,
3054
- children: /* @__PURE__ */jsxRuntime.jsxs(ui.Stack, {
3055
- space: 4,
3056
- style: {
3057
- maxWidth: 500
3058
- },
3059
- children: [/* @__PURE__ */jsxRuntime.jsxs(ui.Text, {
3060
- size: 1,
3061
- children: ["It seems like this workspace contains documents from an", " ", /* @__PURE__ */jsxRuntime.jsxs("strong", {
3062
- children: ["older version of ", pluginTitle]
3063
- }), "."]
3064
- }), /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
3065
- size: 1,
3066
- children: "Cleanup is required."
3067
- }), error ? /* @__PURE__ */jsxRuntime.jsxs(ui.Card, {
3068
- padding: 2,
3069
- tone: "critical",
3070
- border: true,
3071
- children: [/* @__PURE__ */jsxRuntime.jsx(ui.Text, {
3072
- size: 1,
3073
- children: "An error occurred. See console for details."
3074
- }), " "]
3075
- }) : null, /* @__PURE__ */jsxRuntime.jsx(ui.Button, {
3076
- icon: progress ? /* @__PURE__ */jsxRuntime.jsx(ui.Box, {
3077
- style: {
3078
- marginTop: 5
3079
- },
3080
- children: /* @__PURE__ */jsxRuntime.jsx(ui.Spinner, {})
3081
- }) : icons.CheckmarkIcon,
3082
- disabled: !!progress,
3083
- text: progress ? "".concat(Math.floor(progress * 100), "%") : "Ok, convert to new format!",
3084
- tone: "primary",
3085
- onClick: convert
3086
- })]
3087
- })
3088
- })
3089
- });
3090
3434
  }
3091
- return null;
3435
+ return result;
3092
3436
  }
3093
- async function deleteDocs(client, ids, updateProgress) {
3094
- const chunkSize = 50;
3095
- for (let i = 0; i < ids.length; i += chunkSize) {
3096
- const progressCount = Math.min(ids.length, i + chunkSize);
3097
- const chunk = ids.slice(i, progressCount);
3098
- const trans = client.transaction();
3099
- chunk.forEach(id => trans.delete(id));
3100
- await trans.commit();
3101
- updateProgress(progressCount / ids.length);
3437
+ var _getRawTag = getRawTag$1;
3438
+
3439
+ /** Used for built-in method references. */
3440
+
3441
+ var objectProto$3 = Object.prototype;
3442
+
3443
+ /**
3444
+ * Used to resolve the
3445
+ * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
3446
+ * of values.
3447
+ */
3448
+ var nativeObjectToString = objectProto$3.toString;
3449
+
3450
+ /**
3451
+ * Converts `value` to a string using `Object.prototype.toString`.
3452
+ *
3453
+ * @private
3454
+ * @param {*} value The value to convert.
3455
+ * @returns {string} Returns the converted string.
3456
+ */
3457
+ function objectToString$1(value) {
3458
+ return nativeObjectToString.call(value);
3459
+ }
3460
+ var _objectToString = objectToString$1;
3461
+ var Symbol$1 = _Symbol,
3462
+ getRawTag = _getRawTag,
3463
+ objectToString = _objectToString;
3464
+
3465
+ /** `Object#toString` result references. */
3466
+ var nullTag = '[object Null]',
3467
+ undefinedTag = '[object Undefined]';
3468
+
3469
+ /** Built-in value references. */
3470
+ var symToStringTag = Symbol$1 ? Symbol$1.toStringTag : undefined;
3471
+
3472
+ /**
3473
+ * The base implementation of `getTag` without fallbacks for buggy environments.
3474
+ *
3475
+ * @private
3476
+ * @param {*} value The value to query.
3477
+ * @returns {string} Returns the `toStringTag`.
3478
+ */
3479
+ function baseGetTag$2(value) {
3480
+ if (value == null) {
3481
+ return value === undefined ? undefinedTag : nullTag;
3102
3482
  }
3483
+ return symToStringTag && symToStringTag in Object(value) ? getRawTag(value) : objectToString(value);
3103
3484
  }
3104
- async function convertContextDocs(client, docs) {
3105
- const trans = client.transaction();
3106
- for (const doc of docs) {
3107
- const {
3108
- _id,
3109
- _type,
3110
- ...rest
3111
- } = doc;
3112
- trans.createOrReplace({
3113
- ...rest,
3114
- _id: "port.".concat(_id),
3115
- _alphaId: _id,
3116
- _type: contextDocumentTypeName
3117
- });
3118
- }
3119
- await trans.commit();
3120
- }
3121
- async function convertDocs(client, docs, updateProgress) {
3122
- const chunkSize = 10;
3123
- for (let i = 0; i < docs.length; i += chunkSize) {
3124
- const progressCount = Math.min(docs.length, i + chunkSize);
3125
- const chunk = docs.slice(i, progressCount);
3126
- const trans = client.transaction();
3127
- const contextDocs = await client.fetch('*[_type=="'.concat(contextDocumentTypeName, '" && _alphaId != null]{_id, _alphaId}'));
3128
- chunk.forEach(oldDoc => {
3129
- var _a;
3130
- const documentType = oldDoc._id.replace(new RegExp("^(".concat(legacyAssistDocumentIdPrefix, "|").concat(assistDocumentIdPrefix, ")")), "");
3131
- const id = assistDocumentId(documentType);
3132
- const fields = ((_a = oldDoc.fields) != null ? _a : []).filter(field => {
3133
- var _a2;
3134
- return (_a2 = field.instructions) == null ? void 0 : _a2.length;
3135
- }).map(oldField => {
3136
- var _a2;
3137
- const instructions = ((_a2 = oldField.instructions) != null ? _a2 : []).map(inst => {
3138
- var _a3;
3139
- const prompt = ((_a3 = inst.prompt) != null ? _a3 : []).map(block => {
3140
- return mapBlock(block, contextDocs);
3141
- });
3142
- return {
3143
- ...inst,
3144
- _type: instructionTypeName,
3145
- prompt
3146
- };
3147
- });
3148
- return {
3149
- ...oldField,
3150
- _type: assistFieldTypeName,
3151
- instructions
3152
- };
3153
- });
3154
- if (fields.length) {
3155
- trans.createOrReplace({
3156
- _id: id,
3157
- _type: assistDocumentTypeName,
3158
- fields
3159
- });
3160
- }
3161
- trans.delete(oldDoc._id);
3162
- });
3163
- await trans.commit();
3164
- updateProgress(progressCount / docs.length);
3165
- }
3485
+ var _baseGetTag = baseGetTag$2;
3486
+
3487
+ /**
3488
+ * Checks if `value` is object-like. A value is object-like if it's not `null`
3489
+ * and has a `typeof` result of "object".
3490
+ *
3491
+ * @static
3492
+ * @memberOf _
3493
+ * @since 4.0.0
3494
+ * @category Lang
3495
+ * @param {*} value The value to check.
3496
+ * @returns {boolean} Returns `true` if `value` is object-like, else `false`.
3497
+ * @example
3498
+ *
3499
+ * _.isObjectLike({});
3500
+ * // => true
3501
+ *
3502
+ * _.isObjectLike([1, 2, 3]);
3503
+ * // => true
3504
+ *
3505
+ * _.isObjectLike(_.noop);
3506
+ * // => false
3507
+ *
3508
+ * _.isObjectLike(null);
3509
+ * // => false
3510
+ */
3511
+
3512
+ function isObjectLike$1(value) {
3513
+ return value != null && typeof value == 'object';
3166
3514
  }
3167
- function isFieldRef(block) {
3168
- return block._type === "sanity.ai.prompt.fieldRef";
3515
+ var isObjectLike_1 = isObjectLike$1;
3516
+ var baseGetTag$1 = _baseGetTag,
3517
+ isObjectLike = isObjectLike_1;
3518
+
3519
+ /** `Object#toString` result references. */
3520
+ var symbolTag = '[object Symbol]';
3521
+
3522
+ /**
3523
+ * Checks if `value` is classified as a `Symbol` primitive or object.
3524
+ *
3525
+ * @static
3526
+ * @memberOf _
3527
+ * @since 4.0.0
3528
+ * @category Lang
3529
+ * @param {*} value The value to check.
3530
+ * @returns {boolean} Returns `true` if `value` is a symbol, else `false`.
3531
+ * @example
3532
+ *
3533
+ * _.isSymbol(Symbol.iterator);
3534
+ * // => true
3535
+ *
3536
+ * _.isSymbol('abc');
3537
+ * // => false
3538
+ */
3539
+ function isSymbol$3(value) {
3540
+ return typeof value == 'symbol' || isObjectLike(value) && baseGetTag$1(value) == symbolTag;
3541
+ }
3542
+ var isSymbol_1 = isSymbol$3;
3543
+ var isArray$2 = isArray_1,
3544
+ isSymbol$2 = isSymbol_1;
3545
+
3546
+ /** Used to match property names within property paths. */
3547
+ var reIsDeepProp = /\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\\]|\\.)*?\1)\]/,
3548
+ reIsPlainProp = /^\w*$/;
3549
+
3550
+ /**
3551
+ * Checks if `value` is a property name and not a property path.
3552
+ *
3553
+ * @private
3554
+ * @param {*} value The value to check.
3555
+ * @param {Object} [object] The object to query keys on.
3556
+ * @returns {boolean} Returns `true` if `value` is a property name, else `false`.
3557
+ */
3558
+ function isKey$1(value, object) {
3559
+ if (isArray$2(value)) {
3560
+ return false;
3561
+ }
3562
+ var type = typeof value;
3563
+ if (type == 'number' || type == 'symbol' || type == 'boolean' || value == null || isSymbol$2(value)) {
3564
+ return true;
3565
+ }
3566
+ return reIsPlainProp.test(value) || !reIsDeepProp.test(value) || object != null && value in Object(object);
3169
3567
  }
3170
- function isContext(block) {
3171
- return block._type === "sanity.ai.prompt.context";
3568
+ var _isKey = isKey$1;
3569
+
3570
+ /**
3571
+ * Checks if `value` is the
3572
+ * [language type](http://www.ecma-international.org/ecma-262/7.0/#sec-ecmascript-language-types)
3573
+ * of `Object`. (e.g. arrays, functions, objects, regexes, `new Number(0)`, and `new String('')`)
3574
+ *
3575
+ * @static
3576
+ * @memberOf _
3577
+ * @since 0.1.0
3578
+ * @category Lang
3579
+ * @param {*} value The value to check.
3580
+ * @returns {boolean} Returns `true` if `value` is an object, else `false`.
3581
+ * @example
3582
+ *
3583
+ * _.isObject({});
3584
+ * // => true
3585
+ *
3586
+ * _.isObject([1, 2, 3]);
3587
+ * // => true
3588
+ *
3589
+ * _.isObject(_.noop);
3590
+ * // => true
3591
+ *
3592
+ * _.isObject(null);
3593
+ * // => false
3594
+ */
3595
+
3596
+ function isObject$2(value) {
3597
+ var type = typeof value;
3598
+ return value != null && (type == 'object' || type == 'function');
3172
3599
  }
3173
- function isUserInput(block) {
3174
- return block._type === "sanity.ai.prompt.userInput";
3600
+ var isObject_1 = isObject$2;
3601
+ var baseGetTag = _baseGetTag,
3602
+ isObject$1 = isObject_1;
3603
+
3604
+ /** `Object#toString` result references. */
3605
+ var asyncTag = '[object AsyncFunction]',
3606
+ funcTag = '[object Function]',
3607
+ genTag = '[object GeneratorFunction]',
3608
+ proxyTag = '[object Proxy]';
3609
+
3610
+ /**
3611
+ * Checks if `value` is classified as a `Function` object.
3612
+ *
3613
+ * @static
3614
+ * @memberOf _
3615
+ * @since 0.1.0
3616
+ * @category Lang
3617
+ * @param {*} value The value to check.
3618
+ * @returns {boolean} Returns `true` if `value` is a function, else `false`.
3619
+ * @example
3620
+ *
3621
+ * _.isFunction(_);
3622
+ * // => true
3623
+ *
3624
+ * _.isFunction(/abc/);
3625
+ * // => false
3626
+ */
3627
+ function isFunction$1(value) {
3628
+ if (!isObject$1(value)) {
3629
+ return false;
3630
+ }
3631
+ // The use of `Object#toString` avoids issues with the `typeof` operator
3632
+ // in Safari 9 which returns 'object' for typed arrays and other constructors.
3633
+ var tag = baseGetTag(value);
3634
+ return tag == funcTag || tag == genTag || tag == asyncTag || tag == proxyTag;
3175
3635
  }
3176
- function isSpan(block) {
3177
- return block._type === "span";
3636
+ var isFunction_1 = isFunction$1;
3637
+ var root$1 = _root;
3638
+
3639
+ /** Used to detect overreaching core-js shims. */
3640
+ var coreJsData$1 = root$1['__core-js_shared__'];
3641
+ var _coreJsData = coreJsData$1;
3642
+ var coreJsData = _coreJsData;
3643
+
3644
+ /** Used to detect methods masquerading as native. */
3645
+ var maskSrcKey = function () {
3646
+ var uid = /[^.]+$/.exec(coreJsData && coreJsData.keys && coreJsData.keys.IE_PROTO || '');
3647
+ return uid ? 'Symbol(src)_1.' + uid : '';
3648
+ }();
3649
+
3650
+ /**
3651
+ * Checks if `func` has its source masked.
3652
+ *
3653
+ * @private
3654
+ * @param {Function} func The function to check.
3655
+ * @returns {boolean} Returns `true` if `func` is masked, else `false`.
3656
+ */
3657
+ function isMasked$1(func) {
3658
+ return !!maskSrcKey && maskSrcKey in func;
3659
+ }
3660
+ var _isMasked = isMasked$1;
3661
+
3662
+ /** Used for built-in method references. */
3663
+
3664
+ var funcProto$1 = Function.prototype;
3665
+
3666
+ /** Used to resolve the decompiled source of functions. */
3667
+ var funcToString$1 = funcProto$1.toString;
3668
+
3669
+ /**
3670
+ * Converts `func` to its source code.
3671
+ *
3672
+ * @private
3673
+ * @param {Function} func The function to convert.
3674
+ * @returns {string} Returns the source code.
3675
+ */
3676
+ function toSource$1(func) {
3677
+ if (func != null) {
3678
+ try {
3679
+ return funcToString$1.call(func);
3680
+ } catch (e) {}
3681
+ try {
3682
+ return func + '';
3683
+ } catch (e) {}
3684
+ }
3685
+ return '';
3178
3686
  }
3179
- function mapBlock(block, migratedContexts) {
3180
- var _a, _b, _c, _d;
3181
- if (isFieldRef(block)) {
3182
- return {
3183
- ...block,
3184
- _type: fieldReferenceTypeName
3185
- };
3687
+ var _toSource = toSource$1;
3688
+ var isFunction = isFunction_1,
3689
+ isMasked = _isMasked,
3690
+ isObject = isObject_1,
3691
+ toSource = _toSource;
3692
+
3693
+ /**
3694
+ * Used to match `RegExp`
3695
+ * [syntax characters](http://ecma-international.org/ecma-262/7.0/#sec-patterns).
3696
+ */
3697
+ var reRegExpChar = /[\\^$.*+?()[\]{}|]/g;
3698
+
3699
+ /** Used to detect host constructors (Safari). */
3700
+ var reIsHostCtor = /^\[object .+?Constructor\]$/;
3701
+
3702
+ /** Used for built-in method references. */
3703
+ var funcProto = Function.prototype,
3704
+ objectProto$2 = Object.prototype;
3705
+
3706
+ /** Used to resolve the decompiled source of functions. */
3707
+ var funcToString = funcProto.toString;
3708
+
3709
+ /** Used to check objects for own properties. */
3710
+ var hasOwnProperty$2 = objectProto$2.hasOwnProperty;
3711
+
3712
+ /** Used to detect if a method is native. */
3713
+ var reIsNative = RegExp('^' + funcToString.call(hasOwnProperty$2).replace(reRegExpChar, '\\$&').replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g, '$1.*?') + '$');
3714
+
3715
+ /**
3716
+ * The base implementation of `_.isNative` without bad shim checks.
3717
+ *
3718
+ * @private
3719
+ * @param {*} value The value to check.
3720
+ * @returns {boolean} Returns `true` if `value` is a native function,
3721
+ * else `false`.
3722
+ */
3723
+ function baseIsNative$1(value) {
3724
+ if (!isObject(value) || isMasked(value)) {
3725
+ return false;
3186
3726
  }
3187
- if (isUserInput(block)) {
3188
- return {
3189
- ...block,
3190
- _type: userInputTypeName
3191
- };
3727
+ var pattern = isFunction(value) ? reIsNative : reIsHostCtor;
3728
+ return pattern.test(toSource(value));
3729
+ }
3730
+ var _baseIsNative = baseIsNative$1;
3731
+
3732
+ /**
3733
+ * Gets the value at `key` of `object`.
3734
+ *
3735
+ * @private
3736
+ * @param {Object} [object] The object to query.
3737
+ * @param {string} key The key of the property to get.
3738
+ * @returns {*} Returns the property value.
3739
+ */
3740
+
3741
+ function getValue$1(object, key) {
3742
+ return object == null ? undefined : object[key];
3743
+ }
3744
+ var _getValue = getValue$1;
3745
+ var baseIsNative = _baseIsNative,
3746
+ getValue = _getValue;
3747
+
3748
+ /**
3749
+ * Gets the native function at `key` of `object`.
3750
+ *
3751
+ * @private
3752
+ * @param {Object} object The object to query.
3753
+ * @param {string} key The key of the method to get.
3754
+ * @returns {*} Returns the function if it's native, else `undefined`.
3755
+ */
3756
+ function getNative$2(object, key) {
3757
+ var value = getValue(object, key);
3758
+ return baseIsNative(value) ? value : undefined;
3759
+ }
3760
+ var _getNative = getNative$2;
3761
+ var getNative$1 = _getNative;
3762
+
3763
+ /* Built-in method references that are verified to be native. */
3764
+ var nativeCreate$4 = getNative$1(Object, 'create');
3765
+ var _nativeCreate = nativeCreate$4;
3766
+ var nativeCreate$3 = _nativeCreate;
3767
+
3768
+ /**
3769
+ * Removes all key-value entries from the hash.
3770
+ *
3771
+ * @private
3772
+ * @name clear
3773
+ * @memberOf Hash
3774
+ */
3775
+ function hashClear$1() {
3776
+ this.__data__ = nativeCreate$3 ? nativeCreate$3(null) : {};
3777
+ this.size = 0;
3778
+ }
3779
+ var _hashClear = hashClear$1;
3780
+
3781
+ /**
3782
+ * Removes `key` and its value from the hash.
3783
+ *
3784
+ * @private
3785
+ * @name delete
3786
+ * @memberOf Hash
3787
+ * @param {Object} hash The hash to modify.
3788
+ * @param {string} key The key of the value to remove.
3789
+ * @returns {boolean} Returns `true` if the entry was removed, else `false`.
3790
+ */
3791
+
3792
+ function hashDelete$1(key) {
3793
+ var result = this.has(key) && delete this.__data__[key];
3794
+ this.size -= result ? 1 : 0;
3795
+ return result;
3796
+ }
3797
+ var _hashDelete = hashDelete$1;
3798
+ var nativeCreate$2 = _nativeCreate;
3799
+
3800
+ /** Used to stand-in for `undefined` hash values. */
3801
+ var HASH_UNDEFINED$1 = '__lodash_hash_undefined__';
3802
+
3803
+ /** Used for built-in method references. */
3804
+ var objectProto$1 = Object.prototype;
3805
+
3806
+ /** Used to check objects for own properties. */
3807
+ var hasOwnProperty$1 = objectProto$1.hasOwnProperty;
3808
+
3809
+ /**
3810
+ * Gets the hash value for `key`.
3811
+ *
3812
+ * @private
3813
+ * @name get
3814
+ * @memberOf Hash
3815
+ * @param {string} key The key of the value to get.
3816
+ * @returns {*} Returns the entry value.
3817
+ */
3818
+ function hashGet$1(key) {
3819
+ var data = this.__data__;
3820
+ if (nativeCreate$2) {
3821
+ var result = data[key];
3822
+ return result === HASH_UNDEFINED$1 ? undefined : result;
3192
3823
  }
3193
- if (isContext(block)) {
3194
- const newBlock = {
3195
- ...block,
3196
- _type: instructionContextTypeName,
3197
- reference: {
3198
- _type: "reference",
3199
- _ref: (_c = (_a = migratedContexts.find(c => {
3200
- var _a2;
3201
- return c._alphaId === ((_a2 = block.reference) == null ? void 0 : _a2._ref);
3202
- })) == null ? void 0 : _a._id) != null ? _c : (_b = block.reference) == null ? void 0 : _b._ref
3203
- }
3204
- };
3205
- return newBlock;
3824
+ return hasOwnProperty$1.call(data, key) ? data[key] : undefined;
3825
+ }
3826
+ var _hashGet = hashGet$1;
3827
+ var nativeCreate$1 = _nativeCreate;
3828
+
3829
+ /** Used for built-in method references. */
3830
+ var objectProto = Object.prototype;
3831
+
3832
+ /** Used to check objects for own properties. */
3833
+ var hasOwnProperty = objectProto.hasOwnProperty;
3834
+
3835
+ /**
3836
+ * Checks if a hash value for `key` exists.
3837
+ *
3838
+ * @private
3839
+ * @name has
3840
+ * @memberOf Hash
3841
+ * @param {string} key The key of the entry to check.
3842
+ * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
3843
+ */
3844
+ function hashHas$1(key) {
3845
+ var data = this.__data__;
3846
+ return nativeCreate$1 ? data[key] !== undefined : hasOwnProperty.call(data, key);
3847
+ }
3848
+ var _hashHas = hashHas$1;
3849
+ var nativeCreate = _nativeCreate;
3850
+
3851
+ /** Used to stand-in for `undefined` hash values. */
3852
+ var HASH_UNDEFINED = '__lodash_hash_undefined__';
3853
+
3854
+ /**
3855
+ * Sets the hash `key` to `value`.
3856
+ *
3857
+ * @private
3858
+ * @name set
3859
+ * @memberOf Hash
3860
+ * @param {string} key The key of the value to set.
3861
+ * @param {*} value The value to set.
3862
+ * @returns {Object} Returns the hash instance.
3863
+ */
3864
+ function hashSet$1(key, value) {
3865
+ var data = this.__data__;
3866
+ this.size += this.has(key) ? 0 : 1;
3867
+ data[key] = nativeCreate && value === undefined ? HASH_UNDEFINED : value;
3868
+ return this;
3869
+ }
3870
+ var _hashSet = hashSet$1;
3871
+ var hashClear = _hashClear,
3872
+ hashDelete = _hashDelete,
3873
+ hashGet = _hashGet,
3874
+ hashHas = _hashHas,
3875
+ hashSet = _hashSet;
3876
+
3877
+ /**
3878
+ * Creates a hash object.
3879
+ *
3880
+ * @private
3881
+ * @constructor
3882
+ * @param {Array} [entries] The key-value pairs to cache.
3883
+ */
3884
+ function Hash$1(entries) {
3885
+ var index = -1,
3886
+ length = entries == null ? 0 : entries.length;
3887
+ this.clear();
3888
+ while (++index < length) {
3889
+ var entry = entries[index];
3890
+ this.set(entry[0], entry[1]);
3206
3891
  }
3207
- if (isSpan(block)) {
3208
- return block;
3892
+ }
3893
+
3894
+ // Add methods to `Hash`.
3895
+ Hash$1.prototype.clear = hashClear;
3896
+ Hash$1.prototype['delete'] = hashDelete;
3897
+ Hash$1.prototype.get = hashGet;
3898
+ Hash$1.prototype.has = hashHas;
3899
+ Hash$1.prototype.set = hashSet;
3900
+ var _Hash = Hash$1;
3901
+
3902
+ /**
3903
+ * Removes all key-value entries from the list cache.
3904
+ *
3905
+ * @private
3906
+ * @name clear
3907
+ * @memberOf ListCache
3908
+ */
3909
+
3910
+ function listCacheClear$1() {
3911
+ this.__data__ = [];
3912
+ this.size = 0;
3913
+ }
3914
+ var _listCacheClear = listCacheClear$1;
3915
+
3916
+ /**
3917
+ * Performs a
3918
+ * [`SameValueZero`](http://ecma-international.org/ecma-262/7.0/#sec-samevaluezero)
3919
+ * comparison between two values to determine if they are equivalent.
3920
+ *
3921
+ * @static
3922
+ * @memberOf _
3923
+ * @since 4.0.0
3924
+ * @category Lang
3925
+ * @param {*} value The value to compare.
3926
+ * @param {*} other The other value to compare.
3927
+ * @returns {boolean} Returns `true` if the values are equivalent, else `false`.
3928
+ * @example
3929
+ *
3930
+ * var object = { 'a': 1 };
3931
+ * var other = { 'a': 1 };
3932
+ *
3933
+ * _.eq(object, object);
3934
+ * // => true
3935
+ *
3936
+ * _.eq(object, other);
3937
+ * // => false
3938
+ *
3939
+ * _.eq('a', 'a');
3940
+ * // => true
3941
+ *
3942
+ * _.eq('a', Object('a'));
3943
+ * // => false
3944
+ *
3945
+ * _.eq(NaN, NaN);
3946
+ * // => true
3947
+ */
3948
+
3949
+ function eq$1(value, other) {
3950
+ return value === other || value !== value && other !== other;
3951
+ }
3952
+ var eq_1 = eq$1;
3953
+ var eq = eq_1;
3954
+
3955
+ /**
3956
+ * Gets the index at which the `key` is found in `array` of key-value pairs.
3957
+ *
3958
+ * @private
3959
+ * @param {Array} array The array to inspect.
3960
+ * @param {*} key The key to search for.
3961
+ * @returns {number} Returns the index of the matched value, else `-1`.
3962
+ */
3963
+ function assocIndexOf$4(array, key) {
3964
+ var length = array.length;
3965
+ while (length--) {
3966
+ if (eq(array[length][0], key)) {
3967
+ return length;
3968
+ }
3209
3969
  }
3210
- const textBlock = block;
3211
- return {
3212
- ...textBlock,
3213
- children: ((_d = textBlock.children) != null ? _d : []).map(child => mapBlock(child, migratedContexts))
3970
+ return -1;
3971
+ }
3972
+ var _assocIndexOf = assocIndexOf$4;
3973
+ var assocIndexOf$3 = _assocIndexOf;
3974
+
3975
+ /** Used for built-in method references. */
3976
+ var arrayProto = Array.prototype;
3977
+
3978
+ /** Built-in value references. */
3979
+ var splice = arrayProto.splice;
3980
+
3981
+ /**
3982
+ * Removes `key` and its value from the list cache.
3983
+ *
3984
+ * @private
3985
+ * @name delete
3986
+ * @memberOf ListCache
3987
+ * @param {string} key The key of the value to remove.
3988
+ * @returns {boolean} Returns `true` if the entry was removed, else `false`.
3989
+ */
3990
+ function listCacheDelete$1(key) {
3991
+ var data = this.__data__,
3992
+ index = assocIndexOf$3(data, key);
3993
+ if (index < 0) {
3994
+ return false;
3995
+ }
3996
+ var lastIndex = data.length - 1;
3997
+ if (index == lastIndex) {
3998
+ data.pop();
3999
+ } else {
4000
+ splice.call(data, index, 1);
4001
+ }
4002
+ --this.size;
4003
+ return true;
4004
+ }
4005
+ var _listCacheDelete = listCacheDelete$1;
4006
+ var assocIndexOf$2 = _assocIndexOf;
4007
+
4008
+ /**
4009
+ * Gets the list cache value for `key`.
4010
+ *
4011
+ * @private
4012
+ * @name get
4013
+ * @memberOf ListCache
4014
+ * @param {string} key The key of the value to get.
4015
+ * @returns {*} Returns the entry value.
4016
+ */
4017
+ function listCacheGet$1(key) {
4018
+ var data = this.__data__,
4019
+ index = assocIndexOf$2(data, key);
4020
+ return index < 0 ? undefined : data[index][1];
4021
+ }
4022
+ var _listCacheGet = listCacheGet$1;
4023
+ var assocIndexOf$1 = _assocIndexOf;
4024
+
4025
+ /**
4026
+ * Checks if a list cache value for `key` exists.
4027
+ *
4028
+ * @private
4029
+ * @name has
4030
+ * @memberOf ListCache
4031
+ * @param {string} key The key of the entry to check.
4032
+ * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
4033
+ */
4034
+ function listCacheHas$1(key) {
4035
+ return assocIndexOf$1(this.__data__, key) > -1;
4036
+ }
4037
+ var _listCacheHas = listCacheHas$1;
4038
+ var assocIndexOf = _assocIndexOf;
4039
+
4040
+ /**
4041
+ * Sets the list cache `key` to `value`.
4042
+ *
4043
+ * @private
4044
+ * @name set
4045
+ * @memberOf ListCache
4046
+ * @param {string} key The key of the value to set.
4047
+ * @param {*} value The value to set.
4048
+ * @returns {Object} Returns the list cache instance.
4049
+ */
4050
+ function listCacheSet$1(key, value) {
4051
+ var data = this.__data__,
4052
+ index = assocIndexOf(data, key);
4053
+ if (index < 0) {
4054
+ ++this.size;
4055
+ data.push([key, value]);
4056
+ } else {
4057
+ data[index][1] = value;
4058
+ }
4059
+ return this;
4060
+ }
4061
+ var _listCacheSet = listCacheSet$1;
4062
+ var listCacheClear = _listCacheClear,
4063
+ listCacheDelete = _listCacheDelete,
4064
+ listCacheGet = _listCacheGet,
4065
+ listCacheHas = _listCacheHas,
4066
+ listCacheSet = _listCacheSet;
4067
+
4068
+ /**
4069
+ * Creates an list cache object.
4070
+ *
4071
+ * @private
4072
+ * @constructor
4073
+ * @param {Array} [entries] The key-value pairs to cache.
4074
+ */
4075
+ function ListCache$1(entries) {
4076
+ var index = -1,
4077
+ length = entries == null ? 0 : entries.length;
4078
+ this.clear();
4079
+ while (++index < length) {
4080
+ var entry = entries[index];
4081
+ this.set(entry[0], entry[1]);
4082
+ }
4083
+ }
4084
+
4085
+ // Add methods to `ListCache`.
4086
+ ListCache$1.prototype.clear = listCacheClear;
4087
+ ListCache$1.prototype['delete'] = listCacheDelete;
4088
+ ListCache$1.prototype.get = listCacheGet;
4089
+ ListCache$1.prototype.has = listCacheHas;
4090
+ ListCache$1.prototype.set = listCacheSet;
4091
+ var _ListCache = ListCache$1;
4092
+ var getNative = _getNative,
4093
+ root = _root;
4094
+
4095
+ /* Built-in method references that are verified to be native. */
4096
+ var Map$2 = getNative(root, 'Map');
4097
+ var _Map = Map$2;
4098
+ var Hash = _Hash,
4099
+ ListCache = _ListCache,
4100
+ Map$1 = _Map;
4101
+
4102
+ /**
4103
+ * Removes all key-value entries from the map.
4104
+ *
4105
+ * @private
4106
+ * @name clear
4107
+ * @memberOf MapCache
4108
+ */
4109
+ function mapCacheClear$1() {
4110
+ this.size = 0;
4111
+ this.__data__ = {
4112
+ 'hash': new Hash(),
4113
+ 'map': new (Map$1 || ListCache)(),
4114
+ 'string': new Hash()
3214
4115
  };
3215
4116
  }
3216
- function AssistLayout(props) {
3217
- var _a;
3218
- const [connectors, setConnectors] = react.useState([]);
3219
- const migrate = (_a = props.config.alphaMigration) != null ? _a : true;
3220
- return /* @__PURE__ */jsxRuntime.jsxs(AiAssistanceConfigProvider, {
3221
- config: props.config,
3222
- children: [migrate ? /* @__PURE__ */jsxRuntime.jsx(AlphaMigration, {}) : null, /* @__PURE__ */jsxRuntime.jsx(RunInstructionProvider, {
3223
- children: /* @__PURE__ */jsxRuntime.jsxs(ConnectorsProvider, {
3224
- onConnectorsChange: setConnectors,
3225
- children: [props.renderDefault(props), /* @__PURE__ */jsxRuntime.jsx(ui.ThemeProvider, {
3226
- tone: "default",
3227
- children: /* @__PURE__ */jsxRuntime.jsx(AssistConnectorsOverlay, {
3228
- connectors
4117
+ var _mapCacheClear = mapCacheClear$1;
4118
+
4119
+ /**
4120
+ * Checks if `value` is suitable for use as unique object key.
4121
+ *
4122
+ * @private
4123
+ * @param {*} value The value to check.
4124
+ * @returns {boolean} Returns `true` if `value` is suitable, else `false`.
4125
+ */
4126
+
4127
+ function isKeyable$1(value) {
4128
+ var type = typeof value;
4129
+ return type == 'string' || type == 'number' || type == 'symbol' || type == 'boolean' ? value !== '__proto__' : value === null;
4130
+ }
4131
+ var _isKeyable = isKeyable$1;
4132
+ var isKeyable = _isKeyable;
4133
+
4134
+ /**
4135
+ * Gets the data for `map`.
4136
+ *
4137
+ * @private
4138
+ * @param {Object} map The map to query.
4139
+ * @param {string} key The reference key.
4140
+ * @returns {*} Returns the map data.
4141
+ */
4142
+ function getMapData$4(map, key) {
4143
+ var data = map.__data__;
4144
+ return isKeyable(key) ? data[typeof key == 'string' ? 'string' : 'hash'] : data.map;
4145
+ }
4146
+ var _getMapData = getMapData$4;
4147
+ var getMapData$3 = _getMapData;
4148
+
4149
+ /**
4150
+ * Removes `key` and its value from the map.
4151
+ *
4152
+ * @private
4153
+ * @name delete
4154
+ * @memberOf MapCache
4155
+ * @param {string} key The key of the value to remove.
4156
+ * @returns {boolean} Returns `true` if the entry was removed, else `false`.
4157
+ */
4158
+ function mapCacheDelete$1(key) {
4159
+ var result = getMapData$3(this, key)['delete'](key);
4160
+ this.size -= result ? 1 : 0;
4161
+ return result;
4162
+ }
4163
+ var _mapCacheDelete = mapCacheDelete$1;
4164
+ var getMapData$2 = _getMapData;
4165
+
4166
+ /**
4167
+ * Gets the map value for `key`.
4168
+ *
4169
+ * @private
4170
+ * @name get
4171
+ * @memberOf MapCache
4172
+ * @param {string} key The key of the value to get.
4173
+ * @returns {*} Returns the entry value.
4174
+ */
4175
+ function mapCacheGet$1(key) {
4176
+ return getMapData$2(this, key).get(key);
4177
+ }
4178
+ var _mapCacheGet = mapCacheGet$1;
4179
+ var getMapData$1 = _getMapData;
4180
+
4181
+ /**
4182
+ * Checks if a map value for `key` exists.
4183
+ *
4184
+ * @private
4185
+ * @name has
4186
+ * @memberOf MapCache
4187
+ * @param {string} key The key of the entry to check.
4188
+ * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
4189
+ */
4190
+ function mapCacheHas$1(key) {
4191
+ return getMapData$1(this, key).has(key);
4192
+ }
4193
+ var _mapCacheHas = mapCacheHas$1;
4194
+ var getMapData = _getMapData;
4195
+
4196
+ /**
4197
+ * Sets the map `key` to `value`.
4198
+ *
4199
+ * @private
4200
+ * @name set
4201
+ * @memberOf MapCache
4202
+ * @param {string} key The key of the value to set.
4203
+ * @param {*} value The value to set.
4204
+ * @returns {Object} Returns the map cache instance.
4205
+ */
4206
+ function mapCacheSet$1(key, value) {
4207
+ var data = getMapData(this, key),
4208
+ size = data.size;
4209
+ data.set(key, value);
4210
+ this.size += data.size == size ? 0 : 1;
4211
+ return this;
4212
+ }
4213
+ var _mapCacheSet = mapCacheSet$1;
4214
+ var mapCacheClear = _mapCacheClear,
4215
+ mapCacheDelete = _mapCacheDelete,
4216
+ mapCacheGet = _mapCacheGet,
4217
+ mapCacheHas = _mapCacheHas,
4218
+ mapCacheSet = _mapCacheSet;
4219
+
4220
+ /**
4221
+ * Creates a map cache object to store key-value pairs.
4222
+ *
4223
+ * @private
4224
+ * @constructor
4225
+ * @param {Array} [entries] The key-value pairs to cache.
4226
+ */
4227
+ function MapCache$1(entries) {
4228
+ var index = -1,
4229
+ length = entries == null ? 0 : entries.length;
4230
+ this.clear();
4231
+ while (++index < length) {
4232
+ var entry = entries[index];
4233
+ this.set(entry[0], entry[1]);
4234
+ }
4235
+ }
4236
+
4237
+ // Add methods to `MapCache`.
4238
+ MapCache$1.prototype.clear = mapCacheClear;
4239
+ MapCache$1.prototype['delete'] = mapCacheDelete;
4240
+ MapCache$1.prototype.get = mapCacheGet;
4241
+ MapCache$1.prototype.has = mapCacheHas;
4242
+ MapCache$1.prototype.set = mapCacheSet;
4243
+ var _MapCache = MapCache$1;
4244
+ var MapCache = _MapCache;
4245
+
4246
+ /** Error message constants. */
4247
+ var FUNC_ERROR_TEXT = 'Expected a function';
4248
+
4249
+ /**
4250
+ * Creates a function that memoizes the result of `func`. If `resolver` is
4251
+ * provided, it determines the cache key for storing the result based on the
4252
+ * arguments provided to the memoized function. By default, the first argument
4253
+ * provided to the memoized function is used as the map cache key. The `func`
4254
+ * is invoked with the `this` binding of the memoized function.
4255
+ *
4256
+ * **Note:** The cache is exposed as the `cache` property on the memoized
4257
+ * function. Its creation may be customized by replacing the `_.memoize.Cache`
4258
+ * constructor with one whose instances implement the
4259
+ * [`Map`](http://ecma-international.org/ecma-262/7.0/#sec-properties-of-the-map-prototype-object)
4260
+ * method interface of `clear`, `delete`, `get`, `has`, and `set`.
4261
+ *
4262
+ * @static
4263
+ * @memberOf _
4264
+ * @since 0.1.0
4265
+ * @category Function
4266
+ * @param {Function} func The function to have its output memoized.
4267
+ * @param {Function} [resolver] The function to resolve the cache key.
4268
+ * @returns {Function} Returns the new memoized function.
4269
+ * @example
4270
+ *
4271
+ * var object = { 'a': 1, 'b': 2 };
4272
+ * var other = { 'c': 3, 'd': 4 };
4273
+ *
4274
+ * var values = _.memoize(_.values);
4275
+ * values(object);
4276
+ * // => [1, 2]
4277
+ *
4278
+ * values(other);
4279
+ * // => [3, 4]
4280
+ *
4281
+ * object.a = 2;
4282
+ * values(object);
4283
+ * // => [1, 2]
4284
+ *
4285
+ * // Modify the result cache.
4286
+ * values.cache.set(object, ['a', 'b']);
4287
+ * values(object);
4288
+ * // => ['a', 'b']
4289
+ *
4290
+ * // Replace `_.memoize.Cache`.
4291
+ * _.memoize.Cache = WeakMap;
4292
+ */
4293
+ function memoize$1(func, resolver) {
4294
+ if (typeof func != 'function' || resolver != null && typeof resolver != 'function') {
4295
+ throw new TypeError(FUNC_ERROR_TEXT);
4296
+ }
4297
+ var memoized = function () {
4298
+ var args = arguments,
4299
+ key = resolver ? resolver.apply(this, args) : args[0],
4300
+ cache = memoized.cache;
4301
+ if (cache.has(key)) {
4302
+ return cache.get(key);
4303
+ }
4304
+ var result = func.apply(this, args);
4305
+ memoized.cache = cache.set(key, result) || cache;
4306
+ return result;
4307
+ };
4308
+ memoized.cache = new (memoize$1.Cache || MapCache)();
4309
+ return memoized;
4310
+ }
4311
+
4312
+ // Expose `MapCache`.
4313
+ memoize$1.Cache = MapCache;
4314
+ var memoize_1 = memoize$1;
4315
+ var memoize = memoize_1;
4316
+
4317
+ /** Used as the maximum memoize cache size. */
4318
+ var MAX_MEMOIZE_SIZE = 500;
4319
+
4320
+ /**
4321
+ * A specialized version of `_.memoize` which clears the memoized function's
4322
+ * cache when it exceeds `MAX_MEMOIZE_SIZE`.
4323
+ *
4324
+ * @private
4325
+ * @param {Function} func The function to have its output memoized.
4326
+ * @returns {Function} Returns the new memoized function.
4327
+ */
4328
+ function memoizeCapped$1(func) {
4329
+ var result = memoize(func, function (key) {
4330
+ if (cache.size === MAX_MEMOIZE_SIZE) {
4331
+ cache.clear();
4332
+ }
4333
+ return key;
4334
+ });
4335
+ var cache = result.cache;
4336
+ return result;
4337
+ }
4338
+ var _memoizeCapped = memoizeCapped$1;
4339
+ var memoizeCapped = _memoizeCapped;
4340
+
4341
+ /** Used to match property names within property paths. */
4342
+ var rePropName = /[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\\]|\\.)*?)\2)\]|(?=(?:\.|\[\])(?:\.|\[\]|$))/g;
4343
+
4344
+ /** Used to match backslashes in property paths. */
4345
+ var reEscapeChar = /\\(\\)?/g;
4346
+
4347
+ /**
4348
+ * Converts `string` to a property path array.
4349
+ *
4350
+ * @private
4351
+ * @param {string} string The string to convert.
4352
+ * @returns {Array} Returns the property path array.
4353
+ */
4354
+ var stringToPath$1 = memoizeCapped(function (string) {
4355
+ var result = [];
4356
+ if (string.charCodeAt(0) === 46 /* . */) {
4357
+ result.push('');
4358
+ }
4359
+ string.replace(rePropName, function (match, number, quote, subString) {
4360
+ result.push(quote ? subString.replace(reEscapeChar, '$1') : number || match);
4361
+ });
4362
+ return result;
4363
+ });
4364
+ var _stringToPath = stringToPath$1;
4365
+
4366
+ /**
4367
+ * A specialized version of `_.map` for arrays without support for iteratee
4368
+ * shorthands.
4369
+ *
4370
+ * @private
4371
+ * @param {Array} [array] The array to iterate over.
4372
+ * @param {Function} iteratee The function invoked per iteration.
4373
+ * @returns {Array} Returns the new mapped array.
4374
+ */
4375
+
4376
+ function arrayMap$1(array, iteratee) {
4377
+ var index = -1,
4378
+ length = array == null ? 0 : array.length,
4379
+ result = Array(length);
4380
+ while (++index < length) {
4381
+ result[index] = iteratee(array[index], index, array);
4382
+ }
4383
+ return result;
4384
+ }
4385
+ var _arrayMap = arrayMap$1;
4386
+ var Symbol = _Symbol,
4387
+ arrayMap = _arrayMap,
4388
+ isArray$1 = isArray_1,
4389
+ isSymbol$1 = isSymbol_1;
4390
+
4391
+ /** Used as references for various `Number` constants. */
4392
+ var INFINITY$1 = 1 / 0;
4393
+
4394
+ /** Used to convert symbols to primitives and strings. */
4395
+ var symbolProto = Symbol ? Symbol.prototype : undefined,
4396
+ symbolToString = symbolProto ? symbolProto.toString : undefined;
4397
+
4398
+ /**
4399
+ * The base implementation of `_.toString` which doesn't convert nullish
4400
+ * values to empty strings.
4401
+ *
4402
+ * @private
4403
+ * @param {*} value The value to process.
4404
+ * @returns {string} Returns the string.
4405
+ */
4406
+ function baseToString$1(value) {
4407
+ // Exit early for strings to avoid a performance hit in some environments.
4408
+ if (typeof value == 'string') {
4409
+ return value;
4410
+ }
4411
+ if (isArray$1(value)) {
4412
+ // Recursively convert values (susceptible to call stack limits).
4413
+ return arrayMap(value, baseToString$1) + '';
4414
+ }
4415
+ if (isSymbol$1(value)) {
4416
+ return symbolToString ? symbolToString.call(value) : '';
4417
+ }
4418
+ var result = value + '';
4419
+ return result == '0' && 1 / value == -INFINITY$1 ? '-0' : result;
4420
+ }
4421
+ var _baseToString = baseToString$1;
4422
+ var baseToString = _baseToString;
4423
+
4424
+ /**
4425
+ * Converts `value` to a string. An empty string is returned for `null`
4426
+ * and `undefined` values. The sign of `-0` is preserved.
4427
+ *
4428
+ * @static
4429
+ * @memberOf _
4430
+ * @since 4.0.0
4431
+ * @category Lang
4432
+ * @param {*} value The value to convert.
4433
+ * @returns {string} Returns the converted string.
4434
+ * @example
4435
+ *
4436
+ * _.toString(null);
4437
+ * // => ''
4438
+ *
4439
+ * _.toString(-0);
4440
+ * // => '-0'
4441
+ *
4442
+ * _.toString([1, 2, 3]);
4443
+ * // => '1,2,3'
4444
+ */
4445
+ function toString$1(value) {
4446
+ return value == null ? '' : baseToString(value);
4447
+ }
4448
+ var toString_1 = toString$1;
4449
+ var isArray = isArray_1,
4450
+ isKey = _isKey,
4451
+ stringToPath = _stringToPath,
4452
+ toString = toString_1;
4453
+
4454
+ /**
4455
+ * Casts `value` to a path array if it's not one.
4456
+ *
4457
+ * @private
4458
+ * @param {*} value The value to inspect.
4459
+ * @param {Object} [object] The object to query keys on.
4460
+ * @returns {Array} Returns the cast property path array.
4461
+ */
4462
+ function castPath$1(value, object) {
4463
+ if (isArray(value)) {
4464
+ return value;
4465
+ }
4466
+ return isKey(value, object) ? [value] : stringToPath(toString(value));
4467
+ }
4468
+ var _castPath = castPath$1;
4469
+ var isSymbol = isSymbol_1;
4470
+
4471
+ /** Used as references for various `Number` constants. */
4472
+ var INFINITY = 1 / 0;
4473
+
4474
+ /**
4475
+ * Converts `value` to a string key if it's not a string or symbol.
4476
+ *
4477
+ * @private
4478
+ * @param {*} value The value to inspect.
4479
+ * @returns {string|symbol} Returns the key.
4480
+ */
4481
+ function toKey$1(value) {
4482
+ if (typeof value == 'string' || isSymbol(value)) {
4483
+ return value;
4484
+ }
4485
+ var result = value + '';
4486
+ return result == '0' && 1 / value == -INFINITY ? '-0' : result;
4487
+ }
4488
+ var _toKey = toKey$1;
4489
+ var castPath = _castPath,
4490
+ toKey = _toKey;
4491
+
4492
+ /**
4493
+ * The base implementation of `_.get` without support for default values.
4494
+ *
4495
+ * @private
4496
+ * @param {Object} object The object to query.
4497
+ * @param {Array|string} path The path of the property to get.
4498
+ * @returns {*} Returns the resolved value.
4499
+ */
4500
+ function baseGet$1(object, path) {
4501
+ path = castPath(path, object);
4502
+ var index = 0,
4503
+ length = path.length;
4504
+ while (object != null && index < length) {
4505
+ object = object[toKey(path[index++])];
4506
+ }
4507
+ return index && index == length ? object : undefined;
4508
+ }
4509
+ var _baseGet = baseGet$1;
4510
+ var baseGet = _baseGet;
4511
+
4512
+ /**
4513
+ * Gets the value at `path` of `object`. If the resolved value is
4514
+ * `undefined`, the `defaultValue` is returned in its place.
4515
+ *
4516
+ * @static
4517
+ * @memberOf _
4518
+ * @since 3.7.0
4519
+ * @category Object
4520
+ * @param {Object} object The object to query.
4521
+ * @param {Array|string} path The path of the property to get.
4522
+ * @param {*} [defaultValue] The value returned for `undefined` resolved values.
4523
+ * @returns {*} Returns the resolved value.
4524
+ * @example
4525
+ *
4526
+ * var object = { 'a': [{ 'b': { 'c': 3 } }] };
4527
+ *
4528
+ * _.get(object, 'a[0].b.c');
4529
+ * // => 3
4530
+ *
4531
+ * _.get(object, ['a', '0', 'b', 'c']);
4532
+ * // => 3
4533
+ *
4534
+ * _.get(object, 'a.b.c', 'default');
4535
+ * // => 'default'
4536
+ */
4537
+ function get(object, path, defaultValue) {
4538
+ var result = object == null ? undefined : baseGet(object, path);
4539
+ return result === undefined ? defaultValue : result;
4540
+ }
4541
+ var get_1 = get;
4542
+ var get$1 = /*@__PURE__*/getDefaultExportFromCjs(get_1);
4543
+ const getLanguageParams = (select, document) => {
4544
+ if (!select || !document) {
4545
+ return {};
4546
+ }
4547
+ const selection = select || {};
4548
+ const selectedValue = {};
4549
+ for (const [key, path] of Object.entries(selection)) {
4550
+ let value = get$1(document, path);
4551
+ if (Array.isArray(value)) {
4552
+ value = value.filter(item => typeof item === "object" ? (item == null ? void 0 : item._type) !== "reference" || "_ref" in item : true);
4553
+ }
4554
+ selectedValue[key] = value;
4555
+ }
4556
+ return selectedValue;
4557
+ };
4558
+ const toFieldLanguagesKeyPrefix = "sanityStudio:assist:field-languages:from:";
4559
+ function getPreferredToFieldLanguages(fromLanguageId) {
4560
+ if (typeof localStorage === "undefined") {
4561
+ return [];
4562
+ }
4563
+ const value = localStorage.getItem("".concat(toFieldLanguagesKeyPrefix).concat(fromLanguageId));
4564
+ return value ? JSON.parse(value) : [];
4565
+ }
4566
+ function setPreferredToFieldLanguages(fromLanguageId, languageIds) {
4567
+ if (typeof localStorage === "undefined") {
4568
+ return;
4569
+ }
4570
+ localStorage.setItem("".concat(toFieldLanguagesKeyPrefix).concat(fromLanguageId), JSON.stringify(languageIds));
4571
+ }
4572
+ const FieldTranslationContext = react.createContext({
4573
+ openFieldTranslation: () => {},
4574
+ translationLoading: false
4575
+ });
4576
+ function useFieldTranslation() {
4577
+ return react.useContext(FieldTranslationContext);
4578
+ }
4579
+ function hasValuesToTranslate(fieldLanguageMaps, fromLanguage, basePath) {
4580
+ return fieldLanguageMaps == null ? void 0 : fieldLanguageMaps.some(map => map.inputLanguageId === (fromLanguage == null ? void 0 : fromLanguage.id) && map.inputPath && sanity.pathToString(map.inputPath).startsWith(sanity.pathToString(basePath)));
4581
+ }
4582
+ function FieldTranslationProvider(props) {
4583
+ var _a, _b, _c;
4584
+ const {
4585
+ config: assistConfig
4586
+ } = useAiAssistanceConfig();
4587
+ const apiClient = useApiClient(assistConfig.__customApiClient);
4588
+ const config = (_a = assistConfig.translate) == null ? void 0 : _a.field;
4589
+ const {
4590
+ translate: runTranslate
4591
+ } = useTranslate(apiClient);
4592
+ const [dialogOpen, setDialogOpen] = react.useState(false);
4593
+ const [fieldTranslationParams, setFieldTranslationParams] = react.useState();
4594
+ const [languages, setLanguages] = react.useState();
4595
+ const [fromLanguage, setFromLanguage] = react.useState(void 0);
4596
+ const [toLanguages, setToLanguages] = react.useState(void 0);
4597
+ const [fieldLanguageMaps, setFieldLanguageMaps] = react.useState();
4598
+ const close = react.useCallback(() => {
4599
+ setDialogOpen(false);
4600
+ setLanguages(void 0);
4601
+ setFieldTranslationParams(void 0);
4602
+ }, []);
4603
+ const languageClient = sanity.useClient({
4604
+ apiVersion: (_b = config == null ? void 0 : config.apiVersion) != null ? _b : "2022-11-27"
4605
+ });
4606
+ const documentId = (_c = fieldTranslationParams == null ? void 0 : fieldTranslationParams.document) == null ? void 0 : _c._id;
4607
+ const id = react.useId();
4608
+ const selectFromLanguage = react.useCallback((from, languages2, params) => {
4609
+ var _a2, _b2;
4610
+ const {
4611
+ document,
4612
+ documentSchema
4613
+ } = params != null ? params : {};
4614
+ setFromLanguage(from);
4615
+ if (!document || !documentSchema || !params || !languages2) {
4616
+ setFieldLanguageMaps(void 0);
4617
+ return;
4618
+ }
4619
+ const preferred = getPreferredToFieldLanguages(from.id);
4620
+ const allToLanguages = languages2.filter(l => l.id !== (from == null ? void 0 : from.id));
4621
+ const filteredToLanguages = allToLanguages.filter(l => !preferred.length || preferred.includes(l.id));
4622
+ setToLanguages(filteredToLanguages);
4623
+ const fromId = from == null ? void 0 : from.id;
4624
+ const allToIds = (_a2 = allToLanguages == null ? void 0 : allToLanguages.map(l => l.id)) != null ? _a2 : [];
4625
+ const docMembers = getDocumentMembersFlat(document, documentSchema);
4626
+ if (fromId && (allToIds == null ? void 0 : allToIds.length)) {
4627
+ const transMap = getFieldLanguageMap(documentSchema, docMembers, fromId, allToIds.filter(toId => fromId !== toId), (_b2 = config == null ? void 0 : config.translationOutputs) != null ? _b2 : defaultLanguageOutputs);
4628
+ setFieldLanguageMaps(transMap);
4629
+ } else {
4630
+ setFieldLanguageMaps(void 0);
4631
+ }
4632
+ }, [config]);
4633
+ const toggleToLanguage = react.useCallback((toggledLang, toLanguages2, languages2) => {
4634
+ if (!languages2 || !fromLanguage) {
4635
+ return;
4636
+ }
4637
+ const wasSelected = !!(toLanguages2 == null ? void 0 : toLanguages2.find(l => l.id === toggledLang.id));
4638
+ const newToLangs = languages2.filter(anyLang => !!(toLanguages2 == null ? void 0 : toLanguages2.find(selectedLang => toggledLang.id !== selectedLang.id && selectedLang.id === anyLang.id)) || toggledLang.id === anyLang.id && !wasSelected);
4639
+ setToLanguages(newToLangs);
4640
+ setPreferredToFieldLanguages(fromLanguage.id, newToLangs.map(l => l.id));
4641
+ }, [fromLanguage]);
4642
+ const openFieldTranslation = react.useCallback(async params => {
4643
+ setDialogOpen(true);
4644
+ const languageParams = getLanguageParams(config == null ? void 0 : config.selectLanguageParams, params.document);
4645
+ const languages2 = await (typeof (config == null ? void 0 : config.languages) === "function" ? config == null ? void 0 : config.languages(languageClient, languageParams) : Promise.resolve(config == null ? void 0 : config.languages));
4646
+ setLanguages(languages2);
4647
+ setFieldTranslationParams(params);
4648
+ const fromLanguage2 = languages2 == null ? void 0 : languages2[0];
4649
+ if (fromLanguage2) {
4650
+ selectFromLanguage(fromLanguage2, languages2, params);
4651
+ } else {
4652
+ console.error("No languages available for selected language params", languageParams);
4653
+ }
4654
+ }, [selectFromLanguage, config, languageClient]);
4655
+ const contextValue = react.useMemo(() => {
4656
+ return {
4657
+ openFieldTranslation,
4658
+ translationLoading: false
4659
+ };
4660
+ }, [openFieldTranslation]);
4661
+ const runDisabled = !fromLanguage || !(toLanguages == null ? void 0 : toLanguages.length) || !(fieldLanguageMaps == null ? void 0 : fieldLanguageMaps.length) || !documentId || !hasValuesToTranslate(fieldLanguageMaps, fromLanguage, fieldTranslationParams.translatePath);
4662
+ const onRunTranslation = react.useCallback(() => {
4663
+ const translatePath = fieldTranslationParams == null ? void 0 : fieldTranslationParams.translatePath;
4664
+ if (fieldLanguageMaps && documentId && translatePath) {
4665
+ runTranslate({
4666
+ documentId,
4667
+ translatePath,
4668
+ fieldLanguageMap: fieldLanguageMaps.map(map => ({
4669
+ ...map,
4670
+ // eslint-disable-next-line max-nested-callbacks
4671
+ outputs: map.outputs.filter(out => !!(toLanguages == null ? void 0 : toLanguages.find(l => l.id === out.id)))
4672
+ })),
4673
+ conditionalMembers: fieldTranslationParams == null ? void 0 : fieldTranslationParams.conditionalMembers
4674
+ });
4675
+ }
4676
+ close();
4677
+ }, [fieldLanguageMaps, documentId, runTranslate, close, toLanguages, fieldTranslationParams == null ? void 0 : fieldTranslationParams.translatePath, fieldTranslationParams == null ? void 0 : fieldTranslationParams.conditionalMembers]);
4678
+ const runButton = /* @__PURE__ */jsxRuntime.jsx(ui.Button, {
4679
+ text: "Translate",
4680
+ tone: "primary",
4681
+ icon: icons.PlayIcon,
4682
+ style: {
4683
+ width: "100%"
4684
+ },
4685
+ disabled: runDisabled,
4686
+ onClick: onRunTranslation
4687
+ });
4688
+ return /* @__PURE__ */jsxRuntime.jsxs(FieldTranslationContext.Provider, {
4689
+ value: contextValue,
4690
+ children: [dialogOpen ? /* @__PURE__ */jsxRuntime.jsx(ui.Dialog, {
4691
+ id,
4692
+ width: 1,
4693
+ open: dialogOpen,
4694
+ onClose: close,
4695
+ header: "Translate fields",
4696
+ footer: /* @__PURE__ */jsxRuntime.jsx(ui.Flex, {
4697
+ justify: "space-between",
4698
+ padding: 2,
4699
+ flex: 1,
4700
+ children: runDisabled ? /* @__PURE__ */jsxRuntime.jsx(ui.Tooltip, {
4701
+ content: /* @__PURE__ */jsxRuntime.jsx(ui.Flex, {
4702
+ padding: 2,
4703
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
4704
+ children: "There is nothing to translate in the selected from-language."
4705
+ })
4706
+ }),
4707
+ placement: "top",
4708
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Flex, {
4709
+ flex: 1,
4710
+ children: runButton
3229
4711
  })
4712
+ }) : runButton
4713
+ }),
4714
+ children: languages ? /* @__PURE__ */jsxRuntime.jsxs(ui.Flex, {
4715
+ padding: 4,
4716
+ gap: 5,
4717
+ align: "flex-start",
4718
+ justify: "center",
4719
+ children: [/* @__PURE__ */jsxRuntime.jsxs(ui.Stack, {
4720
+ space: 2,
4721
+ children: [/* @__PURE__ */jsxRuntime.jsx(ui.Box, {
4722
+ marginBottom: 2,
4723
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
4724
+ weight: "semibold",
4725
+ children: "From"
4726
+ })
4727
+ }), languages == null ? void 0 : languages.map(radioLanguage => /* @__PURE__ */jsxRuntime.jsx(FromLanguageRadio, {
4728
+ ...{
4729
+ radioLanguage,
4730
+ fromLanguage,
4731
+ selectFromLanguage,
4732
+ languages,
4733
+ fieldTranslationParams
4734
+ }
4735
+ }, radioLanguage.id))]
4736
+ }), /* @__PURE__ */jsxRuntime.jsxs(ui.Stack, {
4737
+ space: 2,
4738
+ children: [/* @__PURE__ */jsxRuntime.jsx(ui.Box, {
4739
+ marginBottom: 2,
4740
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
4741
+ weight: "semibold",
4742
+ children: "To"
4743
+ })
4744
+ }), languages.map(checkboxLanguage => /* @__PURE__ */jsxRuntime.jsx(ToLanguageCheckbox, {
4745
+ ...{
4746
+ checkboxLanguage,
4747
+ fromLanguage,
4748
+ toLanguages,
4749
+ toggleToLanguage,
4750
+ languages
4751
+ }
4752
+ }, checkboxLanguage.id))]
4753
+ })]
4754
+ }) : /* @__PURE__ */jsxRuntime.jsxs(ui.Flex, {
4755
+ padding: 4,
4756
+ gap: 2,
4757
+ align: "flex-start",
4758
+ justify: "center",
4759
+ children: [/* @__PURE__ */jsxRuntime.jsx(ui.Box, {
4760
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Spinner, {})
4761
+ }), /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
4762
+ children: "Loading languages..."
3230
4763
  })]
3231
4764
  })
4765
+ }) : null, props.children]
4766
+ });
4767
+ }
4768
+ function ToLanguageCheckbox(props) {
4769
+ var _a;
4770
+ const {
4771
+ checkboxLanguage,
4772
+ fromLanguage,
4773
+ toLanguages,
4774
+ toggleToLanguage,
4775
+ languages
4776
+ } = props;
4777
+ const langId = checkboxLanguage.id;
4778
+ const onChange = react.useCallback(() => toggleToLanguage(checkboxLanguage, toLanguages, languages), [toggleToLanguage, checkboxLanguage, toLanguages, languages]);
4779
+ return /* @__PURE__ */jsxRuntime.jsxs(ui.Flex, {
4780
+ gap: 3,
4781
+ align: "center",
4782
+ as: "label",
4783
+ style: langId === (fromLanguage == null ? void 0 : fromLanguage.id) ? {
4784
+ opacity: 0.5
4785
+ } : void 0,
4786
+ children: [/* @__PURE__ */jsxRuntime.jsx(ui.Checkbox, {
4787
+ name: "toLang",
4788
+ value: langId,
4789
+ checked: langId !== (fromLanguage == null ? void 0 : fromLanguage.id) && !!(toLanguages == null ? void 0 : toLanguages.find(tl => tl.id === langId)),
4790
+ onChange,
4791
+ disabled: langId === (fromLanguage == null ? void 0 : fromLanguage.id)
4792
+ }), /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
4793
+ muted: langId === (fromLanguage == null ? void 0 : fromLanguage.id),
4794
+ children: (_a = checkboxLanguage.title) != null ? _a : langId
3232
4795
  })]
4796
+ }, langId);
4797
+ }
4798
+ function FromLanguageRadio(props) {
4799
+ var _a;
4800
+ const {
4801
+ languages,
4802
+ radioLanguage,
4803
+ selectFromLanguage,
4804
+ fromLanguage,
4805
+ fieldTranslationParams
4806
+ } = props;
4807
+ const langId = radioLanguage.id;
4808
+ const onChange = react.useCallback(() => selectFromLanguage(radioLanguage, languages, fieldTranslationParams), [selectFromLanguage, radioLanguage, languages, fieldTranslationParams]);
4809
+ return /* @__PURE__ */jsxRuntime.jsxs(ui.Flex, {
4810
+ gap: 3,
4811
+ align: "center",
4812
+ as: "label",
4813
+ children: [/* @__PURE__ */jsxRuntime.jsx(ui.Radio, {
4814
+ name: "fromLang",
4815
+ value: langId,
4816
+ checked: langId === (fromLanguage == null ? void 0 : fromLanguage.id),
4817
+ onChange
4818
+ }), /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
4819
+ children: (_a = radioLanguage.title) != null ? _a : radioLanguage.id
4820
+ })]
4821
+ }, langId);
4822
+ }
4823
+ function AssistLayout(props) {
4824
+ const [connectors, setConnectors] = react.useState([]);
4825
+ return /* @__PURE__ */jsxRuntime.jsx(AiAssistanceConfigProvider, {
4826
+ config: props.config,
4827
+ children: /* @__PURE__ */jsxRuntime.jsx(RunInstructionProvider, {
4828
+ children: /* @__PURE__ */jsxRuntime.jsx(FieldTranslationProvider, {
4829
+ children: /* @__PURE__ */jsxRuntime.jsxs(ConnectorsProvider, {
4830
+ onConnectorsChange: setConnectors,
4831
+ children: [props.renderDefault(props), /* @__PURE__ */jsxRuntime.jsx(ui.ThemeProvider, {
4832
+ tone: "default",
4833
+ children: /* @__PURE__ */jsxRuntime.jsx(AssistConnectorsOverlay, {
4834
+ connectors
4835
+ })
4836
+ })]
4837
+ })
4838
+ })
4839
+ })
3233
4840
  });
3234
4841
  }
3235
4842
  var __freeze$1 = Object.freeze;
@@ -3255,7 +4862,10 @@ function ErrorWrapper(props) {
3255
4862
  const catchError = react.useCallback(params => {
3256
4863
  setError(params.error);
3257
4864
  }, [setError]);
3258
- const unsetValue = react.useCallback(() => onChange(sanity.PatchEvent.from(sanity.unset())), [onChange]);
4865
+ const unsetValue = react.useCallback(() => {
4866
+ onChange(sanity.PatchEvent.from(sanity.unset()));
4867
+ setError(void 0);
4868
+ }, [onChange]);
3259
4869
  const dismiss = react.useCallback(() => setError(void 0), []);
3260
4870
  const catcher = /* @__PURE__ */jsxRuntime.jsx(ui.ErrorBoundary, {
3261
4871
  onCatch: catchError,
@@ -3323,6 +4933,7 @@ function AssistFormBlock(props) {
3323
4933
  _key: key
3324
4934
  }));
3325
4935
  }, [onChange, key]);
4936
+ const singlePresence = presence[0];
3326
4937
  return /* @__PURE__ */jsxRuntime.jsx(ErrorWrapper, {
3327
4938
  onChange: localOnChange,
3328
4939
  children: /* @__PURE__ */jsxRuntime.jsxs(ui.Flex, {
@@ -3331,9 +4942,9 @@ function AssistFormBlock(props) {
3331
4942
  children: [/* @__PURE__ */jsxRuntime.jsx(ui.Box, {
3332
4943
  flex: 1,
3333
4944
  children: props.renderDefault(props)
3334
- }), presence.map(pre => /* @__PURE__ */jsxRuntime.jsx(AiFieldPresence, {
3335
- presence: pre
3336
- }, pre.lastActiveAt))]
4945
+ }), singlePresence && /* @__PURE__ */jsxRuntime.jsx(AiFieldPresence, {
4946
+ presence: singlePresence
4947
+ })]
3337
4948
  })
3338
4949
  });
3339
4950
  }
@@ -3377,16 +4988,24 @@ function InstructionInput(props) {
3377
4988
  ...props
3378
4989
  }), /* @__PURE__ */jsxRuntime.jsx(ShareField, {
3379
4990
  ...props
3380
- }), /* @__PURE__ */jsxRuntime.jsx(PromptField, {
4991
+ }), /* @__PURE__ */jsxRuntime.jsx(ObjectMember, {
4992
+ fieldName: "prompt",
4993
+ ...props
4994
+ }), /* @__PURE__ */jsxRuntime.jsx(ObjectMember, {
4995
+ fieldName: "output",
3381
4996
  ...props
3382
4997
  })]
3383
4998
  });
3384
4999
  }
3385
- function PromptField(props) {
3386
- const promptMember = findFieldMember(props.members, "prompt");
3387
- return promptMember ? /* @__PURE__ */jsxRuntime.jsx(sanity.ObjectInputMember, {
5000
+ function ObjectMember(_ref13) {
5001
+ let {
5002
+ fieldName,
5003
+ ...props
5004
+ } = _ref13;
5005
+ const member = findFieldMember(props.members, fieldName);
5006
+ return member ? /* @__PURE__ */jsxRuntime.jsx(sanity.ObjectInputMember, {
3388
5007
  ...props,
3389
- member: promptMember
5008
+ member
3390
5009
  }) : null;
3391
5010
  }
3392
5011
  const NONE = [];
@@ -3521,8 +5140,8 @@ function IconInput(props) {
3521
5140
  onChange
3522
5141
  } = props;
3523
5142
  const id = react.useId();
3524
- const items = react.useMemo(() => Object.entries(icons.icons).map(_ref10 => {
3525
- let [key, icon] = _ref10;
5143
+ const items = react.useMemo(() => Object.entries(icons.icons).map(_ref14 => {
5144
+ let [key, icon] = _ref14;
3526
5145
  return /* @__PURE__ */jsxRuntime.jsx(IconItem, {
3527
5146
  iconKey: key,
3528
5147
  icon,
@@ -3550,12 +5169,12 @@ function IconInput(props) {
3550
5169
  }
3551
5170
  });
3552
5171
  }
3553
- function IconItem(_ref11) {
5172
+ function IconItem(_ref15) {
3554
5173
  let {
3555
5174
  icon,
3556
5175
  iconKey: key,
3557
5176
  onChange
3558
- } = _ref11;
5177
+ } = _ref15;
3559
5178
  const onClick = react.useCallback(() => onChange(sanity.set(key)), [onChange, key]);
3560
5179
  return /* @__PURE__ */jsxRuntime.jsx(ui.MenuItem, {
3561
5180
  icon,
@@ -3566,8 +5185,8 @@ function IconItem(_ref11) {
3566
5185
  }
3567
5186
  function getIcon(iconName) {
3568
5187
  var _a, _b;
3569
- return (_b = (_a = Object.entries(icons.icons).find(_ref12 => {
3570
- let [key] = _ref12;
5188
+ return (_b = (_a = Object.entries(icons.icons).find(_ref16 => {
5189
+ let [key] = _ref16;
3571
5190
  return key === iconName;
3572
5191
  })) == null ? void 0 : _a[1]) != null ? _b : icons.icons.sparkles;
3573
5192
  }
@@ -3726,11 +5345,11 @@ const contextDocumentSchema = sanity.defineType({
3726
5345
  title: "title",
3727
5346
  context: "context"
3728
5347
  },
3729
- prepare(_ref13) {
5348
+ prepare(_ref17) {
3730
5349
  let {
3731
5350
  title,
3732
5351
  context
3733
- } = _ref13;
5352
+ } = _ref17;
3734
5353
  var _a;
3735
5354
  const text = context == null ? void 0 : context.flatMap(block => block == null ? void 0 : block.children).flatMap(child => {
3736
5355
  var _a2;
@@ -3749,7 +5368,11 @@ const contextDocumentSchema = sanity.defineType({
3749
5368
  // Strict ESM env, designed to run outside Node.js in envs that provide WebCrypto (deno, browsers, etc)
3750
5369
 
3751
5370
  function getRandomValues(typedArray) {
3752
- return window.crypto.getRandomValues(typedArray);
5371
+ const crypto = typeof window !== 'undefined' && 'crypto' in window ? window.crypto : globalThis.crypto;
5372
+ if (!crypto || !crypto.getRandomValues) {
5373
+ throw new Error('WebCrypto not available in this environment');
5374
+ }
5375
+ return crypto.getRandomValues(typedArray);
3753
5376
  }
3754
5377
  function whatwgRNG() {
3755
5378
  let length = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 16;
@@ -3816,10 +5439,204 @@ function InstructionsArrayField(props) {
3816
5439
  title: " "
3817
5440
  });
3818
5441
  }
5442
+ function InstructionOutputField(props) {
5443
+ var _a;
5444
+ const {
5445
+ fieldSchema
5446
+ } = (_a = react.useContext(SelectedFieldContext)) != null ? _a : {};
5447
+ if (!fieldSchema || !(sanity.isObjectSchemaType(fieldSchema) || sanity.isArrayOfObjectsSchemaType(fieldSchema))) {
5448
+ return null;
5449
+ }
5450
+ return /* @__PURE__ */jsxRuntime.jsx(EnabledOutputField, {
5451
+ ...props,
5452
+ fieldSchema,
5453
+ children: props.children
5454
+ });
5455
+ }
5456
+ function EnabledOutputField(_ref18) {
5457
+ let {
5458
+ fieldSchema,
5459
+ ...props
5460
+ } = _ref18;
5461
+ var _a;
5462
+ const [open, setOpen] = react.useState(!!((_a = props.value) == null ? void 0 : _a.length));
5463
+ const onExpand = react.useCallback(() => setOpen(true), []);
5464
+ const onCollapse = react.useCallback(() => setOpen(false), []);
5465
+ return props.renderDefault({
5466
+ ...props,
5467
+ collapsible: true,
5468
+ onExpand,
5469
+ onCollapse,
5470
+ collapsed: !open,
5471
+ level: 1,
5472
+ title: sanity.isObjectSchemaType(fieldSchema) ? "Allowed fields" : "Allowed types"
5473
+ });
5474
+ }
5475
+ function InstructionOutputInput(props) {
5476
+ var _a;
5477
+ const {
5478
+ fieldSchema
5479
+ } = (_a = react.useContext(SelectedFieldContext)) != null ? _a : {};
5480
+ if (!fieldSchema) {
5481
+ return null;
5482
+ }
5483
+ if (sanity.isObjectSchemaType(fieldSchema)) {
5484
+ return /* @__PURE__ */jsxRuntime.jsx(ObjectOutputInput, {
5485
+ ...props,
5486
+ fieldSchema
5487
+ });
5488
+ }
5489
+ if (sanity.isArrayOfObjectsSchemaType(fieldSchema)) {
5490
+ return /* @__PURE__ */jsxRuntime.jsx(ArrayOutputInput, {
5491
+ ...props,
5492
+ fieldSchema
5493
+ });
5494
+ }
5495
+ return null;
5496
+ }
5497
+ function useEmptySelectAllValue(value, allowedValues, onChange) {
5498
+ react.useEffect(() => {
5499
+ var _a, _b;
5500
+ const validValues = value == null ? void 0 : value.filter(v => allowedValues.find(f => f.name === (v._type === outputFieldTypeName ? v.relativePath : v.type)));
5501
+ const valueLength = (_a = value == null ? void 0 : value.length) != null ? _a : 0;
5502
+ const validLength = (_b = validValues == null ? void 0 : validValues.length) != null ? _b : 0;
5503
+ if (!validLength && valueLength || validLength >= allowedValues.length) {
5504
+ onChange(sanity.PatchEvent.from([sanity.unset()]));
5505
+ }
5506
+ }, [allowedValues, value, onChange]);
5507
+ }
5508
+ function ObjectOutputInput(_ref19) {
5509
+ let {
5510
+ fieldSchema,
5511
+ ...props
5512
+ } = _ref19;
5513
+ const {
5514
+ value,
5515
+ onChange
5516
+ } = props;
5517
+ const fields = react.useMemo(() => fieldSchema.fields.filter(field => isAssistSupported(field.type)), [fieldSchema.fields]);
5518
+ useEmptySelectAllValue(value, fields, onChange);
5519
+ const onSelectChange = react.useCallback((checked, selectedValue) => {
5520
+ if (checked) {
5521
+ if (value == null ? void 0 : value.length) {
5522
+ onChange(sanity.PatchEvent.from(sanity.unset([{
5523
+ _key: selectedValue
5524
+ }])));
5525
+ } else {
5526
+ const items = fields.filter(f => f.name !== selectedValue).map(field => sanity.typed({
5527
+ _key: field.name,
5528
+ _type: "sanity.assist.output.field",
5529
+ relativePath: field.name
5530
+ }));
5531
+ onChange(sanity.PatchEvent.from([sanity.setIfMissing([]), sanity.insert(items, "after", [-1])]));
5532
+ }
5533
+ } else {
5534
+ const patchValue = {
5535
+ _key: selectedValue,
5536
+ _type: "sanity.assist.output.field",
5537
+ relativePath: selectedValue
5538
+ };
5539
+ onChange(sanity.PatchEvent.from([sanity.setIfMissing([]), sanity.insert([patchValue], "after", [-1])]));
5540
+ }
5541
+ }, [onChange, value, fields]);
5542
+ return /* @__PURE__ */jsxRuntime.jsx(ui.Stack, {
5543
+ space: 2,
5544
+ children: fields.map(field => {
5545
+ var _a;
5546
+ return /* @__PURE__ */jsxRuntime.jsx(ui.Flex, {
5547
+ align: "center",
5548
+ gap: 2,
5549
+ children: /* @__PURE__ */jsxRuntime.jsx(Selectable, {
5550
+ value: field.name,
5551
+ title: (_a = field.type.title) != null ? _a : field.name,
5552
+ arrayValue: value,
5553
+ onChange: onSelectChange
5554
+ })
5555
+ }, field.name);
5556
+ })
5557
+ });
5558
+ }
5559
+ function ArrayOutputInput(_ref20) {
5560
+ let {
5561
+ fieldSchema,
5562
+ ...props
5563
+ } = _ref20;
5564
+ const {
5565
+ value,
5566
+ onChange
5567
+ } = props;
5568
+ const ofItems = react.useMemo(() => fieldSchema.of.filter(itemType => isAssistSupported(itemType)), [fieldSchema.of]);
5569
+ useEmptySelectAllValue(value, ofItems, onChange);
5570
+ const onSelectChange = react.useCallback((checked, selectedValue) => {
5571
+ if (checked) {
5572
+ if (value == null ? void 0 : value.length) {
5573
+ onChange(sanity.PatchEvent.from(sanity.unset([{
5574
+ _key: selectedValue
5575
+ }])));
5576
+ } else {
5577
+ const items = ofItems.filter(f => f.name !== selectedValue).map(field => sanity.typed({
5578
+ _key: field.name,
5579
+ _type: "sanity.assist.output.type",
5580
+ type: field.name
5581
+ }));
5582
+ onChange(sanity.PatchEvent.from([sanity.setIfMissing([]), sanity.insert(items, "after", [-1])]));
5583
+ }
5584
+ } else {
5585
+ const patchValue = {
5586
+ _key: selectedValue,
5587
+ _type: "sanity.assist.output.type",
5588
+ type: selectedValue
5589
+ };
5590
+ onChange(sanity.PatchEvent.from([sanity.setIfMissing([]), sanity.insert([patchValue], "after", [-1])]));
5591
+ }
5592
+ }, [onChange, value, ofItems]);
5593
+ return /* @__PURE__ */jsxRuntime.jsx(ui.Stack, {
5594
+ space: 2,
5595
+ children: ofItems.map(itemType => {
5596
+ var _a;
5597
+ return /* @__PURE__ */jsxRuntime.jsx(ui.Flex, {
5598
+ children: /* @__PURE__ */jsxRuntime.jsx(Selectable, {
5599
+ value: itemType.name,
5600
+ title: isType(itemType, "block") ? "Text" : (_a = itemType.title) != null ? _a : itemType.name,
5601
+ arrayValue: value,
5602
+ onChange: onSelectChange
5603
+ })
5604
+ }, itemType.name);
5605
+ })
5606
+ });
5607
+ }
5608
+ function Selectable(_ref21) {
5609
+ let {
5610
+ title,
5611
+ arrayValue,
5612
+ value,
5613
+ onChange
5614
+ } = _ref21;
5615
+ const checked = !(arrayValue == null ? void 0 : arrayValue.length) || !!(arrayValue == null ? void 0 : arrayValue.find(v => v._key === value));
5616
+ const handleChange = react.useCallback(() => onChange(checked, value), [onChange, checked, value]);
5617
+ return /* @__PURE__ */jsxRuntime.jsxs(ui.Flex, {
5618
+ gap: 2,
5619
+ align: "flex-start",
5620
+ children: [/* @__PURE__ */jsxRuntime.jsx(ui.Checkbox, {
5621
+ checked,
5622
+ onChange: handleChange
5623
+ }), /* @__PURE__ */jsxRuntime.jsx(ui.Card, {
5624
+ marginTop: 1,
5625
+ onClick: handleChange,
5626
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Text, {
5627
+ style: {
5628
+ cursor: "default"
5629
+ },
5630
+ size: 1,
5631
+ children: title
5632
+ })
5633
+ })]
5634
+ });
5635
+ }
3819
5636
  const fieldReference = sanity.defineType({
3820
5637
  type: "object",
3821
5638
  name: fieldReferenceTypeName,
3822
- title: "Document field",
5639
+ title: "Field",
3823
5640
  icon: icons.ThListIcon,
3824
5641
  fields: [sanity.defineField({
3825
5642
  type: "string",
@@ -3859,10 +5676,10 @@ const fieldReference = sanity.defineType({
3859
5676
  select: {
3860
5677
  path: "path"
3861
5678
  },
3862
- prepare(_ref14) {
5679
+ prepare(_ref22) {
3863
5680
  let {
3864
5681
  path
3865
- } = _ref14;
5682
+ } = _ref22;
3866
5683
  return {
3867
5684
  title: path,
3868
5685
  path,
@@ -4007,12 +5824,12 @@ const instruction = sanity.defineType({
4007
5824
  title: "title",
4008
5825
  userId: "userId"
4009
5826
  },
4010
- prepare: _ref15 => {
5827
+ prepare: _ref23 => {
4011
5828
  let {
4012
5829
  icon,
4013
5830
  title,
4014
5831
  userId
4015
- } = _ref15;
5832
+ } = _ref23;
4016
5833
  return {
4017
5834
  title,
4018
5835
  icon: icon ? icons.icons[icon] : icons.SparklesIcon,
@@ -4117,6 +5934,33 @@ const instruction = sanity.defineType({
4117
5934
  var _a, _b;
4118
5935
  return (_b = (_a = context.currentUser) == null ? void 0 : _a.id) != null ? _b : "";
4119
5936
  }
5937
+ }), sanity.defineField({
5938
+ type: "array",
5939
+ name: "output",
5940
+ title: "Output filter",
5941
+ components: {
5942
+ input: InstructionOutputInput,
5943
+ field: InstructionOutputField
5944
+ },
5945
+ of: [sanity.defineArrayMember({
5946
+ type: "object",
5947
+ name: outputFieldTypeName,
5948
+ title: "Output field",
5949
+ fields: [{
5950
+ type: "string",
5951
+ name: "path",
5952
+ title: "Path"
5953
+ }]
5954
+ }), sanity.defineArrayMember({
5955
+ type: "object",
5956
+ name: outputTypeTypeName,
5957
+ title: "Output type",
5958
+ fields: [{
5959
+ type: "string",
5960
+ name: "type",
5961
+ title: "Type"
5962
+ }]
5963
+ })]
4120
5964
  })]
4121
5965
  });
4122
5966
  const fieldInstructions = sanity.defineType({
@@ -4333,7 +6177,7 @@ function PrivateIcon() {
4333
6177
  children: /* @__PURE__ */jsxRuntime.jsx(icons.LockIcon, {})
4334
6178
  });
4335
6179
  }
4336
- const ImageContext = react.createContext(void 0);
6180
+ const ImageContext = react.createContext({});
4337
6181
  function ImageContextProvider(props) {
4338
6182
  var _a;
4339
6183
  const {
@@ -4348,7 +6192,8 @@ function ImageContextProvider(props) {
4348
6192
  documentSchemaType
4349
6193
  } = useAssistDocumentContext();
4350
6194
  const {
4351
- config
6195
+ config,
6196
+ status
4352
6197
  } = useAiAssistanceConfig();
4353
6198
  const apiClient = useApiClient(config == null ? void 0 : config.__customApiClient);
4354
6199
  const {
@@ -4358,28 +6203,30 @@ function ImageContextProvider(props) {
4358
6203
  isSyncing
4359
6204
  } = sanity.useSyncState(publicId(documentId), documentSchemaType.name);
4360
6205
  react.useEffect(() => {
4361
- const captionField = getCaptionFieldOption(schemaType);
4362
- if (assetRef && documentId && captionField && assetRef !== assetRefState && !isSyncing) {
6206
+ const descriptionField = getDescriptionFieldOption(schemaType);
6207
+ if (assetRef && documentId && descriptionField && assetRef !== assetRefState && !isSyncing && canUseAssist(status)) {
4363
6208
  setAssetRefState(assetRef);
4364
6209
  generateCaption({
4365
- path: sanity.pathToString([...path, captionField]),
6210
+ path: sanity.pathToString([...path, descriptionField]),
4366
6211
  documentId
4367
6212
  });
4368
6213
  }
4369
- }, [schemaType, path, assetRef, assetRefState, documentId, generateCaption, isSyncing]);
6214
+ }, [schemaType, path, assetRef, assetRefState, documentId, generateCaption, isSyncing, status]);
4370
6215
  const context = react.useMemo(() => {
4371
- const captionField = getCaptionFieldOption(schemaType);
4372
- return captionField ? {
4373
- captionPath: sanity.pathToString([...path, captionField]),
6216
+ const descriptionField = getDescriptionFieldOption(schemaType);
6217
+ const imageInstructionField = getImageInstructionFieldOption(schemaType);
6218
+ return {
6219
+ imageDescriptionPath: descriptionField ? sanity.pathToString([...path, descriptionField]) : void 0,
6220
+ imageInstructionPath: imageInstructionField ? sanity.pathToString([...path, imageInstructionField]) : void 0,
4374
6221
  assetRef
4375
- } : void 0;
6222
+ };
4376
6223
  }, [schemaType, path, assetRef]);
4377
6224
  return /* @__PURE__ */jsxRuntime.jsx(ImageContext.Provider, {
4378
6225
  value: context,
4379
6226
  children: props.renderDefault(props)
4380
6227
  });
4381
6228
  }
4382
- function node$1(node2) {
6229
+ function node$3(node2) {
4383
6230
  return node2;
4384
6231
  }
4385
6232
  const generateCaptionsActions = {
@@ -4387,7 +6234,11 @@ const generateCaptionsActions = {
4387
6234
  useAction(props) {
4388
6235
  const pathKey = usePathKey(props.path);
4389
6236
  const {
4390
- config
6237
+ openInspector
6238
+ } = desk.useDocumentPane();
6239
+ const {
6240
+ config,
6241
+ status
4391
6242
  } = useAiAssistanceConfig();
4392
6243
  const apiClient = useApiClient(config == null ? void 0 : config.__customApiClient);
4393
6244
  const {
@@ -4395,12 +6246,12 @@ const generateCaptionsActions = {
4395
6246
  loading
4396
6247
  } = useGenerateCaption(apiClient);
4397
6248
  const imageContext = react.useContext(ImageContext);
4398
- if (imageContext && pathKey === (imageContext == null ? void 0 : imageContext.captionPath)) {
6249
+ if (imageContext && pathKey === (imageContext == null ? void 0 : imageContext.imageDescriptionPath)) {
4399
6250
  const {
4400
6251
  documentId
4401
6252
  } = useAssistDocumentContext();
4402
6253
  return react.useMemo(() => {
4403
- return node$1({
6254
+ return node$3({
4404
6255
  type: "action",
4405
6256
  icon: loading ? () => /* @__PURE__ */jsxRuntime.jsx(ui.Box, {
4406
6257
  style: {
@@ -4412,11 +6263,18 @@ const generateCaptionsActions = {
4412
6263
  }
4413
6264
  })
4414
6265
  }) : icons.ImageIcon,
4415
- title: "Generate caption",
6266
+ title: "Generate image description",
4416
6267
  onAction: () => {
4417
6268
  if (loading) {
4418
6269
  return;
4419
6270
  }
6271
+ if (!canUseAssist(status)) {
6272
+ openInspector(aiInspectorId, {
6273
+ [fieldPathParam]: pathKey,
6274
+ [instructionParam]: void 0
6275
+ });
6276
+ return;
6277
+ }
4420
6278
  generateCaption({
4421
6279
  path: pathKey,
4422
6280
  documentId: documentId != null ? documentId : ""
@@ -4426,7 +6284,186 @@ const generateCaptionsActions = {
4426
6284
  disabled: loading,
4427
6285
  hidden: !imageContext.assetRef
4428
6286
  });
4429
- }, [generateCaption, pathKey, documentId, loading, imageContext]);
6287
+ }, [generateCaption, pathKey, documentId, loading, imageContext, status, openInspector]);
6288
+ }
6289
+ return void 0;
6290
+ }
6291
+ };
6292
+ function node$2(node2) {
6293
+ return node2;
6294
+ }
6295
+ const translateActions = {
6296
+ name: "sanity-assist-translate",
6297
+ useAction(props) {
6298
+ var _a, _b, _c, _d, _e, _f, _g, _h;
6299
+ const {
6300
+ config,
6301
+ status
6302
+ } = useAiAssistanceConfig();
6303
+ const apiClient = useApiClient(config == null ? void 0 : config.__customApiClient);
6304
+ const {
6305
+ schemaType: fieldSchemaType,
6306
+ path,
6307
+ documentId,
6308
+ documentSchemaType,
6309
+ documentIsAssistable
6310
+ } = props;
6311
+ const isDocumentLevel = path.length === 0;
6312
+ const readOnly = fieldSchemaType.readOnly === true;
6313
+ const docTransTypes = (_b = (_a = config.translate) == null ? void 0 : _a.document) == null ? void 0 : _b.documentTypes;
6314
+ const options = fieldSchemaType == null ? void 0 : fieldSchemaType.options;
6315
+ const addFieldAction = isDocumentLevel || ((_c = options == null ? void 0 : options.aiAssist) == null ? void 0 : _c.translateAction);
6316
+ const fieldTransEnabled = addFieldAction && documentSchemaType && ((_f = (_e = (_d = config.translate) == null ? void 0 : _d.field) == null ? void 0 : _e.documentTypes) == null ? void 0 : _f.includes(documentSchemaType.name));
6317
+ const documentTranslationEnabled = addFieldAction && documentSchemaType && (!docTransTypes && isAssistSupported(fieldSchemaType) || (docTransTypes == null ? void 0 : docTransTypes.includes(documentSchemaType.name)));
6318
+ if (documentSchemaType && (documentTranslationEnabled || fieldTransEnabled)) {
6319
+ const {
6320
+ value: documentValue,
6321
+ onChange: documentOnChange,
6322
+ formState
6323
+ } = desk.useDocumentPane();
6324
+ const docRef = react.useRef(documentValue);
6325
+ docRef.current = documentValue;
6326
+ const formStateRef = react.useRef(formState);
6327
+ formStateRef.current = formState;
6328
+ const translationApi = useTranslate(apiClient);
6329
+ const translate = useDraftDelayedTask({
6330
+ documentOnChange,
6331
+ isDocAssistable: documentIsAssistable != null ? documentIsAssistable : false,
6332
+ task: translationApi.translate
6333
+ });
6334
+ const languagePath = (_h = (_g = config.translate) == null ? void 0 : _g.document) == null ? void 0 : _h.languageField;
6335
+ const translateDocumentAction = react.useMemo(() => {
6336
+ if (!languagePath || !documentTranslationEnabled) {
6337
+ return void 0;
6338
+ }
6339
+ const title = path.length ? "Translate" : "Translate document";
6340
+ return node$2({
6341
+ type: "action",
6342
+ icon: translationApi.loading ? () => /* @__PURE__ */jsxRuntime.jsx(ui.Box, {
6343
+ style: {
6344
+ height: 17
6345
+ },
6346
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Spinner, {
6347
+ style: {
6348
+ transform: "translateY(6px)"
6349
+ }
6350
+ })
6351
+ }) : icons.TranslateIcon,
6352
+ title,
6353
+ onAction: () => {
6354
+ if (translationApi.loading || !languagePath || !documentId) {
6355
+ return;
6356
+ }
6357
+ translate({
6358
+ languagePath,
6359
+ translatePath: path,
6360
+ documentId: documentId != null ? documentId : "",
6361
+ conditionalMembers: formStateRef.current ? getConditionalMembers(formStateRef.current) : []
6362
+ });
6363
+ },
6364
+ renderAsButton: true,
6365
+ disabled: translationApi.loading || readOnly
6366
+ });
6367
+ }, [languagePath, translate, documentId, translationApi.loading, documentTranslationEnabled, path, readOnly]);
6368
+ const fieldTranslate = useFieldTranslation();
6369
+ const openFieldTranslation = useDraftDelayedTask({
6370
+ documentOnChange,
6371
+ isDocAssistable: documentIsAssistable != null ? documentIsAssistable : false,
6372
+ task: fieldTranslate.openFieldTranslation
6373
+ });
6374
+ const translateFieldsAction = react.useMemo(() => fieldTransEnabled ? node$2({
6375
+ type: "action",
6376
+ icon: fieldTranslate.translationLoading ? () => /* @__PURE__ */jsxRuntime.jsx(ui.Box, {
6377
+ style: {
6378
+ height: 17
6379
+ },
6380
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Spinner, {
6381
+ style: {
6382
+ transform: "translateY(6px)"
6383
+ }
6384
+ })
6385
+ }) : icons.TranslateIcon,
6386
+ title: "Translate fields...",
6387
+ onAction: () => {
6388
+ if (fieldTranslate.translationLoading || !documentId) {
6389
+ return;
6390
+ }
6391
+ if (formStateRef.current) {
6392
+ getConditionalMembers(formStateRef.current);
6393
+ }
6394
+ openFieldTranslation({
6395
+ document: docRef.current,
6396
+ documentSchema: documentSchemaType,
6397
+ translatePath: path,
6398
+ conditionalMembers: formStateRef.current ? getConditionalMembers(formStateRef.current) : []
6399
+ });
6400
+ },
6401
+ renderAsButton: true,
6402
+ disabled: fieldTranslate.translationLoading || readOnly
6403
+ }) : void 0, [openFieldTranslation, documentSchemaType, documentId, fieldTranslate.translationLoading, fieldTransEnabled, path, readOnly]);
6404
+ return react.useMemo(() => {
6405
+ if (!(status == null ? void 0 : status.initialized)) {
6406
+ return void 0;
6407
+ }
6408
+ return node$2({
6409
+ type: "group",
6410
+ icon: () => null,
6411
+ title: "Translation",
6412
+ children: [translateDocumentAction, translateFieldsAction].filter(c => !!c),
6413
+ expanded: true
6414
+ });
6415
+ }, [translateDocumentAction, translateFieldsAction, status]);
6416
+ }
6417
+ return void 0;
6418
+ }
6419
+ };
6420
+ function node$1(node2) {
6421
+ return node2;
6422
+ }
6423
+ const generateImagActions = {
6424
+ name: "sanity-assist-generate-image",
6425
+ useAction(props) {
6426
+ const pathKey = usePathKey(props.path);
6427
+ const {
6428
+ config
6429
+ } = useAiAssistanceConfig();
6430
+ const apiClient = useApiClient(config == null ? void 0 : config.__customApiClient);
6431
+ const {
6432
+ generateImage,
6433
+ loading
6434
+ } = useGenerateImage(apiClient);
6435
+ const imageContext = react.useContext(ImageContext);
6436
+ if (imageContext && pathKey === (imageContext == null ? void 0 : imageContext.imageInstructionPath)) {
6437
+ const {
6438
+ documentId
6439
+ } = useAssistDocumentContext();
6440
+ return react.useMemo(() => {
6441
+ return node$1({
6442
+ type: "action",
6443
+ icon: loading ? () => /* @__PURE__ */jsxRuntime.jsx(ui.Box, {
6444
+ style: {
6445
+ height: 17
6446
+ },
6447
+ children: /* @__PURE__ */jsxRuntime.jsx(ui.Spinner, {
6448
+ style: {
6449
+ transform: "translateY(6px)"
6450
+ }
6451
+ })
6452
+ }) : icons.ImageIcon,
6453
+ title: "Generate image from prompt",
6454
+ onAction: () => {
6455
+ if (loading) {
6456
+ return;
6457
+ }
6458
+ generateImage({
6459
+ path: pathKey,
6460
+ documentId: documentId != null ? documentId : ""
6461
+ });
6462
+ },
6463
+ renderAsButton: true,
6464
+ disabled: loading
6465
+ });
6466
+ }, [generateImage, pathKey, documentId, loading]);
4430
6467
  }
4431
6468
  return void 0;
4432
6469
  }
@@ -4451,7 +6488,8 @@ const assistFieldActions = {
4451
6488
  documentOnChange,
4452
6489
  documentSchemaType,
4453
6490
  documentId,
4454
- selectedPath
6491
+ selectedPath,
6492
+ assistableDocumentId
4455
6493
  } =
4456
6494
  // document field actions do not have access to the document context
4457
6495
  // conditional hook _should_ be safe here since the logical path will be stable
@@ -4461,8 +6499,11 @@ const assistFieldActions = {
4461
6499
  // eslint-disable-next-line react-hooks/rules-of-hooks
4462
6500
  useAssistDocumentContext();
4463
6501
  const {
4464
- value: docValue
6502
+ value: docValue,
6503
+ formState
4465
6504
  } = desk.useDocumentPane();
6505
+ const formStateRef = react.useRef(formState);
6506
+ formStateRef.current = formState;
4466
6507
  const currentUser = sanity.useCurrentUser();
4467
6508
  const isHidden = !assistDocument;
4468
6509
  const pathKey = usePathKey(props.path);
@@ -4476,7 +6517,7 @@ const assistFieldActions = {
4476
6517
  isDocAssistable: documentIsAssistable != null ? documentIsAssistable : false
4477
6518
  });
4478
6519
  const isSelectable = !!useSelectedField(documentSchemaType, typePath);
4479
- const assistSupported = useAssistSupported(props.path, schemaType) && isSelectable && isSchemaAssistEnabled(documentSchemaType);
6520
+ const assistSupported = useAssistSupported(props.path, schemaType) && isSelectable && isSchemaAssistEnabled(documentSchemaType) && schemaType.readOnly !== true;
4480
6521
  const fieldAssist = react.useMemo(() => {
4481
6522
  var _a;
4482
6523
  return ((_a = assistDocument == null ? void 0 : assistDocument.fields) != null ? _a : []).find(f => f.path === typePath || pathKey === documentRootKey && f.path === pathKey);
@@ -4486,6 +6527,13 @@ const assistFieldActions = {
4486
6527
  const isPathSelected = pathKey === selectedPath;
4487
6528
  const isSelected = isInspectorOpen && isPathSelected;
4488
6529
  const imageCaptionAction = generateCaptionsActions.useAction(props);
6530
+ const imageGenAction = generateImagActions.useAction(props);
6531
+ const translateAction = translateActions.useAction(sanity.typed({
6532
+ ...props,
6533
+ documentId: assistableDocumentId,
6534
+ documentIsAssistable,
6535
+ documentSchemaType
6536
+ }));
4489
6537
  const manageInstructions = react.useCallback(() => isSelected ? closeInspector(aiInspectorId) : openInspector(aiInspectorId, {
4490
6538
  [fieldPathParam]: pathKey,
4491
6539
  [instructionParam]: void 0
@@ -4499,7 +6547,8 @@ const assistFieldActions = {
4499
6547
  assistDocumentId,
4500
6548
  path: pathKey,
4501
6549
  typePath,
4502
- instruction
6550
+ instruction,
6551
+ conditionalMembers: formStateRef.current ? getConditionalMembers(formStateRef.current) : []
4503
6552
  });
4504
6553
  }, [requestRunInstruction, assistableDocId, pathKey, typePath, assistDocumentId, fieldAssistKey]);
4505
6554
  const privateInstructions = react.useMemo(() => {
@@ -4512,7 +6561,7 @@ const assistFieldActions = {
4512
6561
  }, [fieldAssist == null ? void 0 : fieldAssist.instructions]);
4513
6562
  const instructions = react.useMemo(() => [...privateInstructions, ...sharedInstructions], [privateInstructions, sharedInstructions]);
4514
6563
  const runInstructionsGroup = react.useMemo(() => {
4515
- return (instructions == null ? void 0 : instructions.length) || imageCaptionAction ? node({
6564
+ return (instructions == null ? void 0 : instructions.length) || imageCaptionAction || translateAction || imageGenAction ? node({
4516
6565
  type: "group",
4517
6566
  icon: () => null,
4518
6567
  title: "Run instructions",
@@ -4523,10 +6572,10 @@ const assistFieldActions = {
4523
6572
  hidden: isHidden,
4524
6573
  documentIsNew: !!documentIsNew,
4525
6574
  assistSupported
4526
- }))), imageCaptionAction].filter(Boolean),
6575
+ }))), imageCaptionAction, imageGenAction].filter(a => !!a),
4527
6576
  expanded: true
4528
6577
  }) : void 0;
4529
- }, [instructions, currentUser == null ? void 0 : currentUser.id, onInstructionAction, isHidden, documentIsNew, assistSupported, imageCaptionAction]);
6578
+ }, [instructions, currentUser == null ? void 0 : currentUser.id, onInstructionAction, isHidden, documentIsNew, assistSupported, imageCaptionAction, translateAction, imageGenAction]);
4530
6579
  const instructionsLength = (instructions == null ? void 0 : instructions.length) || 0;
4531
6580
  const manageInstructionsItem = react.useMemo(() => node({
4532
6581
  type: "action",
@@ -4539,13 +6588,13 @@ const assistFieldActions = {
4539
6588
  type: "group",
4540
6589
  icon: icons.SparklesIcon,
4541
6590
  title: pluginTitleShort,
4542
- children: [runInstructionsGroup, assistSupported && manageInstructionsItem].filter(c => !!c),
6591
+ children: [runInstructionsGroup, translateAction, assistSupported && manageInstructionsItem].filter(c => !!c).filter(c => c.type === "group" ? c.children.length : true),
4543
6592
  expanded: false,
4544
6593
  renderAsButton: true,
4545
- hidden: !assistSupported && !imageCaptionAction
6594
+ hidden: !assistSupported && !imageCaptionAction && !translateAction && !imageGenAction
4546
6595
  }), [
4547
6596
  //documentIsNew,
4548
- runInstructionsGroup, manageInstructionsItem, assistSupported, imageCaptionAction]);
6597
+ runInstructionsGroup, manageInstructionsItem, assistSupported, imageCaptionAction, translateAction, imageGenAction]);
4549
6598
  const emptyAction = react.useMemo(() => node({
4550
6599
  type: "action",
4551
6600
  hidden: !assistSupported,
@@ -4555,7 +6604,7 @@ const assistFieldActions = {
4555
6604
  title: pluginTitleShort,
4556
6605
  selected: isSelected
4557
6606
  }), [assistSupported, manageInstructions, isSelected]);
4558
- if (instructionsLength === 0 && !imageCaptionAction) {
6607
+ if (instructionsLength === 0 && !imageCaptionAction && !translateAction && !imageGenAction) {
4559
6608
  return emptyAction;
4560
6609
  }
4561
6610
  return group;
@@ -4575,9 +6624,7 @@ function instructionItem(props) {
4575
6624
  iconRight: isPrivate ? PrivateIcon : void 0,
4576
6625
  title: getInstructionTitle(instruction),
4577
6626
  onAction: () => onInstructionAction(instruction),
4578
- disabled: assistSupported ? false : {
4579
- reason: "".concat(pluginTitle, " is not supported for this field")
4580
- },
6627
+ disabled: !assistSupported,
4581
6628
  hidden
4582
6629
  });
4583
6630
  }
@@ -4654,7 +6701,7 @@ function useInstructionToaster(documentId, documentSchemaType) {
4654
6701
  }
4655
6702
  function AssistDocumentInputWrapper(props) {
4656
6703
  var _a;
4657
- if (!isType(props.schemaType, "document") && props.id !== "root") {
6704
+ if (!isType(props.schemaType, "document") && props.id !== "root" && props.id !== assistFormId) {
4658
6705
  return /* @__PURE__ */jsxRuntime.jsx(AssistInput, {
4659
6706
  ...props
4660
6707
  });
@@ -4668,18 +6715,34 @@ function AssistDocumentInputWrapper(props) {
4668
6715
  documentId
4669
6716
  });
4670
6717
  }
4671
- function AssistDocumentInput(_ref16) {
6718
+ function AssistDocumentInput(_ref24) {
4672
6719
  let {
4673
6720
  documentId,
4674
6721
  ...props
4675
- } = _ref16;
6722
+ } = _ref24;
4676
6723
  useInstructionToaster(documentId, props.schemaType);
6724
+ const schemaType = react.useMemo(() => {
6725
+ if (props.schemaType.name !== assistDocumentTypeName) {
6726
+ return props.schemaType;
6727
+ }
6728
+ return {
6729
+ ...props.schemaType,
6730
+ type: {
6731
+ ...props.schemaType.type,
6732
+ // compatability with i18nArrays plugin that requires this to be document
6733
+ name: "document"
6734
+ }
6735
+ };
6736
+ }, [props.schemaType]);
4677
6737
  return /* @__PURE__ */jsxRuntime.jsx(FirstAssistedPathProvider, {
4678
6738
  members: props.members,
4679
6739
  children: /* @__PURE__ */jsxRuntime.jsx(AssistDocumentContextProvider, {
4680
- schemaType: props.schemaType,
6740
+ schemaType,
4681
6741
  documentId,
4682
- children: props.renderDefault(props)
6742
+ children: props.renderDefault({
6743
+ ...props,
6744
+ schemaType
6745
+ })
4683
6746
  })
4684
6747
  });
4685
6748
  }
@@ -4750,31 +6813,41 @@ const assist = sanity.definePlugin(config => {
4750
6813
  schema: {
4751
6814
  types: schemaTypes
4752
6815
  },
6816
+ i18n: {
6817
+ bundles: [{}]
6818
+ },
4753
6819
  document: {
4754
6820
  inspectors: (prev, context) => {
4755
- const docSchema = context.schema.get(context.documentType);
6821
+ const documentType = context.documentType;
6822
+ const docSchema = context.schema.get(documentType);
4756
6823
  if (docSchema && isSchemaAssistEnabled(docSchema)) {
4757
6824
  return [...prev, assistInspector];
4758
6825
  }
4759
6826
  return prev;
4760
6827
  },
4761
- unstable_fieldActions: (prev, _ref17) => {
6828
+ unstable_fieldActions: (prev, _ref25) => {
4762
6829
  let {
4763
6830
  documentType,
4764
6831
  schema
4765
- } = _ref17;
6832
+ } = _ref25;
6833
+ if (documentType === assistDocumentTypeName) {
6834
+ return [];
6835
+ }
4766
6836
  const docSchema = schema.get(documentType);
4767
6837
  if (docSchema && isSchemaAssistEnabled(docSchema)) {
4768
6838
  return [...prev, assistFieldActions];
4769
6839
  }
4770
6840
  return prev;
4771
6841
  },
4772
- unstable_languageFilter: (prev, _ref18) => {
6842
+ unstable_languageFilter: (prev, _ref26) => {
4773
6843
  let {
4774
6844
  documentId,
4775
6845
  schema,
4776
6846
  schemaType
4777
- } = _ref18;
6847
+ } = _ref26;
6848
+ if (schemaType === assistDocumentTypeName) {
6849
+ return [];
6850
+ }
4778
6851
  const docSchema = schema.get(schemaType);
4779
6852
  if (docSchema && sanity.isObjectSchemaType(docSchema) && isSchemaAssistEnabled(docSchema)) {
4780
6853
  return [...prev, createAssistDocumentPresence(documentId, docSchema)];
@@ -4831,4 +6904,5 @@ const assist = sanity.definePlugin(config => {
4831
6904
  exports.SchemaTypeTool = SchemaTypeTool;
4832
6905
  exports.assist = assist;
4833
6906
  exports.contextDocumentTypeName = contextDocumentTypeName;
6907
+ exports.defaultLanguageOutputs = defaultLanguageOutputs;
4834
6908
  //# sourceMappingURL=index.js.map