@happyvertical/smrt-content 0.36.2 → 0.36.3

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 (86) hide show
  1. package/dist/asset-associable.d.ts +2 -2
  2. package/dist/asset-associable.d.ts.map +1 -1
  3. package/dist/body-format.d.ts +18 -3
  4. package/dist/body-format.d.ts.map +1 -1
  5. package/dist/body-format.js.map +1 -1
  6. package/dist/content-contribution-attachment.d.ts +4 -4
  7. package/dist/content-contribution-attachment.d.ts.map +1 -1
  8. package/dist/content-contribution-config.d.ts +1 -1
  9. package/dist/content-contribution-config.d.ts.map +1 -1
  10. package/dist/content-contribution-revision.d.ts +4 -4
  11. package/dist/content-contribution-revision.d.ts.map +1 -1
  12. package/dist/content-contribution-type.d.ts +5 -5
  13. package/dist/content-contribution-type.d.ts.map +1 -1
  14. package/dist/content-contribution.d.ts +7 -7
  15. package/dist/content-contribution.d.ts.map +1 -1
  16. package/dist/content-contributions.d.ts +24 -2
  17. package/dist/content-contributions.d.ts.map +1 -1
  18. package/dist/content-contributor.d.ts +5 -5
  19. package/dist/content-contributor.d.ts.map +1 -1
  20. package/dist/content-correction.d.ts +2 -2
  21. package/dist/content-correction.d.ts.map +1 -1
  22. package/dist/content-feed-parser.d.ts.map +1 -1
  23. package/dist/content-feed-source.d.ts +5 -5
  24. package/dist/content-feed-source.d.ts.map +1 -1
  25. package/dist/content-governance-assignment.d.ts +2 -2
  26. package/dist/content-governance-assignment.d.ts.map +1 -1
  27. package/dist/content-governance-policy.d.ts +2 -2
  28. package/dist/content-governance-policy.d.ts.map +1 -1
  29. package/dist/content-governance-profile.d.ts +2 -2
  30. package/dist/content-governance-profile.d.ts.map +1 -1
  31. package/dist/content-governance.d.ts +7 -7
  32. package/dist/content-governance.d.ts.map +1 -1
  33. package/dist/content-review.d.ts +2 -2
  34. package/dist/content-review.d.ts.map +1 -1
  35. package/dist/content-reviews.d.ts +1 -1
  36. package/dist/content-reviews.d.ts.map +1 -1
  37. package/dist/content-transparency.d.ts +38 -7
  38. package/dist/content-transparency.d.ts.map +1 -1
  39. package/dist/content-types.d.ts +1 -1
  40. package/dist/content-types.d.ts.map +1 -1
  41. package/dist/content-version.d.ts +17 -4
  42. package/dist/content-version.d.ts.map +1 -1
  43. package/dist/content-versions.d.ts.map +1 -1
  44. package/dist/content.d.ts +40 -36
  45. package/dist/content.d.ts.map +1 -1
  46. package/dist/contents.d.ts +46 -31
  47. package/dist/contents.d.ts.map +1 -1
  48. package/dist/index.js +224 -118
  49. package/dist/index.js.map +1 -1
  50. package/dist/manifest.json +40 -40
  51. package/dist/serialization.d.ts +66 -49
  52. package/dist/serialization.d.ts.map +1 -1
  53. package/dist/smrt-knowledge.json +4 -4
  54. package/dist/svelte/components/ContentAgentChat.svelte +42 -24
  55. package/dist/svelte/components/ContentAgentChat.svelte.d.ts.map +1 -1
  56. package/dist/svelte/components/ContentBodyEditor.svelte +8 -3
  57. package/dist/svelte/components/ContentBodyEditor.svelte.d.ts +3 -3
  58. package/dist/svelte/components/ContentBodyEditor.svelte.d.ts.map +1 -1
  59. package/dist/svelte/components/ContentClaimAuditTool.svelte +6 -6
  60. package/dist/svelte/components/ContentCorrectionsTool.svelte +4 -4
  61. package/dist/svelte/components/ContentEditor.svelte +69 -30
  62. package/dist/svelte/components/ContentEditor.svelte.d.ts +6 -3
  63. package/dist/svelte/components/ContentEditor.svelte.d.ts.map +1 -1
  64. package/dist/svelte/components/ContentGovernanceManager.svelte +4 -2
  65. package/dist/svelte/components/ContentGovernanceManager.svelte.d.ts.map +1 -1
  66. package/dist/svelte/components/ContentGovernancePanel.svelte +21 -21
  67. package/dist/svelte/components/ContentList.svelte +20 -17
  68. package/dist/svelte/components/ContentList.svelte.d.ts +8 -7
  69. package/dist/svelte/components/ContentList.svelte.d.ts.map +1 -1
  70. package/dist/svelte/components/ContentMetadataFields.svelte +10 -1
  71. package/dist/svelte/components/ContentMetadataFields.svelte.d.ts +9 -1
  72. package/dist/svelte/components/ContentMetadataFields.svelte.d.ts.map +1 -1
  73. package/dist/svelte/components/ContentStatusFields.svelte +9 -1
  74. package/dist/svelte/components/ContentStatusFields.svelte.d.ts +8 -1
  75. package/dist/svelte/components/ContentStatusFields.svelte.d.ts.map +1 -1
  76. package/dist/svelte/components/ContentTransparencyTool.svelte +4 -2
  77. package/dist/svelte/components/ContentTransparencyTool.svelte.d.ts.map +1 -1
  78. package/dist/svelte/components/ContentVersionsTool.svelte +6 -6
  79. package/dist/svelte/components/GovernedContentEditor.svelte +8 -2
  80. package/dist/svelte/components/GovernedContentEditor.svelte.d.ts.map +1 -1
  81. package/dist/svelte/routes/ContentContributionsRoute.svelte +11 -10
  82. package/dist/svelte/routes/ContentContributionsRoute.svelte.d.ts.map +1 -1
  83. package/dist/svelte/routes/ContentFactsRoute.svelte +2 -2
  84. package/dist/svelte/routes/ContentWorkspaceRoute.svelte +6 -6
  85. package/dist/thumbnail-generator.d.ts.map +1 -1
  86. package/package.json +14 -14
@@ -10,6 +10,7 @@ import {
10
10
  type ContentBodyImagePlacement,
11
11
  editorHtmlToBody,
12
12
  extractBodyImages,
13
+ type ImageAssetLike,
13
14
  imageAssetToHtml,
14
15
  normalizeEditorHtml,
15
16
  resolveBodyFormat,
@@ -35,7 +36,7 @@ export interface Props {
35
36
  onUseImageAsThumbnail?: (assetId: string) => void;
36
37
  onResolveImage?: (
37
38
  selected: ImageLike | File | string,
38
- ) => Promise<any | null> | any | null;
39
+ ) => Promise<unknown> | unknown;
39
40
  }
40
41
 
41
42
  let {
@@ -667,7 +668,7 @@ function insertImageHtml(html: string) {
667
668
  emitChange();
668
669
  }
669
670
 
670
- export function insertImageAsset(asset: any) {
671
+ export function insertImageAsset(asset: ImageAssetLike | null | undefined) {
671
672
  insertImageHtml(imageAssetToHtml(asset));
672
673
  }
673
674
 
@@ -863,9 +864,13 @@ function startImageMove(event: PointerEvent) {
863
864
  }
864
865
 
865
866
  async function resolveAndInsertImage(selected: ImageLike | File | string) {
867
+ // Dynamic boundary: the consumer-supplied `onResolveImage` callback returns an
868
+ // opaque resolved value (or, without it, the raw ImageLike/File/string). The
869
+ // image helpers read optional fields defensively, so coerce to the structural
870
+ // ImageAssetLike shape rather than widening the public insertImageAsset param.
866
871
  const asset = onResolveImage ? await onResolveImage(selected) : selected;
867
872
  if (asset) {
868
- insertImageAsset(asset);
873
+ insertImageAsset(asset as ImageAssetLike);
869
874
  }
870
875
  }
871
876
 
@@ -1,5 +1,5 @@
1
1
  import type { ImageLike } from '@happyvertical/smrt-images/svelte';
2
- import { type ContentBodyFormat, type ContentBodyImage } from '../../body-format';
2
+ import { type ContentBodyFormat, type ContentBodyImage, type ImageAssetLike } from '../../body-format';
3
3
  export interface ContentBodyEditorChange {
4
4
  body: string;
5
5
  bodyFormat: ContentBodyFormat;
@@ -14,10 +14,10 @@ export interface Props {
14
14
  onOpenImageChooser?: () => void;
15
15
  onSelectImage?: (index: number) => void;
16
16
  onUseImageAsThumbnail?: (assetId: string) => void;
17
- onResolveImage?: (selected: ImageLike | File | string) => Promise<any | null> | any | null;
17
+ onResolveImage?: (selected: ImageLike | File | string) => Promise<unknown> | unknown;
18
18
  }
19
19
  declare const ContentBodyEditor: import("svelte").Component<Props, {
20
- insertImageAsset: (asset: any) => void;
20
+ insertImageAsset: (asset: ImageAssetLike | null | undefined) => void;
21
21
  focusImage: (index: number) => void;
22
22
  }, "">;
23
23
  type ContentBodyEditor = ReturnType<typeof ContentBodyEditor>;
@@ -1 +1 @@
1
- {"version":3,"file":"ContentBodyEditor.svelte.d.ts","sourceRoot":"","sources":["../../../src/svelte/components/ContentBodyEditor.svelte.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,mCAAmC,CAAC;AAInE,OAAO,EAEL,KAAK,iBAAiB,EACtB,KAAK,gBAAgB,EAOtB,MAAM,mBAAmB,CAAC;AAI3B,MAAM,WAAW,uBAAuB;IACtC,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,iBAAiB,CAAC;IAC9B,MAAM,EAAE,gBAAgB,EAAE,CAAC;CAC5B;AAED,MAAM,WAAW,KAAK;IACpB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,iBAAiB,GAAG,IAAI,CAAC;IAClC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,EAAE,CAAC,MAAM,EAAE,uBAAuB,KAAK,IAAI,CAAC;IACrD,kBAAkB,CAAC,EAAE,MAAM,IAAI,CAAC;IAChC,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACxC,qBAAqB,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;IAClD,cAAc,CAAC,EAAE,CACf,QAAQ,EAAE,SAAS,GAAG,IAAI,GAAG,MAAM,KAChC,OAAO,CAAC,GAAG,GAAG,IAAI,CAAC,GAAG,GAAG,GAAG,IAAI,CAAC;CACvC;AAwlCD,QAAA,MAAM,iBAAiB;8BArdW,GAAG;wBAIT,MAAM;MAid6B,CAAC;AAChE,KAAK,iBAAiB,GAAG,UAAU,CAAC,OAAO,iBAAiB,CAAC,CAAC;AAC9D,eAAe,iBAAiB,CAAC"}
1
+ {"version":3,"file":"ContentBodyEditor.svelte.d.ts","sourceRoot":"","sources":["../../../src/svelte/components/ContentBodyEditor.svelte.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,mCAAmC,CAAC;AAInE,OAAO,EAEL,KAAK,iBAAiB,EACtB,KAAK,gBAAgB,EAIrB,KAAK,cAAc,EAIpB,MAAM,mBAAmB,CAAC;AAI3B,MAAM,WAAW,uBAAuB;IACtC,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,iBAAiB,CAAC;IAC9B,MAAM,EAAE,gBAAgB,EAAE,CAAC;CAC5B;AAED,MAAM,WAAW,KAAK;IACpB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,iBAAiB,GAAG,IAAI,CAAC;IAClC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,EAAE,CAAC,MAAM,EAAE,uBAAuB,KAAK,IAAI,CAAC;IACrD,kBAAkB,CAAC,EAAE,MAAM,IAAI,CAAC;IAChC,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACxC,qBAAqB,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;IAClD,cAAc,CAAC,EAAE,CACf,QAAQ,EAAE,SAAS,GAAG,IAAI,GAAG,MAAM,KAChC,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,CAAC;CACjC;AA4lCD,QAAA,MAAM,iBAAiB;8BAzdW,cAAc,GAAG,IAAI,GAAG,SAAS;wBAIvC,MAAM;MAqd6B,CAAC;AAChE,KAAK,iBAAiB,GAAG,UAAU,CAAC,OAAO,iBAAiB,CAAC,CAAC;AAC9D,eAAe,iBAAiB,CAAC"}
@@ -113,9 +113,9 @@ async function loadFactAudit(contentIdToLoad = savedContentId) {
113
113
  if (savedContentId !== contentIdToLoad) return;
114
114
  factAudit = response.data;
115
115
  onFactAuditChange?.(response.data);
116
- } catch (err: any) {
116
+ } catch (err) {
117
117
  if (savedContentId !== contentIdToLoad) return;
118
- error = err.message || 'Failed to load claim audit';
118
+ error = (err instanceof Error ? err.message : '') || 'Failed to load claim audit';
119
119
  } finally {
120
120
  if (savedContentId === contentIdToLoad) {
121
121
  busy = false;
@@ -137,9 +137,9 @@ async function repairFactAudit() {
137
137
  factAudit = response.data;
138
138
  notice = `Fact audit repaired: ${response.data.counts.total} claim(s) checked.`;
139
139
  onFactAuditChange?.(response.data);
140
- } catch (err: any) {
140
+ } catch (err) {
141
141
  if (savedContentId !== contentIdToRepair) return;
142
- error = err.message || 'Failed to repair fact audit';
142
+ error = (err instanceof Error ? err.message : '') || 'Failed to repair fact audit';
143
143
  } finally {
144
144
  if (savedContentId === contentIdToRepair) {
145
145
  busy = false;
@@ -167,9 +167,9 @@ async function recheckFactClaims(claimIds: string[]) {
167
167
  notice = `Rechecked ${claimIds.length} claim${claimIds.length === 1 ? '' : 's'} against current evidence.`;
168
168
  selectedClaimIds = selectedClaimIds.filter((id) => !claimIds.includes(id));
169
169
  onFactAuditChange?.(response.data);
170
- } catch (err: any) {
170
+ } catch (err) {
171
171
  if (savedContentId !== contentIdToRecheck) return;
172
- error = err.message || 'Failed to recheck claim support';
172
+ error = (err instanceof Error ? err.message : '') || 'Failed to recheck claim support';
173
173
  } finally {
174
174
  if (savedContentId === contentIdToRecheck) {
175
175
  busy = false;
@@ -117,9 +117,9 @@ async function loadCorrections(contentIdToLoad = savedContentId) {
117
117
  corrections = correctionsResponse.data;
118
118
  facts = factsResponse.data.facts || [];
119
119
  onCorrectionsChange?.(correctionsResponse.data);
120
- } catch (err: any) {
120
+ } catch (err) {
121
121
  if (savedContentId !== contentIdToLoad) return;
122
- error = err.message || 'Failed to load corrections';
122
+ error = (err instanceof Error ? err.message : '') || 'Failed to load corrections';
123
123
  } finally {
124
124
  if (savedContentId === contentIdToLoad) {
125
125
  busy = false;
@@ -149,9 +149,9 @@ async function issueCorrection() {
149
149
 
150
150
  notice = 'Correction issued.';
151
151
  await loadCorrections(contentIdToCorrect);
152
- } catch (err: any) {
152
+ } catch (err) {
153
153
  if (savedContentId !== contentIdToCorrect) return;
154
- error = err.message || 'Failed to issue correction';
154
+ error = (err instanceof Error ? err.message : '') || 'Failed to issue correction';
155
155
  } finally {
156
156
  if (savedContentId === contentIdToCorrect) {
157
157
  busy = false;
@@ -22,13 +22,20 @@ import type {
22
22
  FactEvidenceStatus,
23
23
  } from '../../mock-smrt-client';
24
24
  import { joinApiUrl, normalizeApiBaseUrl } from '../api';
25
+ import type { ContentData } from '../../mock-smrt-client';
25
26
  import {
27
+ type ContentEditorAsset,
26
28
  type ContentEditorFormData,
29
+ type ContentEditorInitialContent,
30
+ type ContentEditorReference,
31
+ type ContentEditorSavePayload,
27
32
  getContentEditorInitialFormData,
28
33
  getContentEditorSavePayload,
29
34
  getContentEditorSnapshot,
30
35
  normalizePublishDate,
31
36
  } from '../content-editor-form';
37
+
38
+ type ContentEditorSnapshot = ReturnType<typeof getContentEditorSnapshot>;
32
39
  import { M } from '../i18n.editor.js';
33
40
  import ContentAgentChat from './ContentAgentChat.svelte';
34
41
  import ContentBodyEditor, {
@@ -40,7 +47,7 @@ const { t } = useI18n();
40
47
 
41
48
  export interface Props {
42
49
  apiBaseUrl?: string;
43
- content?: any;
50
+ content?: ContentData | null;
44
51
  contentId?: string;
45
52
  factAudit?: FactAuditStateData | null;
46
53
  saveDisabled?: boolean;
@@ -51,9 +58,9 @@ export interface Props {
51
58
  hideChat?: boolean;
52
59
  assistantFieldAllowList?: ContentEditorAssistantFieldUpdateAllowList;
53
60
  onAssistantContextChange?: ContentEditorAssistantContextChange;
54
- onChange?: (data: any) => void;
61
+ onChange?: (data: ContentEditorSnapshot) => void;
55
62
  onFactAuditChange?: (state: FactAuditStateData | null) => void;
56
- onSave: (data: any) => void;
63
+ onSave: (data: ContentEditorSavePayload) => void;
57
64
  onCancel: () => void;
58
65
  }
59
66
 
@@ -177,7 +184,11 @@ $effect(() => {
177
184
  const newKey = content?.id ?? contentId;
178
185
  if (newKey !== lastContentKey) {
179
186
  lastContentKey = newKey;
180
- formData = getContentEditorInitialFormData(content);
187
+ // ContentData carries a nullable bodyFormat; the form initializer accepts
188
+ // the editor's stricter ContentEditorInitialContent shape and normalizes it.
189
+ formData = getContentEditorInitialFormData(
190
+ content as ContentEditorInitialContent | null,
191
+ );
181
192
  fieldUndoStack = [];
182
193
  showUndoBanner = false;
183
194
  }
@@ -249,7 +260,7 @@ function undoLastApply() {
249
260
  }
250
261
  }
251
262
 
252
- function getReferenceLabel(reference: any): string {
263
+ function getReferenceLabel(reference: ContentEditorReference): string {
253
264
  return (
254
265
  reference?.title ||
255
266
  reference?.name ||
@@ -260,12 +271,12 @@ function getReferenceLabel(reference: any): string {
260
271
  );
261
272
  }
262
273
 
263
- function getReferenceUrl(reference: any): string | null {
274
+ function getReferenceUrl(reference: ContentEditorReference): string | null {
264
275
  return reference?.url || reference?.originalUrl || reference?.source || null;
265
276
  }
266
277
 
267
278
  function getResourceClaimsForReference(
268
- reference: any,
279
+ reference: ContentEditorReference,
269
280
  ): FactAuditResourceClaimData[] {
270
281
  const selector = getReferenceSourceSelector(reference);
271
282
  const referenceId = String(reference?.id || '');
@@ -290,7 +301,7 @@ function getResourceClaimsForReference(
290
301
  });
291
302
  }
292
303
 
293
- function getAuditReferences(): any[] {
304
+ function getAuditReferences(): ContentEditorReference[] {
294
305
  const references = [...(formData.references ?? [])];
295
306
  const seen = new Set<string>();
296
307
 
@@ -329,7 +340,10 @@ function getAuditReferences(): any[] {
329
340
  return references;
330
341
  }
331
342
 
332
- function getReferenceExpansionKey(reference: any, index: number): string {
343
+ function getReferenceExpansionKey(
344
+ reference: ContentEditorReference,
345
+ index: number,
346
+ ): string {
333
347
  return String(
334
348
  reference?.id ||
335
349
  reference?.url ||
@@ -339,13 +353,19 @@ function getReferenceExpansionKey(reference: any, index: number): string {
339
353
  );
340
354
  }
341
355
 
342
- function isReferenceClaimsExpanded(reference: any, index: number): boolean {
356
+ function isReferenceClaimsExpanded(
357
+ reference: ContentEditorReference,
358
+ index: number,
359
+ ): boolean {
343
360
  return expandedReferenceClaimKeys.includes(
344
361
  getReferenceExpansionKey(reference, index),
345
362
  );
346
363
  }
347
364
 
348
- function toggleReferenceClaims(reference: any, index: number) {
365
+ function toggleReferenceClaims(
366
+ reference: ContentEditorReference,
367
+ index: number,
368
+ ) {
349
369
  const key = getReferenceExpansionKey(reference, index);
350
370
  expandedReferenceClaimKeys = expandedReferenceClaimKeys.includes(key)
351
371
  ? expandedReferenceClaimKeys.filter((expandedKey) => expandedKey !== key)
@@ -432,7 +452,7 @@ function toggleResourceClaimSelection(claim: FactAuditResourceClaimData) {
432
452
  : [...new Set([...selectedEvidenceIds, ...evidenceIds])];
433
453
  }
434
454
 
435
- function getReferenceSourceSelector(reference: any): {
455
+ function getReferenceSourceSelector(reference: ContentEditorReference): {
436
456
  sourceKind: string;
437
457
  sourceId: string;
438
458
  } | null {
@@ -496,7 +516,7 @@ function getEvidenceStatusIcon(status: FactEvidenceStatus | null | undefined) {
496
516
  async function runFactAuditAction(
497
517
  path: string,
498
518
  method: 'POST' | 'PUT',
499
- body: Record<string, any>,
519
+ body: Record<string, unknown>,
500
520
  ): Promise<FactAuditStateData> {
501
521
  if (!contentId || contentId === 'new') {
502
522
  throw new Error('Save this content before updating evidence.');
@@ -540,8 +560,10 @@ async function updateEvidenceStatus(
540
560
  );
541
561
  evidenceNotice = `Updated ${evidenceIds.length} evidence item${evidenceIds.length === 1 ? '' : 's'}.`;
542
562
  onFactAuditChange?.(nextAudit);
543
- } catch (error: any) {
544
- evidenceError = error.message || 'Failed to update evidence status.';
563
+ } catch (error) {
564
+ evidenceError =
565
+ (error instanceof Error ? error.message : '') ||
566
+ 'Failed to update evidence status.';
545
567
  } finally {
546
568
  evidenceBusy = null;
547
569
  }
@@ -551,7 +573,7 @@ async function updateSelectedEvidenceStatus() {
551
573
  await updateEvidenceStatus(selectedEvidenceIds, bulkEvidenceStatus);
552
574
  }
553
575
 
554
- async function repairReferenceEvidence(reference: any) {
576
+ async function repairReferenceEvidence(reference: ContentEditorReference) {
555
577
  const selector = getReferenceSourceSelector(reference);
556
578
  if (!selector || evidenceBusy) {
557
579
  return;
@@ -568,8 +590,10 @@ async function repairReferenceEvidence(reference: any) {
568
590
  selectedEvidenceIds = [];
569
591
  evidenceNotice = 'Reference evidence repaired.';
570
592
  onFactAuditChange?.(nextAudit);
571
- } catch (error: any) {
572
- evidenceError = error.message || 'Failed to repair reference evidence.';
593
+ } catch (error) {
594
+ evidenceError =
595
+ (error instanceof Error ? error.message : '') ||
596
+ 'Failed to repair reference evidence.';
573
597
  } finally {
574
598
  evidenceBusy = null;
575
599
  }
@@ -592,8 +616,10 @@ async function repairSelectedReferenceEvidence() {
592
616
  selectedEvidenceIds = [];
593
617
  evidenceNotice = `Repaired ${sources.length} reference${sources.length === 1 ? '' : 's'}.`;
594
618
  onFactAuditChange?.(nextAudit);
595
- } catch (error: any) {
596
- evidenceError = error.message || 'Failed to repair selected references.';
619
+ } catch (error) {
620
+ evidenceError =
621
+ (error instanceof Error ? error.message : '') ||
622
+ 'Failed to repair selected references.';
597
623
  } finally {
598
624
  evidenceBusy = null;
599
625
  }
@@ -610,7 +636,11 @@ function removeReference(id: string) {
610
636
  let showImageUploader = $state(false);
611
637
  let showInlineImageUploader = $state(false);
612
638
  let expandedReferenceClaimKeys = $state<string[]>([]);
613
- let bodyEditor = $state<any>(null);
639
+ interface BodyEditorInstance {
640
+ focusImage?: (index: number) => void;
641
+ insertImageAsset?: (asset: ContentEditorAsset) => void;
642
+ }
643
+ let bodyEditor = $state<BodyEditorInstance | null>(null);
614
644
  let selectedBodyImageIndex = $state(-1);
615
645
  const bodyImages = $derived(
616
646
  extractBodyImages(
@@ -623,8 +653,14 @@ const bodyImages = $derived(
623
653
  let imageDragOver = $state(false);
624
654
  let refDragOver = $state(false);
625
655
 
626
- function getImageRecord(payload: any) {
627
- return payload?.data ?? payload;
656
+ function getImageRecord(payload: unknown): ContentEditorAsset {
657
+ if (payload && typeof payload === 'object' && 'data' in payload) {
658
+ const data = (payload as { data?: ContentEditorAsset }).data;
659
+ if (data) {
660
+ return data;
661
+ }
662
+ }
663
+ return (payload ?? {}) as ContentEditorAsset;
628
664
  }
629
665
 
630
666
  // ---------- Image drag-and-drop ----------
@@ -791,7 +827,7 @@ async function createImageRecord(input: {
791
827
  name: string;
792
828
  sourceUri: string;
793
829
  mimeType: string;
794
- }): Promise<any | null> {
830
+ }): Promise<ContentEditorAsset | null> {
795
831
  const resp = await fetch(joinApiUrl(apiBaseUrl, '/images'), {
796
832
  method: 'POST',
797
833
  headers: { 'Content-Type': 'application/json' },
@@ -807,7 +843,7 @@ async function createImageRecord(input: {
807
843
 
808
844
  async function resolveSelectedImage(
809
845
  selected: ImageLike | File | string,
810
- ): Promise<any | null> {
846
+ ): Promise<ContentEditorAsset | null> {
811
847
  if (selected && typeof selected === 'object' && 'id' in selected) {
812
848
  addSelectedAsset(selected);
813
849
  return selected;
@@ -853,11 +889,14 @@ function handleImageSelect(selected: ImageLike | File | string) {
853
889
  })();
854
890
  }
855
891
 
856
- function getAssetImageSource(asset: any): string {
892
+ function getAssetImageSource(asset: ContentEditorAsset): string {
857
893
  return String(asset?.sourceUri || asset?.url || asset?.src || '');
858
894
  }
859
895
 
860
- function handleAttachedImageDragStart(event: DragEvent, asset: any) {
896
+ function handleAttachedImageDragStart(
897
+ event: DragEvent,
898
+ asset: ContentEditorAsset,
899
+ ) {
861
900
  if (!event.dataTransfer) {
862
901
  return;
863
902
  }
@@ -902,8 +941,8 @@ async function resolveBodyDropImage(selected: ImageLike | File | string) {
902
941
  }
903
942
  }
904
943
 
905
- function addSelectedAsset(asset: any) {
906
- const assetId = asset.id;
944
+ function addSelectedAsset(asset: ContentEditorAsset) {
945
+ const assetId = asset.id ?? '';
907
946
  if (!formData.assetIds.includes(assetId)) {
908
947
  formData.assetIds = [...formData.assetIds, assetId];
909
948
  formData.assets = [...formData.assets, asset];
@@ -919,7 +958,7 @@ function setThumbnail(id: string) {
919
958
 
920
959
  function removeAsset(id: string) {
921
960
  formData.assetIds = formData.assetIds.filter((aId: string) => aId !== id);
922
- formData.assets = formData.assets.filter((a: any) => a.id !== id);
961
+ formData.assets = formData.assets.filter((a) => a.id !== id);
923
962
  if (formData.thumbnailAssetId === id) {
924
963
  formData.thumbnailAssetId = null;
925
964
  }
@@ -1,8 +1,11 @@
1
1
  import type { ContentEditorAssistantContextChange, ContentEditorAssistantFieldUpdateAllowList } from '../../content-editor-assistant';
2
2
  import type { FactAuditStateData } from '../../mock-smrt-client';
3
+ import type { ContentData } from '../../mock-smrt-client';
4
+ import { type ContentEditorSavePayload, getContentEditorSnapshot } from '../content-editor-form';
5
+ type ContentEditorSnapshot = ReturnType<typeof getContentEditorSnapshot>;
3
6
  export interface Props {
4
7
  apiBaseUrl?: string;
5
- content?: any;
8
+ content?: ContentData | null;
6
9
  contentId?: string;
7
10
  factAudit?: FactAuditStateData | null;
8
11
  saveDisabled?: boolean;
@@ -13,9 +16,9 @@ export interface Props {
13
16
  hideChat?: boolean;
14
17
  assistantFieldAllowList?: ContentEditorAssistantFieldUpdateAllowList;
15
18
  onAssistantContextChange?: ContentEditorAssistantContextChange;
16
- onChange?: (data: any) => void;
19
+ onChange?: (data: ContentEditorSnapshot) => void;
17
20
  onFactAuditChange?: (state: FactAuditStateData | null) => void;
18
- onSave: (data: any) => void;
21
+ onSave: (data: ContentEditorSavePayload) => void;
19
22
  onCancel: () => void;
20
23
  }
21
24
  declare const ContentEditor: import("svelte").Component<Props, {
@@ -1 +1 @@
1
- {"version":3,"file":"ContentEditor.svelte.d.ts","sourceRoot":"","sources":["../../../src/svelte/components/ContentEditor.svelte.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAEV,mCAAmC,EACnC,0CAA0C,EAE3C,MAAM,gCAAgC,CAAC;AAKxC,OAAO,KAAK,EAEV,kBAAkB,EAEnB,MAAM,wBAAwB,CAAC;AAiBhC,MAAM,WAAW,KAAK;IACpB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,OAAO,CAAC,EAAE,GAAG,CAAC;IACd,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,kBAAkB,GAAG,IAAI,CAAC;IACtC,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B,eAAe,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,uBAAuB,CAAC,EAAE,0CAA0C,CAAC;IACrE,wBAAwB,CAAC,EAAE,mCAAmC,CAAC;IAC/D,QAAQ,CAAC,EAAE,CAAC,IAAI,EAAE,GAAG,KAAK,IAAI,CAAC;IAC/B,iBAAiB,CAAC,EAAE,CAAC,KAAK,EAAE,kBAAkB,GAAG,IAAI,KAAK,IAAI,CAAC;IAC/D,MAAM,EAAE,CAAC,IAAI,EAAE,GAAG,KAAK,IAAI,CAAC;IAC5B,QAAQ,EAAE,MAAM,IAAI,CAAC;CACtB;AAivCD,QAAA,MAAM,aAAa;;MAAwC,CAAC;AAC5D,KAAK,aAAa,GAAG,UAAU,CAAC,OAAO,aAAa,CAAC,CAAC;AACtD,eAAe,aAAa,CAAC"}
1
+ {"version":3,"file":"ContentEditor.svelte.d.ts","sourceRoot":"","sources":["../../../src/svelte/components/ContentEditor.svelte.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAEV,mCAAmC,EACnC,0CAA0C,EAE3C,MAAM,gCAAgC,CAAC;AAKxC,OAAO,KAAK,EAEV,kBAAkB,EAEnB,MAAM,wBAAwB,CAAC;AAEhC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAC;AAC1D,OAAO,EAKL,KAAK,wBAAwB,EAG7B,wBAAwB,EAEzB,MAAM,wBAAwB,CAAC;AAShC,KAAK,qBAAqB,GAAG,UAAU,CAAC,OAAO,wBAAwB,CAAC,CAAC;AAEzE,MAAM,WAAW,KAAK;IACpB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,OAAO,CAAC,EAAE,WAAW,GAAG,IAAI,CAAC;IAC7B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,kBAAkB,GAAG,IAAI,CAAC;IACtC,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B,eAAe,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,uBAAuB,CAAC,EAAE,0CAA0C,CAAC;IACrE,wBAAwB,CAAC,EAAE,mCAAmC,CAAC;IAC/D,QAAQ,CAAC,EAAE,CAAC,IAAI,EAAE,qBAAqB,KAAK,IAAI,CAAC;IACjD,iBAAiB,CAAC,EAAE,CAAC,KAAK,EAAE,kBAAkB,GAAG,IAAI,KAAK,IAAI,CAAC;IAC/D,MAAM,EAAE,CAAC,IAAI,EAAE,wBAAwB,KAAK,IAAI,CAAC;IACjD,QAAQ,EAAE,MAAM,IAAI,CAAC;CACtB;AAoxCD,QAAA,MAAM,aAAa;;MAAwC,CAAC;AAC5D,KAAK,aAAa,GAAG,UAAU,CAAC,OAAO,aAAa,CAAC,CAAC;AACtD,eAAe,aAAa,CAAC"}
@@ -56,8 +56,10 @@ async function loadDefinitions() {
56
56
  const response = await governanceClient.contents.getGovernanceDefinitions();
57
57
  definitions = response.data;
58
58
  onChange?.(response.data);
59
- } catch (err: any) {
60
- error = err.message || 'Failed to load governance definitions';
59
+ } catch (err) {
60
+ error =
61
+ (err instanceof Error ? err.message : '') ||
62
+ 'Failed to load governance definitions';
61
63
  } finally {
62
64
  loading = false;
63
65
  }
@@ -1 +1 @@
1
- {"version":3,"file":"ContentGovernanceManager.svelte.d.ts","sourceRoot":"","sources":["../../../src/svelte/components/ContentGovernanceManager.svelte.ts"],"names":[],"mappings":"AAMA,OAAO,EAEL,KAAK,gCAAgC,EAItC,MAAM,wBAAwB,CAAC;AAEhC,OAAO,KAAK,EAAE,8BAA8B,EAAE,MAAM,8BAA8B,CAAC;AASnF,MAAM,WAAW,KAAK;IACpB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,8BAA8B,CAAC;IACxC,QAAQ,CAAC,EAAE,CAAC,WAAW,EAAE,gCAAgC,GAAG,IAAI,KAAK,IAAI,CAAC;CAC3E;AAkRD,QAAA,MAAM,wBAAwB,2CAAwC,CAAC;AACvE,KAAK,wBAAwB,GAAG,UAAU,CAAC,OAAO,wBAAwB,CAAC,CAAC;AAC5E,eAAe,wBAAwB,CAAC"}
1
+ {"version":3,"file":"ContentGovernanceManager.svelte.d.ts","sourceRoot":"","sources":["../../../src/svelte/components/ContentGovernanceManager.svelte.ts"],"names":[],"mappings":"AAMA,OAAO,EAEL,KAAK,gCAAgC,EAItC,MAAM,wBAAwB,CAAC;AAEhC,OAAO,KAAK,EAAE,8BAA8B,EAAE,MAAM,8BAA8B,CAAC;AASnF,MAAM,WAAW,KAAK;IACpB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,8BAA8B,CAAC;IACxC,QAAQ,CAAC,EAAE,CAAC,WAAW,EAAE,gCAAgC,GAAG,IAAI,KAAK,IAAI,CAAC;CAC3E;AAoRD,QAAA,MAAM,wBAAwB,2CAAwC,CAAC;AACvE,KAAK,wBAAwB,GAAG,UAAU,CAAC,OAAO,wBAAwB,CAAC,CAAC;AAC5E,eAAe,wBAAwB,CAAC"}
@@ -568,10 +568,10 @@ async function searchFacts(query = factQuery, page = 1) {
568
568
  catalogPage = nextPage;
569
569
  catalogHasNextPage = rows.length > FACT_CATALOG_PAGE_SIZE;
570
570
  catalogBrowseQuery = query;
571
- } catch (err: any) {
571
+ } catch (err) {
572
572
  catalogFacts = [];
573
573
  catalogHasNextPage = false;
574
- catalogError = err.message || 'Failed to browse facts';
574
+ catalogError = (err instanceof Error ? err.message : '') || 'Failed to browse facts';
575
575
  } finally {
576
576
  catalogLoading = false;
577
577
  }
@@ -621,8 +621,8 @@ async function syncFactsIfSaved(nextFacts: FactData[]) {
621
621
  updateSelectedFacts(response.data.facts || nextFacts);
622
622
  await Promise.all([refreshGovernanceState(), refreshTransparency()]);
623
623
  workflowNotice = 'Saved fact associations.';
624
- } catch (err: any) {
625
- workflowError = err.message || 'Failed to sync facts';
624
+ } catch (err) {
625
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to sync facts';
626
626
  } finally {
627
627
  syncingFacts = false;
628
628
  }
@@ -644,8 +644,8 @@ async function repairFactAudit() {
644
644
  onFactAuditChange?.(response.data);
645
645
  const factsResponse = await client.contents.getFacts(savedContentId);
646
646
  updateSelectedFacts(factsResponse.data.facts || []);
647
- } catch (err: any) {
648
- workflowError = err.message || 'Failed to repair fact audit';
647
+ } catch (err) {
648
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to repair fact audit';
649
649
  } finally {
650
650
  factAuditBusy = false;
651
651
  }
@@ -668,8 +668,8 @@ async function recheckFactClaims(claimIds: string[]) {
668
668
  workflowNotice = `Rechecked ${claimIds.length} claim${claimIds.length === 1 ? '' : 's'} against current evidence.`;
669
669
  selectedClaimIds = selectedClaimIds.filter((id) => !claimIds.includes(id));
670
670
  onFactAuditChange?.(response.data);
671
- } catch (err: any) {
672
- workflowError = err.message || 'Failed to recheck claim support';
671
+ } catch (err) {
672
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to recheck claim support';
673
673
  } finally {
674
674
  factAuditBusy = false;
675
675
  }
@@ -731,12 +731,12 @@ async function loadDraftGovernance() {
731
731
  activeCustomPolicyKey,
732
732
  customReviewPolicyKey,
733
733
  );
734
- } catch (err: any) {
734
+ } catch (err) {
735
735
  governanceState = null;
736
736
  governanceDefinitions = null;
737
737
  reviewProfiles = [];
738
738
  onGovernanceStateChange?.(null);
739
- workflowError = err.message || 'Failed to resolve content governance';
739
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to resolve content governance';
740
740
  } finally {
741
741
  workflowLoading = false;
742
742
  }
@@ -795,8 +795,8 @@ async function loadSavedWorkflow() {
795
795
  activeCustomPolicyKey,
796
796
  customReviewPolicyKey,
797
797
  );
798
- } catch (err: any) {
799
- workflowError = err.message || 'Failed to load governance workflow state';
798
+ } catch (err) {
799
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to load governance workflow state';
800
800
  } finally {
801
801
  workflowLoading = false;
802
802
  }
@@ -832,7 +832,7 @@ async function runReview(action: ReviewAction) {
832
832
  workflowNotice = null;
833
833
 
834
834
  try {
835
- const payload: Record<string, any> = {
835
+ const payload: Record<string, unknown> = {
836
836
  kind: action.kind,
837
837
  factIds: selectedFactIds,
838
838
  };
@@ -851,8 +851,8 @@ async function runReview(action: ReviewAction) {
851
851
  await Promise.all([refreshGovernanceState(), refreshTransparency()]);
852
852
  workflowNotice = `${action.label} completed.`;
853
853
  await refreshVersions();
854
- } catch (err: any) {
855
- workflowError = err.message || 'Failed to run content review';
854
+ } catch (err) {
855
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to run content review';
856
856
  } finally {
857
857
  reviewBusy = null;
858
858
  }
@@ -883,8 +883,8 @@ async function issueCorrection() {
883
883
 
884
884
  workflowNotice = 'Correction issued.';
885
885
  await loadSavedWorkflow();
886
- } catch (err: any) {
887
- workflowError = err.message || 'Failed to issue correction';
886
+ } catch (err) {
887
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to issue correction';
888
888
  } finally {
889
889
  correctionBusy = false;
890
890
  }
@@ -906,8 +906,8 @@ async function createSnapshot() {
906
906
  });
907
907
  workflowNotice = 'Snapshot created.';
908
908
  await Promise.all([refreshVersions(), refreshTransparency()]);
909
- } catch (err: any) {
910
- workflowError = err.message || 'Failed to create version snapshot';
909
+ } catch (err) {
910
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to create version snapshot';
911
911
  } finally {
912
912
  versionBusy = false;
913
913
  }
@@ -948,8 +948,8 @@ async function restoreVersion(versionNumber: number) {
948
948
  );
949
949
  workflowNotice = `Restored version ${versionNumber}.`;
950
950
  await loadSavedWorkflow();
951
- } catch (err: any) {
952
- workflowError = err.message || 'Failed to restore version';
951
+ } catch (err) {
952
+ workflowError = (err instanceof Error ? err.message : '') || 'Failed to restore version';
953
953
  } finally {
954
954
  versionBusy = false;
955
955
  }
@@ -5,11 +5,24 @@ import { useI18n } from '@happyvertical/smrt-ui/i18n';
5
5
  import { Button } from '@happyvertical/smrt-ui/ui';
6
6
  import type { Snippet } from 'svelte';
7
7
  import { untrack } from 'svelte';
8
+ import type { ContentData } from '../../mock-smrt-client.js';
8
9
  import { M } from '../i18n.contribution.js';
9
10
  import ImageThumbnail from './ImageThumbnail.svelte';
10
11
 
11
12
  const { t } = useI18n();
12
13
 
14
+ interface Props {
15
+ apiBaseUrl?: string;
16
+ contents: ContentData[];
17
+ type?: string;
18
+ defaultViewMode?: 'grid' | 'detailed' | 'compact';
19
+ onEdit: (content: ContentData) => void;
20
+ onDelete: (content: ContentData) => void;
21
+ onAdd: () => void;
22
+ controls?: Snippet;
23
+ getViewHref?: (content: ContentData) => string | null;
24
+ }
25
+
13
26
  let {
14
27
  apiBaseUrl = '/api/v1',
15
28
  contents,
@@ -20,17 +33,7 @@ let {
20
33
  onAdd,
21
34
  controls,
22
35
  getViewHref = undefined,
23
- } = $props<{
24
- apiBaseUrl?: string;
25
- contents: any[];
26
- type?: string;
27
- defaultViewMode?: 'grid' | 'detailed' | 'compact';
28
- onEdit: (content: any) => void;
29
- onDelete: (content: any) => void;
30
- onAdd: () => void;
31
- controls?: Snippet;
32
- getViewHref?: (content: any) => string | null;
33
- }>();
36
+ }: Props = $props();
34
37
 
35
38
  let searchTerm = $state('');
36
39
  let selectedType = $state('All Types');
@@ -47,15 +50,15 @@ function getTextValue(value: unknown): string {
47
50
  return typeof value === 'string' ? value : '';
48
51
  }
49
52
 
50
- function getDisplayTitle(content: any): string {
53
+ function getDisplayTitle(content: ContentData): string {
51
54
  return getTextValue(content.title) || 'Untitled content';
52
55
  }
53
56
 
54
- function getDisplayDescription(content: any): string {
57
+ function getDisplayDescription(content: ContentData): string {
55
58
  return getTextValue(content.description);
56
59
  }
57
60
 
58
- function getDisplayAuthor(content: any): string {
61
+ function getDisplayAuthor(content: ContentData): string {
59
62
  return getTextValue(content.author);
60
63
  }
61
64
 
@@ -64,7 +67,7 @@ function getNormalizedType(value: unknown): string {
64
67
  }
65
68
 
66
69
  const filteredContents = $derived(
67
- contents.filter((content: any) => {
70
+ contents.filter((content: ContentData) => {
68
71
  const title = getDisplayTitle(content);
69
72
  const description = getDisplayDescription(content);
70
73
  const author = getDisplayAuthor(content);
@@ -130,9 +133,9 @@ function getStateBadge(value: unknown) {
130
133
  }
131
134
  }
132
135
 
133
- let pendingDelete = $state<any | null>(null);
136
+ let pendingDelete = $state<ContentData | null>(null);
134
137
 
135
- function handleDeleteContent(content: any) {
138
+ function handleDeleteContent(content: ContentData) {
136
139
  pendingDelete = content;
137
140
  }
138
141