@asteby/metacore-runtime-react 18.8.0 → 18.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,22 @@
1
1
  # @asteby/metacore-runtime-react
2
2
 
3
+ ## 18.9.0
4
+
5
+ ### Minor Changes
6
+
7
+ - 5becc8e: Add a `reference` display type for SAP-style polymorphic source-document columns.
8
+
9
+ A column declared `display: "reference"` (e.g. `inventory_movements.source_id`,
10
+ whose target document varies by a `source_kind` discriminator) now renders a
11
+ navigable chip resolved by the backend. The new `ReferenceCell` reads the
12
+ resolved sibling `row[<key w/o _id>] = { value, label, kind, table }`: it shows
13
+ the `label` when present, else a short id (first 8 chars of the value), and —
14
+ when the sibling carries a target `table` and `value` — wraps the chip in a
15
+ plain `<a href="/m/<table>/<value>">` so the host router navigates to the source
16
+ document. Mirrors `RelationCell`'s chip look (subtle tint, dark-mode aware) and
17
+ is domain-agnostic: any polymorphic FK carrying the `reference` renderer works
18
+ without per-addon code.
19
+
3
20
  ## 18.8.0
4
21
 
5
22
  ### Minor Changes
@@ -1 +1 @@
1
- {"version":3,"file":"dynamic-columns.d.ts","sourceRoot":"","sources":["../src/dynamic-columns.tsx"],"names":[],"mappings":"AAgBA,OAAO,EAAU,KAAK,MAAM,EAAE,MAAM,UAAU,CAAA;AAgC9C,OAAO,KAAK,EAAiB,gBAAgB,EAAE,MAAM,SAAS,CAAA;AAE9D,OAAO,KAAK,EAER,iBAAiB,EACpB,MAAM,wBAAwB,CAAA;AAE/B,qEAAqE;AACrE,MAAM,WAAW,qBAAqB;IAClC;;;;OAIG;IACH,WAAW,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAM,CAAA;IACtC;;;;OAIG;IACH,UAAU,CAAC,EAAE,MAAM,CAAA;CACtB;AA0BD;;;;GAIG;AACH,eAAO,MAAM,eAAe,GAAI,KAAK,gBAAgB,EAAE,cAAc,MAAM,KAAG,MACzB,CAAA;AAoErD;;;;;;;;;;;GAWG;AACH,eAAO,MAAM,0BAA0B,GAAI,QAAQ,GAAG,EAAE,KAAK,GAAG,KAAG,OAMlE,CAAA;AAqKD;;;;;;;GAOG;AACH,eAAO,MAAM,cAAc,GAAI,KAAK,IAAI,CAAC,gBAAgB,EAAE,KAAK,CAAC,KAAG,MAGnE,CAAA;AAED,6EAA6E;AAC7E,eAAO,MAAM,eAAe,2DAA4D,CAAA;AAExF;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,cAAc,CAC1B,KAAK,EAAE,OAAO,EACd,QAAQ,EAAE,MAAM,GAAG,SAAS,EAC5B,MAAM,EAAE,MAAM,EACd,QAAQ,CAAC,EAAE,MAAM,GAClB;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CA6C5C;AAED;;;;;;;GAOG;AACH,eAAO,MAAM,oBAAoB,GAAI,KAAK,gBAAgB,EAAE,KAAK,GAAG,KAAG,MAWtE,CAAA;AAED;;;;;;GAMG;AACH,eAAO,MAAM,oBAAoB,GAAI,KAAK,gBAAgB,EAAE,KAAK,GAAG,KAAG,MAOtE,CAAA;AA0ED;;;;GAIG;AACH,wBAAgB,4BAA4B,CACxC,OAAO,GAAE,qBAA0B,GACpC,iBAAiB,CAwmBnB;AAED;;;;GAIG;AACH,eAAO,MAAM,wBAAwB,EAAE,iBACL,CAAA"}
1
+ {"version":3,"file":"dynamic-columns.d.ts","sourceRoot":"","sources":["../src/dynamic-columns.tsx"],"names":[],"mappings":"AAgBA,OAAO,EAAU,KAAK,MAAM,EAAE,MAAM,UAAU,CAAA;AAgC9C,OAAO,KAAK,EAAiB,gBAAgB,EAAE,MAAM,SAAS,CAAA;AAE9D,OAAO,KAAK,EAER,iBAAiB,EACpB,MAAM,wBAAwB,CAAA;AAE/B,qEAAqE;AACrE,MAAM,WAAW,qBAAqB;IAClC;;;;OAIG;IACH,WAAW,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAM,CAAA;IACtC;;;;OAIG;IACH,UAAU,CAAC,EAAE,MAAM,CAAA;CACtB;AA0BD;;;;GAIG;AACH,eAAO,MAAM,eAAe,GAAI,KAAK,gBAAgB,EAAE,cAAc,MAAM,KAAG,MACzB,CAAA;AAoErD;;;;;;;;;;;GAWG;AACH,eAAO,MAAM,0BAA0B,GAAI,QAAQ,GAAG,EAAE,KAAK,GAAG,KAAG,OAMlE,CAAA;AAqKD;;;;;;;GAOG;AACH,eAAO,MAAM,cAAc,GAAI,KAAK,IAAI,CAAC,gBAAgB,EAAE,KAAK,CAAC,KAAG,MAGnE,CAAA;AAED,6EAA6E;AAC7E,eAAO,MAAM,eAAe,2DAA4D,CAAA;AAExF;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,cAAc,CAC1B,KAAK,EAAE,OAAO,EACd,QAAQ,EAAE,MAAM,GAAG,SAAS,EAC5B,MAAM,EAAE,MAAM,EACd,QAAQ,CAAC,EAAE,MAAM,GAClB;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CA6C5C;AAED;;;;;;;GAOG;AACH,eAAO,MAAM,oBAAoB,GAAI,KAAK,gBAAgB,EAAE,KAAK,GAAG,KAAG,MAWtE,CAAA;AAED;;;;;;GAMG;AACH,eAAO,MAAM,oBAAoB,GAAI,KAAK,gBAAgB,EAAE,KAAK,GAAG,KAAG,MAOtE,CAAA;AAsID;;;;GAIG;AACH,wBAAgB,4BAA4B,CACxC,OAAO,GAAE,qBAA0B,GACpC,iBAAiB,CAinBnB;AAED;;;;GAIG;AACH,eAAO,MAAM,wBAAwB,EAAE,iBACL,CAAA"}
@@ -340,6 +340,42 @@ const RelationCell = ({ col, row, getImageUrl }) => {
340
340
  const chipStyles = relationChipStyles(display, { isDark });
341
341
  return (_jsxs("span", { className: "inline-flex max-w-[220px] items-center gap-1.5 rounded-md px-2 py-0.5 text-sm font-medium", style: chipStyles, title: display, children: [image && (_jsx(RelationThumbnail, { src: image, alt: display, getImageUrl: getImageUrl, size: 18 })), _jsx("span", { className: "truncate", children: display })] }));
342
342
  };
343
+ /**
344
+ * Renders a SAP-style polymorphic source-document reference as a navigable
345
+ * chip. Reads the backend-resolved sibling `row[<key w/o _id>] =
346
+ * { value, label, kind, table }` (see `relationKeyFor`) — the discriminator
347
+ * (`source_kind`) selects the target model and the backend stamps the resolved
348
+ * SQL `table` so the cell can link to `/m/<table>/<value>` (the host router
349
+ * handles `/m/:model/:id`). Shows the resolved `label` when present, else a
350
+ * short id (first 8 chars of the value). Domain-agnostic: any polymorphic FK
351
+ * (`source_id`, `document_id`, …) carrying `display: "reference"` works without
352
+ * per-addon code. Mirrors `RelationCell`'s chip look (subtle tint, dark-mode
353
+ * aware) so references read consistently next to plain relations.
354
+ */
355
+ const ReferenceCell = ({ col, row }) => {
356
+ const isDark = useIsDarkTheme();
357
+ const sibling = getNestedValue(row, relationKeyFor(col));
358
+ const value = (sibling && typeof sibling === 'object' ? sibling.value : undefined) ??
359
+ getNestedValue(row, col.key);
360
+ if (value === undefined || value === null || value === '' || isNilUuid(value)) {
361
+ return _jsx(EmptyCell, {});
362
+ }
363
+ const label = sibling && typeof sibling === 'object' ? sibling.label : undefined;
364
+ const kind = sibling && typeof sibling === 'object' ? sibling.kind : undefined;
365
+ const table = sibling && typeof sibling === 'object' ? sibling.table : undefined;
366
+ const displayText = label !== undefined && label !== null && label !== ''
367
+ ? String(label)
368
+ : `${String(value).slice(0, 8)}`;
369
+ // Tint keyed on the discriminator (when present) so e.g. sale/transfer/
370
+ // adjustment chips read as visually distinct families; falls back to the
371
+ // display text. Same subtle relation-chip look + dark-mode handling.
372
+ const chipStyles = relationChipStyles(String(kind || displayText), { isDark });
373
+ const className = 'inline-flex max-w-[220px] items-center gap-1 rounded-md px-2 py-0.5 text-sm font-medium';
374
+ if (table && value) {
375
+ return (_jsx("a", { href: `/m/${table}/${value}`, onClick: (e) => e.stopPropagation(), className: `${className} hover:underline`, style: chipStyles, title: displayText, children: _jsx("span", { className: "truncate", children: displayText }) }));
376
+ }
377
+ return (_jsx("span", { className: className, style: chipStyles, title: displayText, children: _jsx("span", { className: "truncate", children: displayText }) }));
378
+ };
343
379
  /**
344
380
  * Generic avatar-style cell: round/rounded photo (or initials fallback) +
345
381
  * primary name + optional subtitle. Backs the `avatar`/`search` columns as
@@ -444,6 +480,14 @@ export function makeDefaultGetDynamicColumns(helpers = {}) {
444
480
  // `in_progress` reads as "In Progress" instead of raw.
445
481
  return (_jsx(Badge, { variant: "outline", className: "border-0", style: styles, children: humanizeToken(sv) }));
446
482
  }
483
+ // Polymorphic source-document reference (SAP-style). Reads
484
+ // the backend-resolved `{ value, label, kind, table }`
485
+ // sibling and renders a navigable `/m/<table>/<value>` chip.
486
+ // Checked before the relation branch so a polymorphic FK
487
+ // carrying a `ref` still routes here.
488
+ if (renderAs === 'reference') {
489
+ return _jsx(ReferenceCell, { col: col, row: row.original });
490
+ }
447
491
  // Resolved FK relation chip. Triggers on an explicit
448
492
  // `cellStyle: 'relation'` or on any column carrying a `ref`
449
493
  // (a belongs_to FK) that isn't being rendered as an
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@asteby/metacore-runtime-react",
3
- "version": "18.8.0",
3
+ "version": "18.9.0",
4
4
  "description": "React runtime for metacore hosts — renders addon contributions dynamically",
5
5
  "repository": {
6
6
  "type": "git",
@@ -61,8 +61,8 @@
61
61
  "typescript": "^6.0.0",
62
62
  "vitest": "^4.0.0",
63
63
  "zustand": "^5.0.0",
64
- "@asteby/metacore-sdk": "3.2.0",
65
- "@asteby/metacore-ui": "2.5.0"
64
+ "@asteby/metacore-ui": "2.5.0",
65
+ "@asteby/metacore-sdk": "3.2.0"
66
66
  },
67
67
  "scripts": {
68
68
  "build": "tsc -p tsconfig.json",
@@ -509,6 +509,66 @@ const RelationCell: React.FC<{
509
509
  )
510
510
  }
511
511
 
512
+ /**
513
+ * Renders a SAP-style polymorphic source-document reference as a navigable
514
+ * chip. Reads the backend-resolved sibling `row[<key w/o _id>] =
515
+ * { value, label, kind, table }` (see `relationKeyFor`) — the discriminator
516
+ * (`source_kind`) selects the target model and the backend stamps the resolved
517
+ * SQL `table` so the cell can link to `/m/<table>/<value>` (the host router
518
+ * handles `/m/:model/:id`). Shows the resolved `label` when present, else a
519
+ * short id (first 8 chars of the value). Domain-agnostic: any polymorphic FK
520
+ * (`source_id`, `document_id`, …) carrying `display: "reference"` works without
521
+ * per-addon code. Mirrors `RelationCell`'s chip look (subtle tint, dark-mode
522
+ * aware) so references read consistently next to plain relations.
523
+ */
524
+ const ReferenceCell: React.FC<{
525
+ col: ColumnDefinition
526
+ row: any
527
+ }> = ({ col, row }) => {
528
+ const isDark = useIsDarkTheme()
529
+ const sibling = getNestedValue(row, relationKeyFor(col))
530
+ const value =
531
+ (sibling && typeof sibling === 'object' ? sibling.value : undefined) ??
532
+ getNestedValue(row, col.key)
533
+ if (value === undefined || value === null || value === '' || isNilUuid(value)) {
534
+ return <EmptyCell />
535
+ }
536
+ const label =
537
+ sibling && typeof sibling === 'object' ? sibling.label : undefined
538
+ const kind =
539
+ sibling && typeof sibling === 'object' ? sibling.kind : undefined
540
+ const table =
541
+ sibling && typeof sibling === 'object' ? sibling.table : undefined
542
+ const displayText =
543
+ label !== undefined && label !== null && label !== ''
544
+ ? String(label)
545
+ : `${String(value).slice(0, 8)}`
546
+ // Tint keyed on the discriminator (when present) so e.g. sale/transfer/
547
+ // adjustment chips read as visually distinct families; falls back to the
548
+ // display text. Same subtle relation-chip look + dark-mode handling.
549
+ const chipStyles = relationChipStyles(String(kind || displayText), { isDark })
550
+ const className =
551
+ 'inline-flex max-w-[220px] items-center gap-1 rounded-md px-2 py-0.5 text-sm font-medium'
552
+ if (table && value) {
553
+ return (
554
+ <a
555
+ href={`/m/${table}/${value}`}
556
+ onClick={(e) => e.stopPropagation()}
557
+ className={`${className} hover:underline`}
558
+ style={chipStyles}
559
+ title={displayText}
560
+ >
561
+ <span className="truncate">{displayText}</span>
562
+ </a>
563
+ )
564
+ }
565
+ return (
566
+ <span className={className} style={chipStyles} title={displayText}>
567
+ <span className="truncate">{displayText}</span>
568
+ </span>
569
+ )
570
+ }
571
+
512
572
  /**
513
573
  * Generic avatar-style cell: round/rounded photo (or initials fallback) +
514
574
  * primary name + optional subtitle. Backs the `avatar`/`search` columns as
@@ -682,6 +742,15 @@ export function makeDefaultGetDynamicColumns(
682
742
  )
683
743
  }
684
744
 
745
+ // Polymorphic source-document reference (SAP-style). Reads
746
+ // the backend-resolved `{ value, label, kind, table }`
747
+ // sibling and renders a navigable `/m/<table>/<value>` chip.
748
+ // Checked before the relation branch so a polymorphic FK
749
+ // carrying a `ref` still routes here.
750
+ if (renderAs === 'reference') {
751
+ return <ReferenceCell col={col} row={row.original} />
752
+ }
753
+
685
754
  // Resolved FK relation chip. Triggers on an explicit
686
755
  // `cellStyle: 'relation'` or on any column carrying a `ref`
687
756
  // (a belongs_to FK) that isn't being rendered as an