@ai-matrx/content-ir-react 0.19.1 → 0.20.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.
package/dist/index.d.cts CHANGED
@@ -1,7 +1,7 @@
1
1
  import { C as ComponentResolutionSource, a as ComponentResolution, b as ContentIrErrorReporter } from './component-resolution.types-DY4pGymy.cjs';
2
2
  export { c as ComponentRole, d as ContentIrErrorReport, J as JsonObject, K as KindComponentRow, S as SystemComponentEntry, e as consoleErrorReporter } from './component-resolution.types-DY4pGymy.cjs';
3
- import { C as ContentIrHost, K as KindRouteEnv, a as KindDefinitionSource, D as DirectiveFailure, b as DirectiveFailureWords, c as DirectiveRecordRef } from './route-KoRMp3Qn.cjs';
4
- export { d as ContentIrRenderSeams, e as DB_KIND_COMPONENT_KEY, f as DIRECTIVE_BLOCK_TYPE, g as DirectiveApplyResult, h as DirectiveApplyState, i as DirectiveAskRequest, j as DirectiveCopyProps, k as DirectiveHost, l as DirectiveHostProvider, m as DirectiveHostProviderProps, n as DirectiveOpenItemOptions, o as DirectiveRecordProps, p as DirectiveScope, q as DirectiveScopeProvider, r as DirectiveShell, G as GENERIC_STRUCTURED_COMPONENT_KEY, s as GenericFallbackReason, I as IR_PROVISIONAL_KEY, t as IR_ROUTE_KEY, u as IrRenderBlock, v as IrRoutableBlock, w as IrRouteMarker, x as KindRouteBinding, y as KindRouteOptions, P as PartialRenderOptions, z as ProvisionalKindRender, S as StructuredValueRenderProps, A as SupersededKindRender, B as applyIrKindRoute, E as createKindRouteBinding, F as envelopeFromPartialKind, H as isPartialReadyKind, J as isProvisionalBlock, L as kindServerDataFromStoredValue, M as markKindPartialUnsafe, N as readIrRouteMarker, O as resetPartialUnsafeKinds, Q as resetSourcelessDbRowReports, R as resolveAnnouncedKindLoading, T as resolveProvisionalKindRender, U as resolveSupersededKindRender, V as routeEnvOf, W as useDirectiveHost, X as useDirectiveScope } from './route-KoRMp3Qn.cjs';
3
+ import { C as ContentIrHost, K as KindRouteEnv, a as KindDefinitionSource, D as DirectiveHost, b as DirectiveFailure, c as DirectiveFailureWords, d as DirectiveRecordRef } from './route-DMTBn8w4.cjs';
4
+ export { e as ContentIrRenderSeams, f as DB_KIND_COMPONENT_KEY, g as DIRECTIVE_BLOCK_TYPE, h as DirectiveApplyResult, i as DirectiveApplyState, j as DirectiveAskRequest, k as DirectiveCopyProps, l as DirectiveHostProvider, m as DirectiveHostProviderProps, n as DirectiveOpenItemOptions, o as DirectiveRecordProps, p as DirectiveScope, q as DirectiveScopeProvider, r as DirectiveShell, s as DirectiveValueRef, G as GENERIC_STRUCTURED_COMPONENT_KEY, t as GenericFallbackReason, I as IR_PROVISIONAL_KEY, u as IR_ROUTE_KEY, v as IrRenderBlock, w as IrRoutableBlock, x as IrRouteMarker, y as KindRouteBinding, z as KindRouteOptions, P as PartialRenderOptions, A as ProvisionalKindRender, S as StructuredValueRenderProps, B as SupersededKindRender, E as applyIrKindRoute, F as createKindRouteBinding, H as envelopeFromPartialKind, J as isPartialReadyKind, L as isProvisionalBlock, M as kindServerDataFromStoredValue, N as markKindPartialUnsafe, O as readIrRouteMarker, Q as resetPartialUnsafeKinds, R as resetSourcelessDbRowReports, T as resolveAnnouncedKindLoading, U as resolveProvisionalKindRender, V as resolveSupersededKindRender, W as routeEnvOf, X as useDirectiveHost, Y as useDirectiveScope } from './route-DMTBn8w4.cjs';
5
5
  import * as react from 'react';
6
6
  import react__default, { ReactNode, ComponentType } from 'react';
7
7
  export { ComponentResolver, ComponentResolverOptions } from './resolver.cjs';
@@ -301,12 +301,33 @@ declare function ApplyDirectiveButton({ directive, label, itemCount, onApplied,
301
301
  */
302
302
  /** Classes whose items point at an EXISTING record by `id`. */
303
303
  declare const TARGETING_CLASSES: ReadonlySet<string>;
304
- /** How long a changed value may read before it is shortened (full value on hover). */
305
- declare const CHANGE_VALUE_MAX = 60;
304
+ /**
305
+ * How long a changed value may read before it is shortened. A value someone
306
+ * must judge — a title, a status, a date — is always whole (G8A review: a 60
307
+ * cap plus CSS truncation cut "Review4 tasks…" on a phone); only a body of
308
+ * prose longer than this is shortened, whole on hover and in View/Copy.
309
+ */
310
+ declare const CHANGE_VALUE_MAX = 280;
306
311
  /** The id of the existing record an update/delete item targets, or null. */
307
312
  declare function itemRecordId(item: Record<string, unknown>): string | null;
308
- /** "due_date" → "Due date". Underscores read as developer output. */
313
+ /** "due_date" → "Due Date" — THE humanizer; underscores read as developer output. */
309
314
  declare function fieldLabel(key: string): string;
315
+ /**
316
+ * THE ONE FIELD-LABEL RULE for a directive — card rows, card facts and the
317
+ * host's confirm: the noun's title column reads "Title" whatever it is stored
318
+ * as (a workbook's `workbook_name`, a note's `label`), every other field reads
319
+ * through THE humanizer. A new workbook card said "workbook name" while its
320
+ * confirm said "Title" (G8A review, 2026-10-02).
321
+ */
322
+ declare function directiveFieldLabel(key: string, titleColumn: string | null | undefined): string;
323
+ /**
324
+ * The app's word for ONE stored value of ONE field — "incomplete" on a task
325
+ * reads "Inbox", "high" reads "High". The host answers it for its pick-list
326
+ * fields; null → the value as stored.
327
+ */
328
+ type DirectiveValueWord = (field: string, value: string) => string | null;
329
+ /** How an empty value reads — before or after, on the card and in the confirm. */
330
+ declare const EMPTY_VALUE_WORD = "None";
310
331
  /** A short, honest name for a record we could not look up: "Task 1a2b3c4d". */
311
332
  declare function recordFallbackName(nounLabel: string, id: string): string;
312
333
  /** One value as a row reads it: shortened, the whole of it, and whether it is empty. */
@@ -329,7 +350,7 @@ interface ItemChange extends ChangeValue {
329
350
  same?: boolean;
330
351
  }
331
352
  /** One value, described for a change row (`value` shortened, `full` whole). */
332
- declare function describeChangeValue(value: unknown): ChangeValue;
353
+ declare function describeChangeValue(value: unknown, word?: (value: string) => string | null): ChangeValue;
333
354
  /**
334
355
  * Every field an UPDATE item sets, in the order the item carries them — ALL of
335
356
  * them, never a sample: a person approving an overwrite sees the whole of it.
@@ -346,17 +367,27 @@ interface ItemChangesOptions {
346
367
  * (reviewer, 2026-10-02). The same rule the directive builder's form uses.
347
368
  */
348
369
  titleColumn?: string | null;
370
+ /** The app's word for a stored value (`DirectiveHost.valueLabel`, bound to the noun). */
371
+ valueWord?: DirectiveValueWord | null;
349
372
  }
350
373
  declare function itemChanges(item: Record<string, unknown>, current?: Record<string, unknown> | null, options?: ItemChangesOptions): ItemChange[];
351
374
 
352
375
  interface SideEffectDirectiveCardProps {
353
376
  directive: DecodedDirective;
354
377
  }
378
+ /** The host's value words for one record type, or null when it has none. */
379
+ declare function directiveValueWord(host: Pick<DirectiveHost, "valueLabel">, noun: string): DirectiveValueWord | null;
355
380
  /**
356
381
  * THE CHANGE LIST — every field an update sets, as "Label old → new" when the
357
382
  * record's current value is known, "Label → new" when it is not. ONE component
358
383
  * for the card row and the host's confirm dialog, so the two can never read
359
384
  * differently (reviewer, 2026-10-02: the confirm showed only the new value).
385
+ *
386
+ * 🚨 A VALUE SOMEONE MUST JUDGE IS NEVER CUT (G8A review, 2026-10-02): on a
387
+ * phone the card is ~230px and the row read "Title Review… → Review4 tas…".
388
+ * Values wrap; below a 20rem container the label, the old value and the new
389
+ * value stack, one per line. Measured on the list's own width (a container
390
+ * query), so a narrow window panel on a desktop gets the same stacking.
360
391
  */
361
392
  declare function DirectiveChangeList({ changes, className, }: {
362
393
  changes: ItemChange[];
@@ -702,4 +733,4 @@ declare class DbKindComponentErrorBoundary extends react.Component<DbKindCompone
702
733
  render(): react.ReactNode;
703
734
  }
704
735
 
705
- export { ApplyDirectiveButton, type ApplyDirectiveButtonProps, CHANGE_VALUE_MAX, type ChangeValue, type CompiledDbKindComponent, ComponentResolution, ComponentResolutionSource, ContentIrErrorReporter, ContentIrHost, ContentIrRenderProvider, type ContentIrRenderProviderProps, type DbKindActionResult, type DbKindCompileResult, type DbKindComponentCache, type DbKindComponentCachePorts, type DbKindComponentCompiler, DbKindComponentErrorBoundary, type DbKindComponentErrorBoundaryProps, type DbKindComponentIncident, type DbKindComponentIncidentSink, type DbKindComponentIncidentType, type DbKindComponentRenderProps, DelegatedOutput, type DelegatedOutputProps, type DirectiveApplyPhase, DirectiveChangeList, DirectiveFailure, DirectiveFailureWords, DirectiveFallbackCard, type DirectiveFallbackCardProps, DirectiveProvisionalCard, type DirectiveProvisionalCardProps, DirectiveRecordRef, DirectiveRender, type DirectiveRenderProps, type DirectiveRenderer, type DirectiveRendererProps, GenericStructuredView, type GenericStructuredViewProps, type ItemChange, type ItemChangesOptions, type KindComponentUiOptions, KindDefinitionSource, KindInstanceRender, type KindInstanceRenderProps, KindRouteEnv, type KindVersionSources, NodeOutcomeView, type NodeOutcomeViewProps, ProvisionalKindBoundary, ProvisionalKindFrame, type RecordReader, type RecordValues, type RecordValuesStatus, type ResolveKindValue, type RunDbKindAction, RunResultView, type RunResultViewProps, SideEffectDirectiveCard, type SideEffectDirectiveCardProps, TARGETING_CLASSES, createDbKindComponentCache, defaultFailureWords, describeChangeValue, failureWords, fieldLabel, getDirectiveRenderer, isDbKindComponentBodyPending, isRecordValue, itemChanges, itemRecordId, kindIsRoutable, noteRecordChanged, provisionalDirectiveSlug, readsApplyLedger, recordFallbackName, recordRevision, registerDirectiveRenderer, resetDirectiveRenderers, useContentIrHost, useContentIrHostOrNull, useContentIrKindVersion, useKindRouteEnv, useRecordRevision, useRecordValues };
736
+ export { ApplyDirectiveButton, type ApplyDirectiveButtonProps, CHANGE_VALUE_MAX, type ChangeValue, type CompiledDbKindComponent, ComponentResolution, ComponentResolutionSource, ContentIrErrorReporter, ContentIrHost, ContentIrRenderProvider, type ContentIrRenderProviderProps, type DbKindActionResult, type DbKindCompileResult, type DbKindComponentCache, type DbKindComponentCachePorts, type DbKindComponentCompiler, DbKindComponentErrorBoundary, type DbKindComponentErrorBoundaryProps, type DbKindComponentIncident, type DbKindComponentIncidentSink, type DbKindComponentIncidentType, type DbKindComponentRenderProps, DelegatedOutput, type DelegatedOutputProps, type DirectiveApplyPhase, DirectiveChangeList, DirectiveFailure, DirectiveFailureWords, DirectiveFallbackCard, type DirectiveFallbackCardProps, DirectiveHost, DirectiveProvisionalCard, type DirectiveProvisionalCardProps, DirectiveRecordRef, DirectiveRender, type DirectiveRenderProps, type DirectiveRenderer, type DirectiveRendererProps, type DirectiveValueWord, EMPTY_VALUE_WORD, GenericStructuredView, type GenericStructuredViewProps, type ItemChange, type ItemChangesOptions, type KindComponentUiOptions, KindDefinitionSource, KindInstanceRender, type KindInstanceRenderProps, KindRouteEnv, type KindVersionSources, NodeOutcomeView, type NodeOutcomeViewProps, ProvisionalKindBoundary, ProvisionalKindFrame, type RecordReader, type RecordValues, type RecordValuesStatus, type ResolveKindValue, type RunDbKindAction, RunResultView, type RunResultViewProps, SideEffectDirectiveCard, type SideEffectDirectiveCardProps, TARGETING_CLASSES, createDbKindComponentCache, defaultFailureWords, describeChangeValue, directiveFieldLabel, directiveValueWord, failureWords, fieldLabel, getDirectiveRenderer, isDbKindComponentBodyPending, isRecordValue, itemChanges, itemRecordId, kindIsRoutable, noteRecordChanged, provisionalDirectiveSlug, readsApplyLedger, recordFallbackName, recordRevision, registerDirectiveRenderer, resetDirectiveRenderers, useContentIrHost, useContentIrHostOrNull, useContentIrKindVersion, useKindRouteEnv, useRecordRevision, useRecordValues };
package/dist/index.d.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  import { C as ComponentResolutionSource, a as ComponentResolution, b as ContentIrErrorReporter } from './component-resolution.types-DY4pGymy.js';
2
2
  export { c as ComponentRole, d as ContentIrErrorReport, J as JsonObject, K as KindComponentRow, S as SystemComponentEntry, e as consoleErrorReporter } from './component-resolution.types-DY4pGymy.js';
3
- import { C as ContentIrHost, K as KindRouteEnv, a as KindDefinitionSource, D as DirectiveFailure, b as DirectiveFailureWords, c as DirectiveRecordRef } from './route-CtYw2cTN.js';
4
- export { d as ContentIrRenderSeams, e as DB_KIND_COMPONENT_KEY, f as DIRECTIVE_BLOCK_TYPE, g as DirectiveApplyResult, h as DirectiveApplyState, i as DirectiveAskRequest, j as DirectiveCopyProps, k as DirectiveHost, l as DirectiveHostProvider, m as DirectiveHostProviderProps, n as DirectiveOpenItemOptions, o as DirectiveRecordProps, p as DirectiveScope, q as DirectiveScopeProvider, r as DirectiveShell, G as GENERIC_STRUCTURED_COMPONENT_KEY, s as GenericFallbackReason, I as IR_PROVISIONAL_KEY, t as IR_ROUTE_KEY, u as IrRenderBlock, v as IrRoutableBlock, w as IrRouteMarker, x as KindRouteBinding, y as KindRouteOptions, P as PartialRenderOptions, z as ProvisionalKindRender, S as StructuredValueRenderProps, A as SupersededKindRender, B as applyIrKindRoute, E as createKindRouteBinding, F as envelopeFromPartialKind, H as isPartialReadyKind, J as isProvisionalBlock, L as kindServerDataFromStoredValue, M as markKindPartialUnsafe, N as readIrRouteMarker, O as resetPartialUnsafeKinds, Q as resetSourcelessDbRowReports, R as resolveAnnouncedKindLoading, T as resolveProvisionalKindRender, U as resolveSupersededKindRender, V as routeEnvOf, W as useDirectiveHost, X as useDirectiveScope } from './route-CtYw2cTN.js';
3
+ import { C as ContentIrHost, K as KindRouteEnv, a as KindDefinitionSource, D as DirectiveHost, b as DirectiveFailure, c as DirectiveFailureWords, d as DirectiveRecordRef } from './route-CiCUQGAB.js';
4
+ export { e as ContentIrRenderSeams, f as DB_KIND_COMPONENT_KEY, g as DIRECTIVE_BLOCK_TYPE, h as DirectiveApplyResult, i as DirectiveApplyState, j as DirectiveAskRequest, k as DirectiveCopyProps, l as DirectiveHostProvider, m as DirectiveHostProviderProps, n as DirectiveOpenItemOptions, o as DirectiveRecordProps, p as DirectiveScope, q as DirectiveScopeProvider, r as DirectiveShell, s as DirectiveValueRef, G as GENERIC_STRUCTURED_COMPONENT_KEY, t as GenericFallbackReason, I as IR_PROVISIONAL_KEY, u as IR_ROUTE_KEY, v as IrRenderBlock, w as IrRoutableBlock, x as IrRouteMarker, y as KindRouteBinding, z as KindRouteOptions, P as PartialRenderOptions, A as ProvisionalKindRender, S as StructuredValueRenderProps, B as SupersededKindRender, E as applyIrKindRoute, F as createKindRouteBinding, H as envelopeFromPartialKind, J as isPartialReadyKind, L as isProvisionalBlock, M as kindServerDataFromStoredValue, N as markKindPartialUnsafe, O as readIrRouteMarker, Q as resetPartialUnsafeKinds, R as resetSourcelessDbRowReports, T as resolveAnnouncedKindLoading, U as resolveProvisionalKindRender, V as resolveSupersededKindRender, W as routeEnvOf, X as useDirectiveHost, Y as useDirectiveScope } from './route-CiCUQGAB.js';
5
5
  import * as react from 'react';
6
6
  import react__default, { ReactNode, ComponentType } from 'react';
7
7
  export { ComponentResolver, ComponentResolverOptions } from './resolver.js';
@@ -301,12 +301,33 @@ declare function ApplyDirectiveButton({ directive, label, itemCount, onApplied,
301
301
  */
302
302
  /** Classes whose items point at an EXISTING record by `id`. */
303
303
  declare const TARGETING_CLASSES: ReadonlySet<string>;
304
- /** How long a changed value may read before it is shortened (full value on hover). */
305
- declare const CHANGE_VALUE_MAX = 60;
304
+ /**
305
+ * How long a changed value may read before it is shortened. A value someone
306
+ * must judge — a title, a status, a date — is always whole (G8A review: a 60
307
+ * cap plus CSS truncation cut "Review4 tasks…" on a phone); only a body of
308
+ * prose longer than this is shortened, whole on hover and in View/Copy.
309
+ */
310
+ declare const CHANGE_VALUE_MAX = 280;
306
311
  /** The id of the existing record an update/delete item targets, or null. */
307
312
  declare function itemRecordId(item: Record<string, unknown>): string | null;
308
- /** "due_date" → "Due date". Underscores read as developer output. */
313
+ /** "due_date" → "Due Date" — THE humanizer; underscores read as developer output. */
309
314
  declare function fieldLabel(key: string): string;
315
+ /**
316
+ * THE ONE FIELD-LABEL RULE for a directive — card rows, card facts and the
317
+ * host's confirm: the noun's title column reads "Title" whatever it is stored
318
+ * as (a workbook's `workbook_name`, a note's `label`), every other field reads
319
+ * through THE humanizer. A new workbook card said "workbook name" while its
320
+ * confirm said "Title" (G8A review, 2026-10-02).
321
+ */
322
+ declare function directiveFieldLabel(key: string, titleColumn: string | null | undefined): string;
323
+ /**
324
+ * The app's word for ONE stored value of ONE field — "incomplete" on a task
325
+ * reads "Inbox", "high" reads "High". The host answers it for its pick-list
326
+ * fields; null → the value as stored.
327
+ */
328
+ type DirectiveValueWord = (field: string, value: string) => string | null;
329
+ /** How an empty value reads — before or after, on the card and in the confirm. */
330
+ declare const EMPTY_VALUE_WORD = "None";
310
331
  /** A short, honest name for a record we could not look up: "Task 1a2b3c4d". */
311
332
  declare function recordFallbackName(nounLabel: string, id: string): string;
312
333
  /** One value as a row reads it: shortened, the whole of it, and whether it is empty. */
@@ -329,7 +350,7 @@ interface ItemChange extends ChangeValue {
329
350
  same?: boolean;
330
351
  }
331
352
  /** One value, described for a change row (`value` shortened, `full` whole). */
332
- declare function describeChangeValue(value: unknown): ChangeValue;
353
+ declare function describeChangeValue(value: unknown, word?: (value: string) => string | null): ChangeValue;
333
354
  /**
334
355
  * Every field an UPDATE item sets, in the order the item carries them — ALL of
335
356
  * them, never a sample: a person approving an overwrite sees the whole of it.
@@ -346,17 +367,27 @@ interface ItemChangesOptions {
346
367
  * (reviewer, 2026-10-02). The same rule the directive builder's form uses.
347
368
  */
348
369
  titleColumn?: string | null;
370
+ /** The app's word for a stored value (`DirectiveHost.valueLabel`, bound to the noun). */
371
+ valueWord?: DirectiveValueWord | null;
349
372
  }
350
373
  declare function itemChanges(item: Record<string, unknown>, current?: Record<string, unknown> | null, options?: ItemChangesOptions): ItemChange[];
351
374
 
352
375
  interface SideEffectDirectiveCardProps {
353
376
  directive: DecodedDirective;
354
377
  }
378
+ /** The host's value words for one record type, or null when it has none. */
379
+ declare function directiveValueWord(host: Pick<DirectiveHost, "valueLabel">, noun: string): DirectiveValueWord | null;
355
380
  /**
356
381
  * THE CHANGE LIST — every field an update sets, as "Label old → new" when the
357
382
  * record's current value is known, "Label → new" when it is not. ONE component
358
383
  * for the card row and the host's confirm dialog, so the two can never read
359
384
  * differently (reviewer, 2026-10-02: the confirm showed only the new value).
385
+ *
386
+ * 🚨 A VALUE SOMEONE MUST JUDGE IS NEVER CUT (G8A review, 2026-10-02): on a
387
+ * phone the card is ~230px and the row read "Title Review… → Review4 tas…".
388
+ * Values wrap; below a 20rem container the label, the old value and the new
389
+ * value stack, one per line. Measured on the list's own width (a container
390
+ * query), so a narrow window panel on a desktop gets the same stacking.
360
391
  */
361
392
  declare function DirectiveChangeList({ changes, className, }: {
362
393
  changes: ItemChange[];
@@ -702,4 +733,4 @@ declare class DbKindComponentErrorBoundary extends react.Component<DbKindCompone
702
733
  render(): react.ReactNode;
703
734
  }
704
735
 
705
- export { ApplyDirectiveButton, type ApplyDirectiveButtonProps, CHANGE_VALUE_MAX, type ChangeValue, type CompiledDbKindComponent, ComponentResolution, ComponentResolutionSource, ContentIrErrorReporter, ContentIrHost, ContentIrRenderProvider, type ContentIrRenderProviderProps, type DbKindActionResult, type DbKindCompileResult, type DbKindComponentCache, type DbKindComponentCachePorts, type DbKindComponentCompiler, DbKindComponentErrorBoundary, type DbKindComponentErrorBoundaryProps, type DbKindComponentIncident, type DbKindComponentIncidentSink, type DbKindComponentIncidentType, type DbKindComponentRenderProps, DelegatedOutput, type DelegatedOutputProps, type DirectiveApplyPhase, DirectiveChangeList, DirectiveFailure, DirectiveFailureWords, DirectiveFallbackCard, type DirectiveFallbackCardProps, DirectiveProvisionalCard, type DirectiveProvisionalCardProps, DirectiveRecordRef, DirectiveRender, type DirectiveRenderProps, type DirectiveRenderer, type DirectiveRendererProps, GenericStructuredView, type GenericStructuredViewProps, type ItemChange, type ItemChangesOptions, type KindComponentUiOptions, KindDefinitionSource, KindInstanceRender, type KindInstanceRenderProps, KindRouteEnv, type KindVersionSources, NodeOutcomeView, type NodeOutcomeViewProps, ProvisionalKindBoundary, ProvisionalKindFrame, type RecordReader, type RecordValues, type RecordValuesStatus, type ResolveKindValue, type RunDbKindAction, RunResultView, type RunResultViewProps, SideEffectDirectiveCard, type SideEffectDirectiveCardProps, TARGETING_CLASSES, createDbKindComponentCache, defaultFailureWords, describeChangeValue, failureWords, fieldLabel, getDirectiveRenderer, isDbKindComponentBodyPending, isRecordValue, itemChanges, itemRecordId, kindIsRoutable, noteRecordChanged, provisionalDirectiveSlug, readsApplyLedger, recordFallbackName, recordRevision, registerDirectiveRenderer, resetDirectiveRenderers, useContentIrHost, useContentIrHostOrNull, useContentIrKindVersion, useKindRouteEnv, useRecordRevision, useRecordValues };
736
+ export { ApplyDirectiveButton, type ApplyDirectiveButtonProps, CHANGE_VALUE_MAX, type ChangeValue, type CompiledDbKindComponent, ComponentResolution, ComponentResolutionSource, ContentIrErrorReporter, ContentIrHost, ContentIrRenderProvider, type ContentIrRenderProviderProps, type DbKindActionResult, type DbKindCompileResult, type DbKindComponentCache, type DbKindComponentCachePorts, type DbKindComponentCompiler, DbKindComponentErrorBoundary, type DbKindComponentErrorBoundaryProps, type DbKindComponentIncident, type DbKindComponentIncidentSink, type DbKindComponentIncidentType, type DbKindComponentRenderProps, DelegatedOutput, type DelegatedOutputProps, type DirectiveApplyPhase, DirectiveChangeList, DirectiveFailure, DirectiveFailureWords, DirectiveFallbackCard, type DirectiveFallbackCardProps, DirectiveHost, DirectiveProvisionalCard, type DirectiveProvisionalCardProps, DirectiveRecordRef, DirectiveRender, type DirectiveRenderProps, type DirectiveRenderer, type DirectiveRendererProps, type DirectiveValueWord, EMPTY_VALUE_WORD, GenericStructuredView, type GenericStructuredViewProps, type ItemChange, type ItemChangesOptions, type KindComponentUiOptions, KindDefinitionSource, KindInstanceRender, type KindInstanceRenderProps, KindRouteEnv, type KindVersionSources, NodeOutcomeView, type NodeOutcomeViewProps, ProvisionalKindBoundary, ProvisionalKindFrame, type RecordReader, type RecordValues, type RecordValuesStatus, type ResolveKindValue, type RunDbKindAction, RunResultView, type RunResultViewProps, SideEffectDirectiveCard, type SideEffectDirectiveCardProps, TARGETING_CLASSES, createDbKindComponentCache, defaultFailureWords, describeChangeValue, directiveFieldLabel, directiveValueWord, failureWords, fieldLabel, getDirectiveRenderer, isDbKindComponentBodyPending, isRecordValue, itemChanges, itemRecordId, kindIsRoutable, noteRecordChanged, provisionalDirectiveSlug, readsApplyLedger, recordFallbackName, recordRevision, registerDirectiveRenderer, resetDirectiveRenderers, useContentIrHost, useContentIrHostOrNull, useContentIrKindVersion, useKindRouteEnv, useRecordRevision, useRecordValues };
package/dist/index.js CHANGED
@@ -758,9 +758,10 @@ import { nounLabel } from "@ai-matrx/content-ir";
758
758
 
759
759
  // directives/item-changes.ts
760
760
  import { isUuidShape } from "@ai-matrx/kit/uuid";
761
+ import { humanizeIdentifier } from "@ai-matrx/kit/text-case";
761
762
  var TARGETING_CLASSES = /* @__PURE__ */ new Set(["update", "delete"]);
762
763
  var NOT_A_CHANGE = /* @__PURE__ */ new Set(["__kind", "id"]);
763
- var CHANGE_VALUE_MAX = 60;
764
+ var CHANGE_VALUE_MAX = 280;
764
765
  function itemRecordId(item) {
765
766
  const id = item.id;
766
767
  if (typeof id === "string" && id.trim()) return id.trim();
@@ -768,21 +769,27 @@ function itemRecordId(item) {
768
769
  return null;
769
770
  }
770
771
  function fieldLabel(key) {
771
- const spaced = key.replace(/_/g, " ").trim();
772
- return spaced.charAt(0).toUpperCase() + spaced.slice(1);
772
+ return humanizeIdentifier(key) || key;
773
773
  }
774
+ function directiveFieldLabel(key, titleColumn) {
775
+ return titleColumn && key === titleColumn ? "Title" : fieldLabel(key);
776
+ }
777
+ var EMPTY_VALUE_WORD = "None";
774
778
  function recordFallbackName(nounLabel3, id) {
775
779
  const short = isUuidShape(id) ? id.slice(0, 8) : id.length > 12 ? `${id.slice(0, 12)}\u2026` : id;
776
780
  return `${nounLabel3} ${short}`;
777
781
  }
778
- function describeChangeValue(value) {
779
- return describeValue(value);
782
+ function describeChangeValue(value, word) {
783
+ return describeValue(value, word);
780
784
  }
781
- function describeValue(value) {
782
- if (value === null || value === void 0) return { value: "cleared", full: "cleared", clears: true };
785
+ var EMPTY = { value: EMPTY_VALUE_WORD, full: EMPTY_VALUE_WORD, clears: true };
786
+ function describeValue(value, word) {
787
+ if (value === null || value === void 0) return EMPTY;
783
788
  if (typeof value === "string") {
784
789
  const trimmed = value.trim();
785
- if (!trimmed) return { value: "cleared", full: "cleared", clears: true };
790
+ if (!trimmed) return EMPTY;
791
+ const named = word?.(trimmed) ?? null;
792
+ if (named) return { value: named, full: named, clears: false };
786
793
  const oneLine = trimmed.replace(/\s+/g, " ");
787
794
  const shown = oneLine.length > CHANGE_VALUE_MAX ? `${oneLine.slice(0, CHANGE_VALUE_MAX - 1)}\u2026` : oneLine;
788
795
  return { value: shown, full: trimmed, clears: false };
@@ -792,11 +799,11 @@ function describeValue(value) {
792
799
  }
793
800
  if (Array.isArray(value)) {
794
801
  const n2 = value.length;
795
- const text2 = n2 === 0 ? "cleared" : `${n2} ${n2 === 1 ? "entry" : "entries"}`;
802
+ const text2 = n2 === 0 ? EMPTY_VALUE_WORD : `${n2} ${n2 === 1 ? "entry" : "entries"}`;
796
803
  return { value: text2, full: safeJson(value), clears: n2 === 0 };
797
804
  }
798
805
  const n = Object.keys(value).length;
799
- const text = n === 0 ? "cleared" : `${n} ${n === 1 ? "field" : "fields"}`;
806
+ const text = n === 0 ? EMPTY_VALUE_WORD : `${n} ${n === 1 ? "field" : "fields"}`;
800
807
  return { value: text, full: safeJson(value), clears: n === 0 };
801
808
  }
802
809
  function safeJson(value) {
@@ -821,10 +828,12 @@ function itemChanges(item, current, options = {}) {
821
828
  const titleColumn = options.titleColumn ?? null;
822
829
  for (const [key, raw] of Object.entries(item)) {
823
830
  if (NOT_A_CHANGE.has(key)) continue;
824
- const label = key === titleColumn ? "Title" : fieldLabel(key);
825
- const change = { key, label, ...describeValue(raw) };
831
+ const label = directiveFieldLabel(key, titleColumn);
832
+ const valueWord = options.valueWord;
833
+ const word = key === titleColumn || !valueWord ? void 0 : (v) => valueWord(key, v);
834
+ const change = { key, label, ...describeValue(raw, word) };
826
835
  if (current && Object.prototype.hasOwnProperty.call(current, key)) {
827
- change.before = describeValue(current[key]);
836
+ change.before = describeValue(current[key], word);
828
837
  change.same = sameValue(current[key], raw);
829
838
  }
830
839
  out.push(change);
@@ -1280,7 +1289,7 @@ function ApplyDirectiveButton({
1280
1289
  type: "button",
1281
1290
  disabled: askingAgain,
1282
1291
  onClick: () => void handleApply(!bad),
1283
- className: "inline-flex items-center gap-1 rounded px-1 py-0.5 text-muted-foreground hover:bg-accent hover:text-accent-foreground disabled:opacity-50",
1292
+ className: "inline-flex shrink-0 items-center gap-1 whitespace-nowrap rounded px-1 py-0.5 text-muted-foreground hover:bg-accent hover:text-accent-foreground disabled:opacity-50",
1284
1293
  "data-apply-action": bad ? "retry" : "run-again",
1285
1294
  children: [
1286
1295
  /* @__PURE__ */ jsx4(RotateCcwIcon, { className: "h-3 w-3" }),
@@ -1320,8 +1329,8 @@ function ApplyDirectiveButton({
1320
1329
  }
1321
1330
  const destructive = directive.directiveClass === "delete";
1322
1331
  const muted = nothingToChange && view.status === "idle";
1323
- return /* @__PURE__ */ jsxs2("span", { className: "inline-flex items-center gap-2", children: [
1324
- muted ? /* @__PURE__ */ jsx4("span", { className: "text-xs text-muted-foreground", "data-apply-nothing": "", children: "Nothing to change" }) : null,
1332
+ return /* @__PURE__ */ jsxs2("span", { className: "flex min-w-0 flex-wrap items-center justify-end gap-x-2 gap-y-1", children: [
1333
+ muted ? /* @__PURE__ */ jsx4("span", { className: "min-w-0 text-xs text-muted-foreground", "data-apply-nothing": "", children: "Nothing to change" }) : null,
1325
1334
  /* @__PURE__ */ jsxs2(
1326
1335
  "button",
1327
1336
  {
@@ -1330,7 +1339,7 @@ function ApplyDirectiveButton({
1330
1339
  disabled: view.status === "applying" || view.status === "asking" || items.length === 0,
1331
1340
  "data-apply-tone": muted ? "muted" : destructive ? "destructive" : "default",
1332
1341
  title: muted ? "It sets no fields, so applying it changes nothing." : void 0,
1333
- className: `inline-flex items-center gap-1 rounded-md border px-2 py-1 text-xs font-medium disabled:opacity-50 ${muted ? "border-border/60 bg-background text-muted-foreground hover:bg-accent" : destructive ? "border-destructive/50 bg-background text-destructive hover:bg-destructive/10" : "border-border bg-background hover:bg-accent"}`,
1342
+ className: `inline-flex shrink-0 items-center gap-1 whitespace-nowrap rounded-md border px-2 py-1 text-xs font-medium disabled:opacity-50 ${muted ? "border-border/60 bg-background text-muted-foreground hover:bg-accent" : destructive ? "border-destructive/50 bg-background text-destructive hover:bg-destructive/10" : "border-border bg-background hover:bg-accent"}`,
1334
1343
  children: [
1335
1344
  view.status === "applying" ? /* @__PURE__ */ jsx4(LoaderIcon, { className: "h-3.5 w-3.5 animate-spin" }) : /* @__PURE__ */ jsx4(PlayIcon, { className: "h-3.5 w-3.5" }),
1336
1345
  view.status === "applying" ? `Applying${itemCount ? ` ${itemCount} ${itemCount === 1 ? "item" : "items"}` : ""}\u2026${elapsed ? ` ${elapsed}s` : ""}` : label
@@ -1381,7 +1390,7 @@ function FailureNotice({
1381
1390
  type: "button",
1382
1391
  onClick: () => setOpen((v) => !v),
1383
1392
  "aria-expanded": open,
1384
- className: "ml-1 underline underline-offset-2 hover:no-underline",
1393
+ className: "ml-1 whitespace-nowrap underline underline-offset-2 hover:no-underline",
1385
1394
  "data-apply-failure-details-toggle": true,
1386
1395
  children: open ? "Hide details" : "Details"
1387
1396
  }
@@ -1498,6 +1507,14 @@ import {
1498
1507
  nounTitleColumn
1499
1508
  } from "@ai-matrx/content-ir";
1500
1509
  import { Fragment, jsx as jsx7, jsxs as jsxs5 } from "react/jsx-runtime";
1510
+ function directiveValueWord(host, noun) {
1511
+ const valueLabel = host.valueLabel;
1512
+ return valueLabel ? (field, value) => valueLabel({ noun, field, value }) : null;
1513
+ }
1514
+ function omitKey(item, key) {
1515
+ const { [key]: _omitted, ...rest } = item;
1516
+ return rest;
1517
+ }
1501
1518
  var ROWS_BEFORE_FOLD = 3;
1502
1519
  function ItemRow({
1503
1520
  directive,
@@ -1514,16 +1531,21 @@ function ItemRow({
1514
1531
  const titleColumn = nounTitleColumn(directive.noun, host.nouns);
1515
1532
  const title = itemTitle(item, titleColumn, index, total);
1516
1533
  const subtitle = itemSubtitle(item);
1517
- const facts = itemFacts(item);
1534
+ const valueWord = directiveValueWord(host, directive.noun);
1535
+ const facts = itemFacts(titleColumn ? omitKey(item, titleColumn) : item).map((fact) => ({
1536
+ ...fact,
1537
+ label: directiveFieldLabel(fact.key, titleColumn),
1538
+ value: valueWord?.(fact.key, fact.value) ?? fact.value
1539
+ }));
1518
1540
  const kind = host.itemKind?.(directive.slug) ?? null;
1519
1541
  const display = directiveDisplay3(directive.directiveClass, directive.noun, host.nouns);
1520
1542
  const openItem = host.openItem;
1521
1543
  const body = /* @__PURE__ */ jsxs5(Fragment, { children: [
1522
1544
  /* @__PURE__ */ jsx7("span", { className: "min-w-0 shrink-0 truncate font-medium text-foreground", children: title }),
1523
- /* @__PURE__ */ jsx7("span", { className: "hidden min-w-0 flex-1 items-baseline gap-2 overflow-hidden sm:flex", children: facts.map((fact) => /* @__PURE__ */ jsxs5("span", { className: "truncate text-[11px] text-muted-foreground", children: [
1524
- fact.value,
1545
+ /* @__PURE__ */ jsx7("span", { className: "hidden min-w-0 flex-1 items-baseline gap-2 overflow-hidden sm:flex", children: facts.map((fact) => /* @__PURE__ */ jsxs5("span", { className: "truncate text-[11px] text-muted-foreground", "data-item-fact": fact.key, children: [
1546
+ fact.label,
1525
1547
  " ",
1526
- fact.label
1548
+ /* @__PURE__ */ jsx7("span", { className: "text-foreground/80", children: fact.value })
1527
1549
  ] }, fact.key)) }),
1528
1550
  subtitle && facts.length === 0 ? /* @__PURE__ */ jsx7("span", { className: "hidden truncate text-[11px] text-muted-foreground sm:inline", children: subtitle }) : null,
1529
1551
  openItem ? /* @__PURE__ */ jsx7(MaximizeIcon, { className: "ml-auto h-3 w-3 shrink-0 text-muted-foreground" }) : null
@@ -1558,35 +1580,36 @@ function DirectiveChangeList({
1558
1580
  if (changes.length === 0) {
1559
1581
  return /* @__PURE__ */ jsx7("p", { className: `text-[11px] text-muted-foreground${className ? ` ${className}` : ""}`, children: "Sets no fields \u2014 nothing would change." });
1560
1582
  }
1561
- return /* @__PURE__ */ jsx7("ul", { className: `space-y-0.5${className ? ` ${className}` : ""}`, "data-directive-changes": "", children: changes.map((change) => {
1583
+ return /* @__PURE__ */ jsx7("ul", { className: `@container space-y-1${className ? ` ${className}` : ""}`, "data-directive-changes": "", children: changes.map((change) => {
1562
1584
  const before = change.before && !change.same ? change.before : null;
1563
- const was = before ? before.clears ? "empty" : before.value : null;
1564
1585
  return /* @__PURE__ */ jsxs5(
1565
1586
  "li",
1566
1587
  {
1567
- className: "flex min-w-0 items-baseline gap-1.5 text-[11px]",
1568
- title: before ? `${change.label}: ${before.clears ? "empty" : before.full} \u2192 ${change.full}` : `${change.label} \u2192 ${change.full}`,
1588
+ className: "flex min-w-0 flex-col text-[11px] @xs:flex-row @xs:flex-wrap @xs:items-baseline @xs:gap-x-1.5",
1589
+ title: before ? `${change.label}: ${before.full} \u2192 ${change.full}` : `${change.label} \u2192 ${change.full}`,
1569
1590
  "data-change-key": change.key,
1570
1591
  children: [
1571
1592
  /* @__PURE__ */ jsx7("span", { className: "shrink-0 text-muted-foreground", children: change.label }),
1572
- was !== null ? /* @__PURE__ */ jsx7(
1593
+ before ? /* @__PURE__ */ jsx7(
1573
1594
  "span",
1574
1595
  {
1575
- className: "min-w-0 max-w-[40%] shrink truncate text-muted-foreground line-through",
1596
+ className: "min-w-0 text-muted-foreground line-through [overflow-wrap:anywhere]",
1576
1597
  "data-change-before": "",
1577
- children: was
1598
+ children: before.value
1578
1599
  }
1579
1600
  ) : null,
1580
- /* @__PURE__ */ jsx7("span", { "aria-hidden": true, className: "shrink-0 text-muted-foreground", children: "\u2192" }),
1581
- /* @__PURE__ */ jsx7(
1582
- "span",
1583
- {
1584
- className: `min-w-0 truncate ${change.clears ? "italic text-muted-foreground" : "text-foreground"}`,
1585
- "data-change-after": "",
1586
- children: change.value
1587
- }
1588
- ),
1589
- change.same ? /* @__PURE__ */ jsx7("span", { className: "shrink-0 text-muted-foreground", children: "(no change)" }) : null
1601
+ /* @__PURE__ */ jsxs5("span", { className: "flex min-w-0 items-baseline gap-1.5", children: [
1602
+ /* @__PURE__ */ jsx7("span", { "aria-hidden": true, className: "shrink-0 text-muted-foreground", children: "\u2192" }),
1603
+ /* @__PURE__ */ jsx7(
1604
+ "span",
1605
+ {
1606
+ className: `min-w-0 [overflow-wrap:anywhere] ${change.clears ? "italic text-muted-foreground" : "text-foreground"}`,
1607
+ "data-change-after": "",
1608
+ children: change.value
1609
+ }
1610
+ ),
1611
+ change.same ? /* @__PURE__ */ jsx7("span", { className: "shrink-0 text-muted-foreground", children: "(no change)" }) : null
1612
+ ] })
1590
1613
  ]
1591
1614
  },
1592
1615
  change.key
@@ -1609,12 +1632,20 @@ function TargetRow({
1609
1632
  readsLive ? { noun: directive.noun, id: recordId } : null
1610
1633
  );
1611
1634
  const compareTo = phase.phase === "applied" ? phase.before?.[index] ?? null : readsLive ? live.values : null;
1612
- const changes = isUpdate ? itemChanges(item, compareTo, { titleColumn: nounTitleColumn(directive.noun, host.nouns) }) : [];
1635
+ const changes = isUpdate ? itemChanges(item, compareTo, {
1636
+ titleColumn: nounTitleColumn(directive.noun, host.nouns),
1637
+ valueWord: directiveValueWord(host, directive.noun)
1638
+ }) : [];
1613
1639
  const name = host.renderRecord ? host.renderRecord({ noun: directive.noun, id: recordId, fallback, context: "row" }) : /* @__PURE__ */ jsx7("span", { className: "truncate font-medium text-foreground", children: fallback });
1614
1640
  return /* @__PURE__ */ jsxs5("div", { className: "py-1 text-xs", "data-directive-target": recordId, children: [
1615
1641
  /* @__PURE__ */ jsxs5("div", { className: "flex min-w-0 items-center gap-2", children: [
1616
1642
  /* @__PURE__ */ jsx7("span", { className: "flex min-w-0 flex-1 items-center gap-1 px-1", children: name }),
1617
- host.renderCopy?.({ label: fallback, value: item, size: "xs" })
1643
+ host.renderCopy?.({
1644
+ label: `this ${nounLabel2(directive.noun, host.nouns).toLowerCase()}`,
1645
+ value: item,
1646
+ size: "xs",
1647
+ record: { noun: directive.noun, id: recordId }
1648
+ })
1618
1649
  ] }),
1619
1650
  isUpdate ? /* @__PURE__ */ jsx7(DirectiveChangeList, { changes, className: "mt-0.5 px-1" }) : null
1620
1651
  ] });
@@ -1642,7 +1673,7 @@ function SideEffectDirectiveCard({ directive }) {
1642
1673
  " ",
1643
1674
  total === 1 ? "item" : "items"
1644
1675
  ] }),
1645
- /* @__PURE__ */ jsxs5("div", { className: "ml-auto flex items-center gap-1", children: [
1676
+ /* @__PURE__ */ jsxs5("div", { className: "ml-auto flex min-w-0 flex-wrap items-center justify-end gap-1", children: [
1646
1677
  host.renderCopy?.({ label: display.title, value: directive.shell, size: "icon" }),
1647
1678
  /* @__PURE__ */ jsx7(
1648
1679
  ApplyDirectiveButton,
@@ -1664,7 +1695,7 @@ function SideEffectDirectiveCard({ directive }) {
1664
1695
  {
1665
1696
  type: "button",
1666
1697
  onClick: () => setExpanded((v) => !v),
1667
- className: "mt-0.5 inline-flex items-center gap-1 rounded px-1 py-0.5 text-[11px] text-muted-foreground hover:text-foreground",
1698
+ className: "mt-0.5 inline-flex items-center gap-1 whitespace-nowrap rounded px-1 py-0.5 text-[11px] text-muted-foreground hover:text-foreground",
1668
1699
  children: [
1669
1700
  expanded ? /* @__PURE__ */ jsx7(ChevronDownIcon, { className: "h-3 w-3" }) : /* @__PURE__ */ jsx7(ChevronRightIcon, { className: "h-3 w-3" }),
1670
1701
  expanded ? "Show less" : `Show ${hidden} more`
@@ -2154,6 +2185,7 @@ export {
2154
2185
  DirectiveProvisionalCard,
2155
2186
  DirectiveRender,
2156
2187
  DirectiveScopeProvider,
2188
+ EMPTY_VALUE_WORD,
2157
2189
  GENERIC_STRUCTURED_COMPONENT_KEY,
2158
2190
  GenericStructuredView,
2159
2191
  IR_PROVISIONAL_KEY,
@@ -2171,6 +2203,8 @@ export {
2171
2203
  createKindRouteBinding,
2172
2204
  defaultFailureWords,
2173
2205
  describeChangeValue,
2206
+ directiveFieldLabel,
2207
+ directiveValueWord,
2174
2208
  envelopeFromPartialKind,
2175
2209
  failureWords,
2176
2210
  fieldLabel,