@ai-matrx/chat 0.5.8 → 0.5.11

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,33 @@
1
1
  # @ai-matrx/chat
2
2
 
3
+ ## 0.5.11
4
+
5
+ Automatic changed-only republish (docs/metadata drift since the last tag — see
6
+ `git diff npm/chat/v0.5.8..npm/chat/v0.5.11 -- apps/shared/chat`).
7
+ No source changes intended and no consumer action required.
8
+
9
+ ## 0.5.10 — message Print is the one message print
10
+
11
+ - `conversation/utils/markdown-print` delegates to `@ai-matrx/rich-content/copy/print-message`
12
+ (`printMarkdownContent` now always returns a Promise). Needs rich-content ≥ 0.2.58.
13
+
14
+ Consumer action: none.
15
+
16
+ ## Unreleased — lane L4b rendered-output
17
+ ### an artifact edit shows its new version
18
+
19
+ `getToolArtifact` maps a completed `edit_artifact` call to a new `canvas_item` kind (`id` = the new
20
+ version's `canvas_items.id`, `version`); the tool card draws a "Page · Edited" bar and, under it, the
21
+ host slot **`CanvasItemCard`** (`{ canvasItemId, version? }`) — the version's own card rendered through
22
+ the host's block registry. Unregistered, the slot draws nothing. **Consumer action:** register
23
+ `CanvasItemCard` (matrx-frontend renders the item through its artifact renderer registry).
24
+
25
+ ## 0.5.9
26
+
27
+ Automatic changed-only republish (docs/metadata drift since the last tag — see
28
+ `git diff npm/chat/v0.5.5..npm/chat/v0.5.9 -- apps/shared/chat`).
29
+ No source changes intended and no consumer action required.
30
+
3
31
  ## 0.5.8 — attach from outside React
4
32
 
5
33
  - `attachResourceToConversation(store, conversationId, resource)` — THE attach path without a hook
@@ -12,8 +12,9 @@ export type RichCopySplitProps = MatrxCopyMenuProps & {
12
12
  exportTitle?: string;
13
13
  };
14
14
  /**
15
- * THE content action set of a markdown host (ContentActions, Arman 2026-10-08: copy, Plain,
16
- * Export, Print and Transform each one click away; Transform opens the Alchemy palette below).
15
+ * THE content action set of a markdown host (ContentActions, Arman 2026-10-08 revised): ONE Copy icon
16
+ * (raw, then Copy raw / formatted / for AI — the host's `agent` envelope), Raw/Formatted, and "…" with
17
+ * Alchemy… (the palette below), the downloads and Print.
17
18
  * Formerly the split Copy of a markdown host (Arman, 2026-10-04: "one click to get either the markdown
18
19
  * version or the no-markup version"). One click copies the person's flavor (`copy.default_flavor`);
19
20
  * the chevron offers exactly Copy markdown and Copy plain text (2026-10-07). The Alchemy palette
@@ -5,6 +5,7 @@ import { ContentActions } from "@ai-matrx/rich-content/copy/ContentActions";
5
5
  import { copyRichContent } from "@ai-matrx/rich-content/copy/copy-commands";
6
6
  import { ExportPaletteAnchor, openExportPalette, useExportPaletteKey } from "@ai-matrx/rich-content/copy/ExportPalette";
7
7
  import { cn } from "@ai-matrx/design-system";
8
+ import { buildAgentPayload } from "@ai-matrx/alchemy/operate";
8
9
  import { CopyButtons } from "../host/ui-slots.js";
9
10
  function RichCopySplit(props) {
10
11
  const { human, className, size } = props;
@@ -25,7 +26,11 @@ function RichCopySplit(props) {
25
26
  },
26
27
  copy,
27
28
  size: splitSize,
28
- label: `Copy ${props.label ?? ""}`.trim(),
29
+ label: props.label ?? "content",
30
+ copyForAi: props.agent ? async () => {
31
+ const built = typeof props.agent === "function" ? await props.agent() : props.agent;
32
+ return typeof built === "string" ? built : buildAgentPayload(built, { url: window.location.href, capturedAt: (/* @__PURE__ */ new Date()).toISOString() });
33
+ } : void 0,
29
34
  title: props.exportTitle ?? props.label,
30
35
  viewKey: props.viewKey,
31
36
  onTransform: () => void openExportPalette(exportKey)
@@ -152,7 +152,7 @@ function ChatAgentMenu({
152
152
  else onSelectAgent(info.customAgentId, { mandateKey: MANDATE_KEYS.chat__cx_default });
153
153
  };
154
154
  return /* @__PURE__ */ jsxs(Fragment, { children: [
155
- info.agentId ? /* @__PURE__ */ jsx(ComposerSubmenu, { row: { icon: Webhook, label: `Agent: ${agentLabel}` }, panelClassName: "w-[340px] h-[420px] p-0", children: /* @__PURE__ */ jsx(ComposerAgentPeek, { agentId: info.agentId, onDone: close }) }) : null,
155
+ info.agentId ? /* @__PURE__ */ jsx(ComposerSubmenu, { row: { icon: Webhook, label: `Agent: ${agentLabel}` }, pageTitle: "Agent", panelClassName: "w-[340px] h-[420px] p-0", children: /* @__PURE__ */ jsx(ComposerAgentPeek, { agentId: info.agentId, onDone: close }) }) : null,
156
156
  isManualMode ? /* @__PURE__ */ jsx(
157
157
  ComposerMenuRow,
158
158
  {
@@ -165,6 +165,7 @@ function ChatAgentMenu({
165
165
  ComposerSubmenu,
166
166
  {
167
167
  row: { icon: Cpu, label: `Model: ${info.effectiveModelLabel ?? "Choose a model"}` },
168
+ pageTitle: "Model",
168
169
  panelClassName: MODEL_PICKER_PANEL,
169
170
  children: (closePanel) => /* @__PURE__ */ jsx(
170
171
  QuickRunModelSelect,
@@ -213,7 +214,7 @@ function AnyAgentRow({
213
214
  agentFilter,
214
215
  choose
215
216
  }) {
216
- return /* @__PURE__ */ jsx(ComposerSubmenu, { row: { icon, label }, panelClassName: AGENT_PICKER_PANEL, children: /* @__PURE__ */ jsx(
217
+ return /* @__PURE__ */ jsx(ComposerSubmenu, { row: { icon, label }, pageTitle: "Agents", panelClassName: AGENT_PICKER_PANEL, children: /* @__PURE__ */ jsx(
217
218
  AgentListPanel,
218
219
  {
219
220
  consumerId: "composer-agent-pill",
@@ -105,7 +105,7 @@ export declare function ComposerMenuLevel({ children }: {
105
105
  * Popover anchored to the row, so Radix treats it as a child layer: clicking
106
106
  * inside it never dismisses the parent menu.
107
107
  */
108
- export declare function ComposerSubmenu({ row, children, panelClassName, open: controlledOpen, onOpenChange, drillInPlace, }: {
108
+ export declare function ComposerSubmenu({ row, children, panelClassName, open: controlledOpen, onOpenChange, drillInPlace, pageTitle, }: {
109
109
  row: Omit<ComposerMenuRowProps, "onClick" | "chevron" | "active">;
110
110
  children: ReactNode | ((close: () => void) => ReactNode);
111
111
  /** Width/height of the cascade panel (e.g. "w-[360px] h-[440px]"). */
@@ -118,6 +118,8 @@ export declare function ComposerSubmenu({ row, children, panelClassName, open: c
118
118
  * the menu. The phone sheet pushes pages either way.
119
119
  */
120
120
  drillInPlace?: boolean;
121
+ /** The phone sheet's page title when the row's label carries a value ("Model: X" → "Model"). */
122
+ pageTitle?: string;
121
123
  }): import("react").JSX.Element;
122
124
  /**
123
125
  * What a narrow composer folded out of its rows (Arman, 2026-10-04): its own
@@ -243,7 +243,8 @@ function ComposerSubmenu({
243
243
  panelClassName,
244
244
  open: controlledOpen,
245
245
  onOpenChange,
246
- drillInPlace
246
+ drillInPlace,
247
+ pageTitle
247
248
  }) {
248
249
  const id = useId();
249
250
  const level = useContext(ComposerMenuLevelContext);
@@ -269,7 +270,7 @@ function ComposerSubmenu({
269
270
  ...row,
270
271
  chevron: true,
271
272
  onClick: () => sheetNav.push({
272
- title: typeof row.label === "string" ? row.label : "",
273
+ title: pageTitle ?? (typeof row.label === "string" ? row.label : ""),
273
274
  // A panel with no fixed height on desktop is content-sized on the
274
275
  // phone too — one sizing decision, both presentations.
275
276
  fit: panelClassName && !/(^|\s)h-\[/.test(panelClassName) ? "content" : "fill",
@@ -12,13 +12,10 @@
12
12
  *
13
13
  * Fix conversion or styling in the package (SAME-SESSION LAW), never here.
14
14
  */
15
- import { type PrintOutcome } from "@ai-matrx/print/core";
15
+ import type { PrintOutcome } from "@ai-matrx/print/core";
16
16
  /**
17
- * Prints a message: its prose through the article skin, and every embedded
18
- * block through the SAME adapter its own print uses (`@ai-matrx/print`'s one
19
- * block-printer registry, keyed by artifact type / `__kind`) — a quiz as its
20
- * questions, a deck as its study sheet, a diagram as its drawing, an HTML page
21
- * as its picture (a print window runs no author scripts; the page's own Print
22
- * is the sharp one, and the person is told so).
17
+ * Prints a message through THE message print (`@ai-matrx/rich-content/copy/print-message`):
18
+ * prose plus every embedded block through its own registry adapter — the same
19
+ * composition the content actions' Print uses.
23
20
  */
24
- export declare function printMarkdownContent(markdown: string, title?: string): PrintOutcome | Promise<PrintOutcome>;
21
+ export declare function printMarkdownContent(markdown: string, title?: string): Promise<PrintOutcome>;
@@ -1,74 +1,17 @@
1
- import { listPrintBlocks, printMarkdown, printMarkdownWhenReady } from "@ai-matrx/print/markdown";
2
- import { getBlockPrinter } from "@ai-matrx/print/core";
1
+ import { printMessage } from "@ai-matrx/rich-content/copy/print-message";
3
2
  import { notifyPrintOutcome } from "../../host/ui-slots.js";
4
- const FRAME_BLOCK_TYPES = /* @__PURE__ */ new Set(["html", "react", "iframe"]);
5
- function blockData(block) {
6
- const text = block.body.trim();
7
- if (text.startsWith("{") || text.startsWith("[")) {
8
- try {
9
- return JSON.parse(text);
10
- } catch {
11
- return block.body;
12
- }
13
- }
14
- return block.body;
15
- }
16
- function adapterFor(block) {
17
- const printer = getBlockPrinter(block.type);
18
- return printer?.toPrintHtml ? printer : null;
19
- }
20
- function printMarkdownContent(markdown, title = "AI Response") {
21
- const blocks = listPrintBlocks(markdown, "article");
22
- const hasMermaid = blocks.some((block) => block.source === "fence" && block.type === "mermaid");
23
- const adapted = blocks.filter((block) => adapterFor(block) !== null);
24
- if (!hasMermaid && adapted.length === 0) {
25
- const outcome = printMarkdown(markdown, { skin: "article", title });
26
- notifyPrintOutcome(outcome);
27
- return outcome;
28
- }
29
- let drawing = null;
30
- const drawAll = () => drawing ??= (async () => {
31
- try {
32
- const { drawMermaidForPrint } = await import("@ai-matrx/rich-content/mermaid/print-render");
33
- const { pictures, failed } = await drawMermaidForPrint(markdown);
34
- if (failed > 0) {
35
- const { toast } = await import("../../host/notify.js");
36
- toast.warning(
37
- `${failed} diagram${failed === 1 ? "" : "s"} could not be drawn and print${failed === 1 ? "s" : ""} as source.`
38
- );
39
- }
40
- return pictures;
41
- } catch (error) {
42
- console.error("[print] diagrams could not be drawn", error);
43
- const { toast } = await import("../../host/notify.js");
44
- toast.warning("Diagrams could not be drawn, so they print as source.");
45
- return null;
46
- }
47
- })();
48
- return printMarkdownWhenReady(markdown, {
3
+ async function printMarkdownContent(markdown, title = "AI Response") {
4
+ const outcome = await printMessage(markdown, {
49
5
  skin: "article",
50
6
  title,
51
- renderBlock: async (block) => {
52
- if (block.source === "fence" && block.type === "mermaid") {
53
- const svg = (await drawAll())?.get(block.body);
54
- return svg ? { svg, alt: "Diagram" } : null;
55
- }
56
- const printer = adapterFor(block);
57
- if (!printer?.toPrintHtml) return null;
58
- return printer.toPrintHtml(blockData(block), {
59
- type: block.type,
60
- raw: block.body,
61
- ...block.title ? { title: block.title } : {}
62
- });
63
- }
64
- }).then(async (outcome) => {
65
- notifyPrintOutcome(outcome);
66
- if (outcome === "opened" && adapted.some((block) => FRAME_BLOCK_TYPES.has(block.type))) {
7
+ onNotice: async (level, message) => {
67
8
  const { toast } = await import("../../host/notify.js");
68
- toast.info("Web pages print as a picture inside a message. For sharp text, print the page from its card.");
9
+ if (level === "warning") toast.warning(message);
10
+ else toast.info(message);
69
11
  }
70
- return outcome;
71
12
  });
13
+ notifyPrintOutcome(outcome);
14
+ return outcome;
72
15
  }
73
16
  export {
74
17
  printMarkdownContent
@@ -80,6 +80,12 @@ interface ValueChangeProps<T> {
80
80
  [extra: string]: any;
81
81
  }
82
82
  type AnyComponent = ComponentType<any>;
83
+ export interface CanvasItemCardProps {
84
+ /** `canvas_items.id` of the version to show. */
85
+ canvasItemId: string;
86
+ /** Its chain version, when the caller knows it. */
87
+ version?: number;
88
+ }
83
89
  /**
84
90
  * A component slot typed by the props the PACKAGE passes. Bivariant on purpose: the host
85
91
  * component has its own (usually richer) prop type, and a slot must accept it as long as the
@@ -105,6 +111,8 @@ export interface ChatUiSlots {
105
111
  FileResourceChip: AnyComponent;
106
112
  ConnectorMark: AnyComponent;
107
113
  MessageFilesStrip: AnyComponent;
114
+ /** A canvas item rendered by id through the host's block registry (a tool's new artifact version). */
115
+ CanvasItemCard: SlotComponent<CanvasItemCardProps>;
108
116
  RulebookNudge: AnyComponent;
109
117
  NegativeVerdictFollowUp: AnyComponent;
110
118
  SpeakerButton: AnyComponent;
@@ -468,6 +476,7 @@ export declare const TableChooser: AnyComponent;
468
476
  export declare const FileResourceChip: AnyComponent;
469
477
  export declare const ConnectorMark: AnyComponent;
470
478
  export declare const MessageFilesStrip: AnyComponent;
479
+ export declare const CanvasItemCard: SlotComponent<CanvasItemCardProps>;
471
480
  export declare const RulebookNudge: AnyComponent;
472
481
  export declare const NegativeVerdictFollowUp: AnyComponent;
473
482
  export declare const SpeakerButton: AnyComponent;
@@ -232,6 +232,7 @@ const TableChooser = slotComponent("TableChooser");
232
232
  const FileResourceChip = slotComponent("FileResourceChip");
233
233
  const ConnectorMark = slotComponent("ConnectorMark");
234
234
  const MessageFilesStrip = slotComponent("MessageFilesStrip", optionalWidget("MessageFilesStrip"));
235
+ const CanvasItemCard = slotComponent("CanvasItemCard", optionalWidget("CanvasItemCard"));
235
236
  const RulebookNudge = slotComponent("RulebookNudge", optionalWidget("RulebookNudge"));
236
237
  const NegativeVerdictFollowUp = slotComponent("NegativeVerdictFollowUp", optionalWidget("NegativeVerdictFollowUp"));
237
238
  const SpeakerButton = slotComponent("SpeakerButton", optionalWidget("SpeakerButton"));
@@ -527,6 +528,7 @@ export {
527
528
  AttachedResourcesSection,
528
529
  AuthGateDialog,
529
530
  BlockHoverPreview,
531
+ CanvasItemCard,
530
532
  ChangeDiff,
531
533
  CitationChip,
532
534
  ClampedNumberInput,
@@ -4,6 +4,7 @@ import {
4
4
  ChevronDown,
5
5
  FileText,
6
6
  Frame,
7
+ Globe,
7
8
  PanelRightOpen,
8
9
  Pencil,
9
10
  StickyNote,
@@ -35,6 +36,11 @@ const KIND_META = {
35
36
  Icon: StickyNote,
36
37
  noun: "Note",
37
38
  iconTint: "text-amber-600 dark:text-amber-400"
39
+ },
40
+ canvas_item: {
41
+ Icon: Globe,
42
+ noun: "Page",
43
+ iconTint: "text-emerald-600 dark:text-emerald-400"
38
44
  }
39
45
  };
40
46
  function ArtifactResultBar({
@@ -134,7 +140,7 @@ function ArtifactResultBar({
134
140
  /* @__PURE__ */ jsx(Frame, { className: "size-4" }),
135
141
  "Canvas"
136
142
  ] }),
137
- /* @__PURE__ */ jsxs(DropdownMenuItem, { onClick: openEdit, className: "gap-2", children: [
143
+ artifact.kind !== "canvas_item" && /* @__PURE__ */ jsxs(DropdownMenuItem, { onClick: openEdit, className: "gap-2", children: [
138
144
  /* @__PURE__ */ jsx(Pencil, { className: "size-4" }),
139
145
  "Edit"
140
146
  ] }),
@@ -1,5 +1,5 @@
1
1
  "use client";
2
- import { jsx, jsxs } from "react/jsx-runtime";
2
+ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
3
3
  import React, { useEffect, useMemo, useState } from "react";
4
4
  import {
5
5
  ChevronDown,
@@ -41,7 +41,7 @@ import {
41
41
  } from "../result-fields/ToolErrorCard.js";
42
42
  import { guardRoutingOf } from "../result-fields/guard-routing.js";
43
43
  import { resultAsObject } from "../renderers/_shared.js";
44
- import { RecordChangeApprovalCard, useHeldWriteTableName } from "../../host/ui-slots.js";
44
+ import { CanvasItemCard, RecordChangeApprovalCard, useHeldWriteTableName } from "../../host/ui-slots.js";
45
45
  import { SHOW_PARKED_ASK_EVENT } from "../../agents/runtime-reconnect/show-parked-ask.js";
46
46
  import { ParkedOnPersonCard } from "../../action-requests/components/ParkedOnPersonCard.js";
47
47
  import {
@@ -193,6 +193,7 @@ const ToolCallVisualizationInner = ({
193
193
  const querySubtitle = phase === "error" || heldWait || parkedAsk ? null : headerSubtitle;
194
194
  const artifactRaw = phase === "complete" && settled.length === 1 && !heldWait ? getToolArtifact(headerTool) : null;
195
195
  const artifact = artifactRaw && (artifactRaw.kind === "working_document" ? typeof conversationId === "string" && conversationId.length > 0 : Boolean(artifactRaw.id)) ? artifactRaw : null;
196
+ const canvasItemCard = artifact?.kind === "canvas_item" && artifact.id ? /* @__PURE__ */ jsx("div", { className: "mt-1.5", children: /* @__PURE__ */ jsx(CanvasItemCard, { canvasItemId: artifact.id, version: artifact.version }) }) : null;
196
197
  if (entries.length === 0) return null;
197
198
  const handleOpenOverlay = (tabId) => {
198
199
  setInitialOverlayTab(tabId);
@@ -232,17 +233,20 @@ const ToolCallVisualizationInner = ({
232
233
  className
233
234
  ),
234
235
  children: [
235
- artifact ? /* @__PURE__ */ jsx(
236
- ArtifactResultBar,
237
- {
238
- artifact,
239
- conversationId,
240
- peekExpanded: isExpanded,
241
- onTogglePeek: toggleExpand,
242
- onOpenOverlay: handleOpenOverlay,
243
- onOpenWindowPanel: handleOpenWindowPanel
244
- }
245
- ) : cardMode && headerTool && HeaderInline ? (
236
+ artifact ? /* @__PURE__ */ jsxs(Fragment, { children: [
237
+ /* @__PURE__ */ jsx(
238
+ ArtifactResultBar,
239
+ {
240
+ artifact,
241
+ conversationId,
242
+ peekExpanded: isExpanded,
243
+ onTogglePeek: toggleExpand,
244
+ onOpenOverlay: handleOpenOverlay,
245
+ onOpenWindowPanel: handleOpenWindowPanel
246
+ }
247
+ ),
248
+ canvasItemCard
249
+ ] }) : cardMode && headerTool && HeaderInline ? (
246
250
  // Self-headed entity card — no fold line; the card's own header carries
247
251
  // the name + "Open in" menu. createElement (not JSX) since the component
248
252
  // is resolved at runtime from the registry.
@@ -14,18 +14,22 @@
14
14
  * branch here + one entry in the bar's `KIND_META`.
15
15
  */
16
16
  import type { ToolLifecycleEntry } from "../../agents/types/request.types.js";
17
- export type ToolArtifactKind = "working_document" | "note";
17
+ export type ToolArtifactKind = "working_document" | "note" | "canvas_item";
18
18
  export interface ToolArtifact {
19
19
  kind: ToolArtifactKind;
20
20
  /** Generic fallback label; the working-doc bar prefers the live document title. */
21
21
  title: string;
22
22
  /** Past-tense verb for the sub-label: "Edited" / "Rewrote" / "Saved" / "Updated". */
23
23
  verbPast: string;
24
- /** Open handle for id-based kinds (note). The working document uses the shell's conversationId. */
24
+ /** Open handle for id-based kinds (note, canvas_item). The working document uses the shell's conversationId. */
25
25
  id?: string;
26
+ /** canvas_item: the chain version this call produced (the card shows THAT version). */
27
+ version?: number;
26
28
  }
27
29
  /** The `ctx_patch` tool and its live production alias — the canonical set of
28
30
  * tool names that carry a working-document (or any ctx key) patch. Shared so
29
31
  * the drawer's live-diff hook matches patch entries the same way. */
30
32
  export declare const PATCH_TOOLS: Set<string>;
33
+ /** Tools whose result is a new version of a canvas item (`artifact_id` + `version`). */
34
+ export declare const CANVAS_ITEM_TOOLS: Set<string>;
31
35
  export declare function getToolArtifact(entry: ToolLifecycleEntry | null | undefined): ToolArtifact | null;
@@ -1,6 +1,7 @@
1
1
  import { getArg, resultAsObject } from "../renderers/_shared.js";
2
2
  const PATCH_TOOLS = /* @__PURE__ */ new Set(["ctx_patch", "context_patch"]);
3
3
  const NOTE_TOOLS = /* @__PURE__ */ new Set(["note", "war_room_update_note"]);
4
+ const CANVAS_ITEM_TOOLS = /* @__PURE__ */ new Set(["edit_artifact"]);
4
5
  const WORKING_DOC_KEY = "working_document";
5
6
  function pastForPatchCommand(command) {
6
7
  switch (command) {
@@ -45,9 +46,23 @@ function getToolArtifact(entry) {
45
46
  id
46
47
  };
47
48
  }
49
+ if (CANVAS_ITEM_TOOLS.has(tool)) {
50
+ const facts = result && typeof result.artifact_id === "string" ? result : result && typeof result.details === "object" && result.details !== null ? result.details : null;
51
+ const id = facts && typeof facts.artifact_id === "string" ? facts.artifact_id : void 0;
52
+ if (!id) return null;
53
+ const version = facts && typeof facts.version === "number" ? facts.version : void 0;
54
+ return {
55
+ kind: "canvas_item",
56
+ title: version ? `Version ${version}` : "New version",
57
+ verbPast: "Edited",
58
+ id,
59
+ ...version ? { version } : {}
60
+ };
61
+ }
48
62
  return null;
49
63
  }
50
64
  export {
65
+ CANVAS_ITEM_TOOLS,
51
66
  PATCH_TOOLS,
52
67
  getToolArtifact
53
68
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ai-matrx/chat",
3
- "version": "0.5.8",
3
+ "version": "0.5.11",
4
4
  "description": "THE one AI Matrx person-to-agent chat system: the full chat (running agents, conversations, tool calls, streaming, context, surfaces, voice) as per-module subpaths @ai-matrx/chat/<domain>/<module> over a host contract (/host, /host/react) whose only required value is a db. One chat, one renderer: the old kernel entries (., /external-store, /matrx, /react, /tools, styles.css, tokens.css) are retired.",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -169,22 +169,22 @@
169
169
  "@ai-matrx/agents": "latest",
170
170
  "@ai-matrx/alchemy": "latest",
171
171
  "@ai-matrx/associations": "latest",
172
+ "@ai-matrx/browser-audio": "latest",
172
173
  "@ai-matrx/canvas": "latest",
173
174
  "@ai-matrx/content-ir": "latest",
174
175
  "@ai-matrx/content-ir-react": "latest",
175
176
  "@ai-matrx/data": "latest",
176
- "@ai-matrx/browser-audio": "latest",
177
+ "@ai-matrx/design-system": "latest",
177
178
  "@ai-matrx/diff": "latest",
178
179
  "@ai-matrx/icons": "latest",
179
- "@ai-matrx/design-system": "latest",
180
+ "@ai-matrx/media": "latest",
180
181
  "@ai-matrx/kit": "latest",
181
182
  "@ai-matrx/print": "latest",
182
183
  "@ai-matrx/realtime": "latest",
183
- "@ai-matrx/media": "latest",
184
- "@ai-matrx/records-ui": "latest",
185
184
  "@ai-matrx/records": "latest",
186
- "@ai-matrx/rich-editor": "latest",
187
- "@ai-matrx/rich-content": "latest"
185
+ "@ai-matrx/records-ui": "latest",
186
+ "@ai-matrx/rich-content": "latest",
187
+ "@ai-matrx/rich-editor": "latest"
188
188
  },
189
189
  "devDependencies": {
190
190
  "@arethetypeswrong/cli": "^0.18.5",