agentic-ui-libs 1.0.0-beta.6 → 1.0.0-beta.8

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.js CHANGED
@@ -1482,6 +1482,16 @@ const Minimize2 = createLucideIcon("Minimize2", [
1482
1482
  * See the LICENSE file in the root directory of this source tree.
1483
1483
  */
1484
1484
  const Minus = createLucideIcon("Minus", [["path", { d: "M5 12h14", key: "1ays0h" }]]);
1485
+ /**
1486
+ * @license lucide-react v0.294.0 - ISC
1487
+ *
1488
+ * This source code is licensed under the ISC license.
1489
+ * See the LICENSE file in the root directory of this source tree.
1490
+ */
1491
+ const Pencil = createLucideIcon("Pencil", [
1492
+ ["path", { d: "M17 3a2.85 2.83 0 1 1 4 4L7.5 20.5 2 22l1.5-5.5Z", key: "5qss01" }],
1493
+ ["path", { d: "m15 5 4 4", key: "1mk7zo" }]
1494
+ ]);
1485
1495
  /**
1486
1496
  * @license lucide-react v0.294.0 - ISC
1487
1497
  *
@@ -67671,7 +67681,7 @@ function nodeToMarkdown(node) {
67671
67681
  case "paragraph":
67672
67682
  return inlineContentToMarkdown(node.content || []);
67673
67683
  case "heading":
67674
- const level = ((_a = node.attrs) == null ? void 0 : _a.level) || 1;
67684
+ const level = ((_a = node.attrs) == null ? void 0 : _a["level"]) || 1;
67675
67685
  const headingPrefix = "#".repeat(level);
67676
67686
  return `${headingPrefix} ${inlineContentToMarkdown(node.content || [])}`;
67677
67687
  case "bulletList":
@@ -67687,11 +67697,11 @@ function nodeToMarkdown(node) {
67687
67697
  case "taskList":
67688
67698
  return (node.content || []).map((item) => {
67689
67699
  var _a2, _b2, _c2;
67690
- const checked = ((_a2 = item.attrs) == null ? void 0 : _a2.checked) ? "x" : " ";
67700
+ const checked = ((_a2 = item.attrs) == null ? void 0 : _a2["checked"]) ? "x" : " ";
67691
67701
  return `- [${checked}] ${inlineContentToMarkdown(((_c2 = (_b2 = item.content) == null ? void 0 : _b2[0]) == null ? void 0 : _c2.content) || [])}`;
67692
67702
  }).join("\n");
67693
67703
  case "codeBlock":
67694
- const language = ((_b = node.attrs) == null ? void 0 : _b.language) || "";
67704
+ const language = ((_b = node.attrs) == null ? void 0 : _b["language"]) || "";
67695
67705
  const code = ((_d = (_c = node.content) == null ? void 0 : _c[0]) == null ? void 0 : _d.text) || "";
67696
67706
  return `\`\`\`${language}
67697
67707
  ${code}
@@ -67754,7 +67764,7 @@ function inlineContentToMarkdown(content) {
67754
67764
  text = `<u>${text}</u>`;
67755
67765
  break;
67756
67766
  case "link":
67757
- const href = ((_a = mark.attrs) == null ? void 0 : _a.href) || "";
67767
+ const href = ((_a = mark.attrs) == null ? void 0 : _a["href"]) || "";
67758
67768
  text = `[${text}](${href})`;
67759
67769
  break;
67760
67770
  }
@@ -68209,7 +68219,7 @@ function nodeToBlock(node) {
68209
68219
  const id = crypto.randomUUID ? crypto.randomUUID() : `block-${Date.now()}-${Math.random().toString(36).slice(2)}`;
68210
68220
  switch (node.type) {
68211
68221
  case "heading":
68212
- const level = ((_a = node.attrs) == null ? void 0 : _a.level) || 1;
68222
+ const level = ((_a = node.attrs) == null ? void 0 : _a["level"]) || 1;
68213
68223
  return {
68214
68224
  id,
68215
68225
  type: `heading${level}`,
@@ -68248,7 +68258,7 @@ function nodeToBlock(node) {
68248
68258
  id,
68249
68259
  type: "code",
68250
68260
  content: [{ type: "text", text: ((_c = (_b = node.content) == null ? void 0 : _b[0]) == null ? void 0 : _c.text) || "" }],
68251
- meta: { language: (_d = node.attrs) == null ? void 0 : _d.language }
68261
+ meta: { language: (_d = node.attrs) == null ? void 0 : _d["language"] }
68252
68262
  };
68253
68263
  case "blockquote":
68254
68264
  return {
@@ -68272,18 +68282,18 @@ function nodeContentToInline(content) {
68272
68282
  if (node.type === "variableChip") {
68273
68283
  return {
68274
68284
  type: "variable",
68275
- variableType: (_a = node.attrs) == null ? void 0 : _a.variableType,
68276
- path: (_b = node.attrs) == null ? void 0 : _b.path,
68277
- displayName: (_c = node.attrs) == null ? void 0 : _c.displayName
68285
+ variableType: (_a = node.attrs) == null ? void 0 : _a["variableType"],
68286
+ path: (_b = node.attrs) == null ? void 0 : _b["path"],
68287
+ displayName: (_c = node.attrs) == null ? void 0 : _c["displayName"]
68278
68288
  };
68279
68289
  }
68280
68290
  if (node.type === "mentionChip") {
68281
68291
  return {
68282
68292
  type: "mention",
68283
- mentionType: (_d = node.attrs) == null ? void 0 : _d.mentionType,
68284
- id: (_e = node.attrs) == null ? void 0 : _e.id,
68285
- name: (_f = node.attrs) == null ? void 0 : _f.name,
68286
- icon: (_g = node.attrs) == null ? void 0 : _g.icon
68293
+ mentionType: (_d = node.attrs) == null ? void 0 : _d["mentionType"],
68294
+ id: (_e = node.attrs) == null ? void 0 : _e["id"],
68295
+ name: (_f = node.attrs) == null ? void 0 : _f["name"],
68296
+ icon: (_g = node.attrs) == null ? void 0 : _g["icon"]
68287
68297
  };
68288
68298
  }
68289
68299
  const styles = {};
@@ -68305,7 +68315,7 @@ function nodeContentToInline(content) {
68305
68315
  styles.code = true;
68306
68316
  break;
68307
68317
  case "link":
68308
- styles.link = (_h = mark.attrs) == null ? void 0 : _h.href;
68318
+ styles.link = (_h = mark.attrs) == null ? void 0 : _h["href"];
68309
68319
  break;
68310
68320
  }
68311
68321
  }
@@ -68357,6 +68367,8 @@ const buildVariableSyntax = (variableType, path) => {
68357
68367
  const VariableChipComponent = ({
68358
68368
  node,
68359
68369
  deleteNode: deleteNode2,
68370
+ editor,
68371
+ getPos,
68360
68372
  selected
68361
68373
  }) => {
68362
68374
  const { variableType, path, displayName } = node.attrs;
@@ -68367,6 +68379,24 @@ const VariableChipComponent = ({
68367
68379
  e3.stopPropagation();
68368
68380
  deleteNode2();
68369
68381
  };
68382
+ const handleEdit = (e3) => {
68383
+ e3.preventDefault();
68384
+ e3.stopPropagation();
68385
+ const pos = typeof getPos === "function" ? getPos() : null;
68386
+ if (pos !== null && editor) {
68387
+ const event = new CustomEvent("variable-chip-edit", {
68388
+ bubbles: true,
68389
+ detail: {
68390
+ variableType,
68391
+ path,
68392
+ displayName,
68393
+ position: pos,
68394
+ nodeSize: node.nodeSize
68395
+ }
68396
+ });
68397
+ editor.view.dom.dispatchEvent(event);
68398
+ }
68399
+ };
68370
68400
  return /* @__PURE__ */ jsxRuntimeExports.jsxs(
68371
68401
  NodeViewWrapper,
68372
68402
  {
@@ -68401,7 +68431,19 @@ const VariableChipComponent = ({
68401
68431
  "button",
68402
68432
  {
68403
68433
  type: "button",
68404
- className: "k-md-editor-variable-chip__remove inline-flex items-center justify-center w-3.5 h-3.5 p-0 border-0 bg-transparent cursor-pointer rounded-sm opacity-70 transition-opacity ml-0.5 shrink-0 hover:opacity-100",
68434
+ className: "k-md-editor-variable-chip__edit inline-flex items-center justify-center w-3.5 h-3.5 p-0 border-0 bg-transparent cursor-pointer rounded-sm opacity-70 transition-opacity shrink-0 hover:opacity-100",
68435
+ onClick: handleEdit,
68436
+ onMouseDown: (e3) => e3.preventDefault(),
68437
+ style: { color: config2.color },
68438
+ "aria-label": "Edit variable",
68439
+ children: /* @__PURE__ */ jsxRuntimeExports.jsx(Pencil, { size: 10 })
68440
+ }
68441
+ ),
68442
+ /* @__PURE__ */ jsxRuntimeExports.jsx(
68443
+ "button",
68444
+ {
68445
+ type: "button",
68446
+ className: "k-md-editor-variable-chip__remove inline-flex items-center justify-center w-3.5 h-3.5 p-0 border-0 bg-transparent cursor-pointer rounded-sm opacity-70 transition-opacity shrink-0 hover:opacity-100",
68405
68447
  onClick: handleRemove,
68406
68448
  onMouseDown: (e3) => e3.preventDefault(),
68407
68449
  style: { color: config2.color },
@@ -68480,22 +68522,22 @@ const VariableChipExtension = Node$1.create({
68480
68522
  default: "env",
68481
68523
  parseHTML: (element) => element.getAttribute("data-variable-type"),
68482
68524
  renderHTML: (attributes) => ({
68483
- "data-variable-type": attributes.variableType
68525
+ "data-variable-type": attributes["variableType"]
68484
68526
  })
68485
68527
  },
68486
68528
  path: {
68487
68529
  default: "",
68488
68530
  parseHTML: (element) => element.getAttribute("data-path"),
68489
68531
  renderHTML: (attributes) => ({
68490
- "data-path": attributes.path
68532
+ "data-path": attributes["path"]
68491
68533
  })
68492
68534
  },
68493
68535
  displayName: {
68494
68536
  default: null,
68495
68537
  parseHTML: (element) => element.getAttribute("data-display-name"),
68496
68538
  renderHTML: (attributes) => {
68497
- if (!attributes.displayName) return {};
68498
- return { "data-display-name": attributes.displayName };
68539
+ if (!attributes["displayName"]) return {};
68540
+ return { "data-display-name": attributes["displayName"] };
68499
68541
  }
68500
68542
  }
68501
68543
  };
@@ -68655,29 +68697,29 @@ const MentionChipExtension = Node$1.create({
68655
68697
  default: "agent",
68656
68698
  parseHTML: (element) => element.getAttribute("data-mention-type"),
68657
68699
  renderHTML: (attributes) => ({
68658
- "data-mention-type": attributes.mentionType
68700
+ "data-mention-type": attributes["mentionType"]
68659
68701
  })
68660
68702
  },
68661
68703
  id: {
68662
68704
  default: "",
68663
68705
  parseHTML: (element) => element.getAttribute("data-id"),
68664
68706
  renderHTML: (attributes) => ({
68665
- "data-id": attributes.id
68707
+ "data-id": attributes["id"]
68666
68708
  })
68667
68709
  },
68668
68710
  name: {
68669
68711
  default: "",
68670
68712
  parseHTML: (element) => element.getAttribute("data-name"),
68671
68713
  renderHTML: (attributes) => ({
68672
- "data-name": attributes.name
68714
+ "data-name": attributes["name"]
68673
68715
  })
68674
68716
  },
68675
68717
  icon: {
68676
68718
  default: null,
68677
68719
  parseHTML: (element) => element.getAttribute("data-icon"),
68678
68720
  renderHTML: (attributes) => {
68679
- if (!attributes.icon) return {};
68680
- return { "data-icon": attributes.icon };
68721
+ if (!attributes["icon"]) return {};
68722
+ return { "data-icon": attributes["icon"] };
68681
68723
  }
68682
68724
  }
68683
68725
  };
@@ -69089,8 +69131,10 @@ const SlashMenu = forwardRef(
69089
69131
  // Default: plain text
69090
69132
  range: range3,
69091
69133
  // The range of the slash command trigger (to delete it)
69092
- hiddenCategories = []
69134
+ hiddenCategories = [],
69093
69135
  // Categories to hide
69136
+ suggestionsLoading = false
69137
+ // Loading state for suggestions
69094
69138
  }, ref) => {
69095
69139
  const [activeCategory, setActiveCategory] = useState(null);
69096
69140
  const [selectedIndex, setSelectedIndex] = useState(0);
@@ -69406,6 +69450,12 @@ const SlashMenu = forwardRef(
69406
69450
  const filteredCategoryItems = query ? visibleCategories.filter((cat) => cat.label.toLowerCase().includes(query.toLowerCase())) : visibleCategories;
69407
69451
  const hasBlockItems = !activeCategory && filteredBlockItems.length > 0;
69408
69452
  const hasCategoryItems = !activeCategory && filteredCategoryItems.length > 0;
69453
+ if (suggestionsLoading && !activeCategory && !hasBlockItems && !hasCategoryItems) {
69454
+ return /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "k-md-editor-slash-menu p-4 text-center text-gray-400 text-[13px] bg-white rounded-lg shadow-lg", children: /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "flex items-center justify-center gap-2", children: [
69455
+ /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "w-4 h-4 border-2 border-gray-300 border-t-gray-600 rounded-full animate-spin" }),
69456
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { children: "Loading suggestions..." })
69457
+ ] }) });
69458
+ }
69409
69459
  if (!hasBlockItems && !hasCategoryItems && !activeCategory) {
69410
69460
  return /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "k-md-editor-slash-menu p-4 text-center text-gray-400 text-[13px] bg-white rounded-lg shadow-lg", children: "No results found" });
69411
69461
  }
@@ -69550,8 +69600,10 @@ const SlashCommandExtension = Extension.create({
69550
69600
  systemVariables: [],
69551
69601
  contentVariables: [],
69552
69602
  onSelectItem: void 0,
69553
- highlightMentions: false
69603
+ highlightMentions: false,
69554
69604
  // Default: insert as plain text
69605
+ suggestionsLoading: false,
69606
+ getSuggestions: void 0
69555
69607
  };
69556
69608
  },
69557
69609
  addProseMirrorPlugins() {
@@ -69576,19 +69628,46 @@ const SlashCommandExtension = Extension.create({
69576
69628
  render: () => {
69577
69629
  let component = null;
69578
69630
  let popup = null;
69631
+ const getCurrentSuggestions = () => {
69632
+ var _a, _b;
69633
+ if (this.options.getSuggestions) {
69634
+ const data = this.options.getSuggestions();
69635
+ console.log("SlashCommand: getSuggestions() returned:", {
69636
+ hasGetter: true,
69637
+ agentsCount: ((_a = data.agents) == null ? void 0 : _a.length) || 0,
69638
+ toolsCount: ((_b = data.tools) == null ? void 0 : _b.length) || 0,
69639
+ data
69640
+ });
69641
+ return data;
69642
+ }
69643
+ console.log("SlashCommand: Using static options (no getter)");
69644
+ return {
69645
+ agents: this.options.agents || [],
69646
+ tools: this.options.tools || [],
69647
+ knowledge: this.options.knowledge || [],
69648
+ envVariables: this.options.envVariables || [],
69649
+ memoryVariables: this.options.memoryVariables || [],
69650
+ systemVariables: this.options.systemVariables || [],
69651
+ contentVariables: this.options.contentVariables || [],
69652
+ loading: this.options.suggestionsLoading || false
69653
+ };
69654
+ };
69579
69655
  return {
69580
69656
  onStart: (props) => {
69657
+ const suggestions = getCurrentSuggestions();
69658
+ console.log("SlashCommand onStart: suggestions =", suggestions);
69581
69659
  component = new ReactRenderer(SlashMenu, {
69582
69660
  props: {
69583
69661
  ...props,
69584
- agents: this.options.agents,
69585
- tools: this.options.tools,
69586
- knowledge: this.options.knowledge,
69587
- envVariables: this.options.envVariables,
69588
- memoryVariables: this.options.memoryVariables,
69589
- systemVariables: this.options.systemVariables,
69590
- contentVariables: this.options.contentVariables,
69662
+ agents: suggestions.agents,
69663
+ tools: suggestions.tools,
69664
+ knowledge: suggestions.knowledge,
69665
+ envVariables: suggestions.envVariables,
69666
+ memoryVariables: suggestions.memoryVariables,
69667
+ systemVariables: suggestions.systemVariables,
69668
+ contentVariables: suggestions.contentVariables,
69591
69669
  highlightMentions: this.options.highlightMentions,
69670
+ suggestionsLoading: suggestions.loading,
69592
69671
  range: props.range,
69593
69672
  // Pass the range for deletion
69594
69673
  command: (item) => {
@@ -69616,16 +69695,18 @@ const SlashCommandExtension = Extension.create({
69616
69695
  },
69617
69696
  onUpdate: (props) => {
69618
69697
  var _a;
69698
+ const suggestions = getCurrentSuggestions();
69619
69699
  component == null ? void 0 : component.updateProps({
69620
69700
  ...props,
69621
- agents: this.options.agents,
69622
- tools: this.options.tools,
69623
- knowledge: this.options.knowledge,
69624
- envVariables: this.options.envVariables,
69625
- memoryVariables: this.options.memoryVariables,
69626
- systemVariables: this.options.systemVariables,
69627
- contentVariables: this.options.contentVariables,
69701
+ agents: suggestions.agents,
69702
+ tools: suggestions.tools,
69703
+ knowledge: suggestions.knowledge,
69704
+ envVariables: suggestions.envVariables,
69705
+ memoryVariables: suggestions.memoryVariables,
69706
+ systemVariables: suggestions.systemVariables,
69707
+ contentVariables: suggestions.contentVariables,
69628
69708
  highlightMentions: this.options.highlightMentions,
69709
+ suggestionsLoading: suggestions.loading,
69629
69710
  range: props.range
69630
69711
  // Update the range
69631
69712
  });
@@ -69679,7 +69760,9 @@ const MentionCommandExtension = Extension.create({
69679
69760
  agents: [],
69680
69761
  tools: [],
69681
69762
  knowledge: [],
69682
- onSelectItem: void 0
69763
+ onSelectItem: void 0,
69764
+ suggestionsLoading: false,
69765
+ getSuggestions: void 0
69683
69766
  };
69684
69767
  },
69685
69768
  addProseMirrorPlugins() {
@@ -69701,14 +69784,26 @@ const MentionCommandExtension = Extension.create({
69701
69784
  render: () => {
69702
69785
  let component = null;
69703
69786
  let popup = null;
69787
+ const getCurrentSuggestions = () => {
69788
+ if (this.options.getSuggestions) {
69789
+ return this.options.getSuggestions();
69790
+ }
69791
+ return {
69792
+ agents: this.options.agents || [],
69793
+ tools: this.options.tools || [],
69794
+ knowledge: this.options.knowledge || [],
69795
+ loading: this.options.suggestionsLoading || false
69796
+ };
69797
+ };
69704
69798
  return {
69705
69799
  onStart: (props) => {
69800
+ const suggestions = getCurrentSuggestions();
69706
69801
  component = new ReactRenderer(SlashMenu, {
69707
69802
  props: {
69708
69803
  ...props,
69709
- agents: this.options.agents,
69710
- tools: this.options.tools,
69711
- knowledge: this.options.knowledge,
69804
+ agents: suggestions.agents,
69805
+ tools: suggestions.tools,
69806
+ knowledge: suggestions.knowledge,
69712
69807
  // No variables or blocks for @ mentions
69713
69808
  envVariables: [],
69714
69809
  memoryVariables: [],
@@ -69718,6 +69813,7 @@ const MentionCommandExtension = Extension.create({
69718
69813
  // Insert as plain bold text
69719
69814
  hiddenCategories: ["blocks"],
69720
69815
  // Hide blocks category
69816
+ suggestionsLoading: suggestions.loading,
69721
69817
  range: props.range,
69722
69818
  command: (item) => {
69723
69819
  props.editor.chain().focus().deleteRange(props.range).run();
@@ -69745,16 +69841,18 @@ const MentionCommandExtension = Extension.create({
69745
69841
  },
69746
69842
  onUpdate: (props) => {
69747
69843
  var _a;
69844
+ const suggestions = getCurrentSuggestions();
69748
69845
  component == null ? void 0 : component.updateProps({
69749
69846
  ...props,
69750
- agents: this.options.agents,
69751
- tools: this.options.tools,
69752
- knowledge: this.options.knowledge,
69847
+ agents: suggestions.agents,
69848
+ tools: suggestions.tools,
69849
+ knowledge: suggestions.knowledge,
69753
69850
  envVariables: [],
69754
69851
  memoryVariables: [],
69755
69852
  systemVariables: [],
69756
69853
  contentVariables: [],
69757
69854
  highlightMentions: false,
69855
+ suggestionsLoading: suggestions.loading,
69758
69856
  hiddenCategories: ["blocks"],
69759
69857
  range: props.range
69760
69858
  });
@@ -69826,18 +69924,51 @@ const VariableMenu = ({
69826
69924
  query,
69827
69925
  onQueryChange,
69828
69926
  onSelect,
69927
+ onCustomVariable,
69829
69928
  onClose,
69830
69929
  envVariables: envVariables2 = [],
69831
69930
  memoryVariables = [],
69832
69931
  systemVariables: systemVariables2 = [],
69833
- contentVariables = []
69932
+ contentVariables = [],
69933
+ allowCustomVariables = false,
69934
+ editorControlled = false,
69935
+ customInputMode = false,
69936
+ isEditMode = false
69834
69937
  }) => {
69938
+ const [customVariableInput, setCustomVariableInput] = useState("");
69939
+ const customInputRef = useRef(null);
69835
69940
  const [activeCategory, setActiveCategory] = useState(null);
69836
69941
  const [selectedIndex, setSelectedIndex] = useState(0);
69837
69942
  const [currentPath, setCurrentPath] = useState([]);
69838
69943
  const [adjustedPosition, setAdjustedPosition] = useState(position);
69839
69944
  const menuRef = useRef(null);
69840
69945
  const inputRef = useRef(null);
69946
+ const parsedQuery = useMemo(() => {
69947
+ const parts = query.split(".");
69948
+ if (parts.length > 1) {
69949
+ const category = parts[0].toLowerCase();
69950
+ if (["env", "memory", "system", "content"].includes(category)) {
69951
+ return {
69952
+ category,
69953
+ path: parts.slice(1, -1),
69954
+ searchTerm: parts[parts.length - 1],
69955
+ fullPath: parts.slice(0, -1).join(".")
69956
+ };
69957
+ }
69958
+ }
69959
+ return {
69960
+ category: null,
69961
+ path: [],
69962
+ searchTerm: query,
69963
+ fullPath: ""
69964
+ };
69965
+ }, [query]);
69966
+ useEffect(() => {
69967
+ if (parsedQuery.category && parsedQuery.category !== activeCategory) {
69968
+ setActiveCategory(parsedQuery.category);
69969
+ setCurrentPath(parsedQuery.path);
69970
+ }
69971
+ }, [parsedQuery.category, parsedQuery.path, activeCategory]);
69841
69972
  useEffect(() => {
69842
69973
  if (!menuRef.current) return;
69843
69974
  const menuRect = menuRef.current.getBoundingClientRect();
@@ -69867,10 +69998,11 @@ const VariableMenu = ({
69867
69998
  { id: "content", label: "Content Variables", icon: FileText, variables: contentVariables }
69868
69999
  ].filter((cat) => cat.variables.length > 0);
69869
70000
  const getCurrentItems = useCallback(() => {
70001
+ const searchTerm = parsedQuery.searchTerm.toLowerCase();
69870
70002
  if (!activeCategory) {
69871
- if (query) {
70003
+ if (searchTerm) {
69872
70004
  return categories.filter(
69873
- (cat) => cat.label.toLowerCase().includes(query.toLowerCase())
70005
+ (cat) => cat.label.toLowerCase().includes(searchTerm) || cat.id.toLowerCase().includes(searchTerm)
69874
70006
  );
69875
70007
  }
69876
70008
  return categories;
@@ -69878,29 +70010,99 @@ const VariableMenu = ({
69878
70010
  const category = categories.find((c3) => c3.id === activeCategory);
69879
70011
  if (!category) return [];
69880
70012
  let variables = category.variables;
69881
- for (const segment of currentPath) {
69882
- const parent = variables.find((v) => v.name === segment);
70013
+ const pathToFollow = parsedQuery.path.length > 0 ? parsedQuery.path : currentPath;
70014
+ for (const segment of pathToFollow) {
70015
+ const parent = variables.find((v) => v.name.toLowerCase() === segment.toLowerCase());
69883
70016
  if (parent == null ? void 0 : parent.children) {
69884
70017
  variables = parent.children;
69885
70018
  } else {
69886
70019
  break;
69887
70020
  }
69888
70021
  }
69889
- if (query) {
70022
+ if (searchTerm) {
69890
70023
  variables = variables.filter(
69891
70024
  (v) => {
69892
70025
  var _a;
69893
- return v.name.toLowerCase().includes(query.toLowerCase()) || ((_a = v.description) == null ? void 0 : _a.toLowerCase().includes(query.toLowerCase()));
70026
+ return v.name.toLowerCase().includes(searchTerm) || ((_a = v.description) == null ? void 0 : _a.toLowerCase().includes(searchTerm));
69894
70027
  }
69895
70028
  );
69896
70029
  }
69897
70030
  return variables;
69898
- }, [activeCategory, categories, currentPath, query]);
70031
+ }, [activeCategory, categories, currentPath, parsedQuery]);
70032
+ const shouldShowCustomOption = useMemo(() => {
70033
+ if (!allowCustomVariables || !query.trim()) return false;
70034
+ const items2 = getCurrentItems();
70035
+ const hasExactMatch = items2.some((item) => {
70036
+ if ("variables" in item) return false;
70037
+ return item.name.toLowerCase() === parsedQuery.searchTerm.toLowerCase();
70038
+ });
70039
+ return !hasExactMatch && query.length > 0;
70040
+ }, [allowCustomVariables, query, getCurrentItems, parsedQuery.searchTerm]);
70041
+ const getCustomVariablePath = useCallback(() => {
70042
+ if (query.includes(".")) {
70043
+ return query;
70044
+ }
70045
+ if (activeCategory) {
70046
+ const pathParts = [activeCategory, ...currentPath, query].filter(Boolean);
70047
+ return pathParts.join(".");
70048
+ }
70049
+ return query;
70050
+ }, [query, activeCategory, currentPath]);
69899
70051
  const items = getCurrentItems();
70052
+ const totalItems = items.length + (shouldShowCustomOption ? 1 : 0);
70053
+ const handleBack = useCallback(() => {
70054
+ if (currentPath.length > 0) {
70055
+ setCurrentPath((prev) => prev.slice(0, -1));
70056
+ } else {
70057
+ setActiveCategory(null);
70058
+ }
70059
+ onQueryChange("");
70060
+ }, [currentPath.length, onQueryChange]);
70061
+ const handleItemClick = useCallback((item) => {
70062
+ if (item === "custom") {
70063
+ if (onCustomVariable) {
70064
+ onCustomVariable(getCustomVariablePath());
70065
+ }
70066
+ return;
70067
+ }
70068
+ if ("variables" in item) {
70069
+ setActiveCategory(item.id);
70070
+ setCurrentPath([]);
70071
+ onQueryChange(item.id + ".");
70072
+ } else {
70073
+ if (item.children && item.children.length > 0) {
70074
+ setCurrentPath((prev) => [...prev, item.name]);
70075
+ const newPath = activeCategory ? `${activeCategory}.${[...currentPath, item.name].join(".")}.` : `${item.name}.`;
70076
+ onQueryChange(newPath);
70077
+ } else {
70078
+ const fullPath = activeCategory ? [...currentPath, item.name].join(".") : item.path;
70079
+ onSelect({
70080
+ ...item,
70081
+ path: fullPath
70082
+ });
70083
+ }
70084
+ }
70085
+ }, [onCustomVariable, getCustomVariablePath, onQueryChange, activeCategory, currentPath, onSelect]);
69900
70086
  useEffect(() => {
69901
70087
  var _a;
69902
- (_a = inputRef.current) == null ? void 0 : _a.focus();
69903
- }, []);
70088
+ if (!editorControlled && !customInputMode) {
70089
+ (_a = inputRef.current) == null ? void 0 : _a.focus();
70090
+ }
70091
+ }, [editorControlled, customInputMode]);
70092
+ useEffect(() => {
70093
+ if (customInputMode) {
70094
+ setTimeout(() => {
70095
+ var _a;
70096
+ (_a = customInputRef.current) == null ? void 0 : _a.focus();
70097
+ }, 50);
70098
+ }
70099
+ }, [customInputMode]);
70100
+ const handleCustomVariableSubmit = useCallback(() => {
70101
+ if (customVariableInput.trim() && onCustomVariable) {
70102
+ onCustomVariable(customVariableInput.trim());
70103
+ setCustomVariableInput("");
70104
+ }
70105
+ }, [customVariableInput, onCustomVariable]);
69904
70106
  useEffect(() => {
69905
70107
  const handleClickOutside = (e3) => {
69906
70108
  if (menuRef.current && !menuRef.current.contains(e3.target)) {
@@ -69912,65 +70114,61 @@ const VariableMenu = ({
69912
70114
  }, [onClose]);
69913
70115
  useEffect(() => {
69914
70116
  const handleKeyDown2 = (e3) => {
70117
+ if (customInputMode) return;
69915
70118
  switch (e3.key) {
69916
70119
  case "ArrowDown":
69917
70120
  e3.preventDefault();
69918
- setSelectedIndex((prev) => Math.min(prev + 1, items.length - 1));
70121
+ e3.stopPropagation();
70122
+ setSelectedIndex((prev) => Math.min(prev + 1, totalItems - 1));
69919
70123
  break;
69920
70124
  case "ArrowUp":
69921
70125
  e3.preventDefault();
70126
+ e3.stopPropagation();
69922
70127
  setSelectedIndex((prev) => Math.max(prev - 1, 0));
69923
70128
  break;
69924
70129
  case "Enter":
69925
70130
  e3.preventDefault();
69926
- if (items[selectedIndex]) {
70131
+ e3.stopPropagation();
70132
+ if (shouldShowCustomOption && selectedIndex === items.length) {
70133
+ handleItemClick("custom");
70134
+ } else if (items[selectedIndex]) {
69927
70135
  handleItemClick(items[selectedIndex]);
70136
+ } else if (items.length > 0) {
70137
+ handleItemClick(items[0]);
70138
+ } else if (shouldShowCustomOption) {
70139
+ handleItemClick("custom");
70140
+ }
70141
+ if (items.length === 0 && !shouldShowCustomOption) {
70142
+ onClose();
69928
70143
  }
69929
70144
  break;
69930
70145
  case "Escape":
69931
70146
  e3.preventDefault();
69932
- if (activeCategory) {
70147
+ e3.stopPropagation();
70148
+ if (activeCategory && !parsedQuery.category) {
69933
70149
  handleBack();
69934
70150
  } else {
69935
70151
  onClose();
69936
70152
  }
69937
70153
  break;
69938
- case "Backspace":
69939
- if (!query && activeCategory) {
69940
- e3.preventDefault();
69941
- handleBack();
70154
+ case "Tab":
70155
+ if (items.length > 0 && !("variables" in items[0])) {
70156
+ const firstItem = items[0];
70157
+ if (firstItem.children && firstItem.children.length > 0) {
70158
+ e3.preventDefault();
70159
+ e3.stopPropagation();
70160
+ handleItemClick(firstItem);
70161
+ }
69942
70162
  }
69943
70163
  break;
69944
70164
  }
69945
70165
  };
69946
- document.addEventListener("keydown", handleKeyDown2);
69947
- return () => document.removeEventListener("keydown", handleKeyDown2);
69948
- }, [items, selectedIndex, activeCategory, query, onClose]);
70166
+ document.addEventListener("keydown", handleKeyDown2, true);
70167
+ return () => document.removeEventListener("keydown", handleKeyDown2, true);
70168
+ }, [customInputMode, items, selectedIndex, activeCategory, onClose, shouldShowCustomOption, totalItems, parsedQuery.category, handleItemClick, handleBack]);
69949
70169
  useEffect(() => {
69950
70170
  setSelectedIndex(0);
69951
- }, [items.length, activeCategory, query]);
69952
- const handleItemClick = (item) => {
69953
- if ("variables" in item) {
69954
- setActiveCategory(item.id);
69955
- setCurrentPath([]);
69956
- onQueryChange("");
69957
- } else {
69958
- if (item.children && item.children.length > 0) {
69959
- setCurrentPath((prev) => [...prev, item.name]);
69960
- onQueryChange("");
69961
- } else {
69962
- onSelect(item);
69963
- }
69964
- }
69965
- };
69966
- const handleBack = () => {
69967
- if (currentPath.length > 0) {
69968
- setCurrentPath((prev) => prev.slice(0, -1));
69969
- } else {
69970
- setActiveCategory(null);
69971
- }
69972
- onQueryChange("");
69973
- };
70171
+ }, [totalItems, activeCategory, query]);
69974
70172
  const getIconForType = (type) => {
69975
70173
  switch (type) {
69976
70174
  case "env":
@@ -69986,10 +70184,12 @@ const VariableMenu = ({
69986
70184
  }
69987
70185
  };
69988
70186
  const getCurrentTitle = () => {
69989
- if (!activeCategory) return "Insert Variable";
70187
+ const prefix2 = isEditMode ? "Edit Variable" : "Insert Variable";
70188
+ if (!activeCategory) return prefix2;
69990
70189
  const category = categories.find((c3) => c3.id === activeCategory);
69991
- if (currentPath.length > 0) {
69992
- return currentPath.join(".");
70190
+ const pathToShow = parsedQuery.path.length > 0 ? parsedQuery.path : currentPath;
70191
+ if (pathToShow.length > 0) {
70192
+ return `${activeCategory}.${pathToShow.join(".")}`;
69993
70193
  }
69994
70194
  return (category == null ? void 0 : category.label) || "Variables";
69995
70195
  };
@@ -70015,51 +70215,142 @@ const VariableMenu = ({
70015
70215
  ),
70016
70216
  /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "text-[13px] font-medium text-gray-700 flex-1", children: getCurrentTitle() })
70017
70217
  ] }),
70018
- /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "px-3 py-2 border-b border-gray-200", children: /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "flex items-center gap-2 px-2.5 py-1.5 bg-gray-50 rounded-md border border-gray-200", children: [
70019
- /* @__PURE__ */ jsxRuntimeExports.jsx(Search, { size: 14, className: "text-gray-400" }),
70020
- /* @__PURE__ */ jsxRuntimeExports.jsx(
70021
- "input",
70022
- {
70023
- ref: inputRef,
70024
- type: "text",
70025
- value: query,
70026
- onChange: (e3) => onQueryChange(e3.target.value),
70027
- placeholder: "Search...",
70028
- className: "flex-1 border-0 bg-transparent outline-none text-[13px] text-gray-700",
70029
- "data-id": "md-editor-variable-search"
70030
- }
70031
- )
70032
- ] }) }),
70033
- /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "flex-1 overflow-y-auto p-1", children: items.length === 0 ? /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "p-4 text-center text-gray-400 text-[13px]", children: "No items found" }) : items.map((item, index) => {
70034
- var _a;
70035
- const isCategory = "variables" in item;
70036
- const Icon = isCategory ? item.icon : getIconForType(item.type);
70037
- const hasChildren = !isCategory && ((_a = item.children) == null ? void 0 : _a.length);
70038
- return /* @__PURE__ */ jsxRuntimeExports.jsxs(
70218
+ customInputMode ? /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "px-3 py-3 border-b border-gray-200 bg-blue-50", children: [
70219
+ /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "text-[12px] text-blue-600 mb-2 font-medium", children: "Type your custom variable:" }),
70220
+ /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "flex items-center gap-2", children: [
70221
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "text-[14px] font-mono text-gray-500", children: "{{" }),
70222
+ /* @__PURE__ */ jsxRuntimeExports.jsx(
70223
+ "input",
70224
+ {
70225
+ ref: customInputRef,
70226
+ type: "text",
70227
+ value: customVariableInput,
70228
+ onChange: (e3) => setCustomVariableInput(e3.target.value),
70229
+ onKeyDown: (e3) => {
70230
+ if (e3.key === "Enter" && customVariableInput.trim()) {
70231
+ e3.preventDefault();
70232
+ handleCustomVariableSubmit();
70233
+ } else if (e3.key === "Escape") {
70234
+ e3.preventDefault();
70235
+ onClose();
70236
+ }
70237
+ },
70238
+ placeholder: "memory.store.field",
70239
+ className: "flex-1 border border-blue-300 bg-white rounded px-2 py-1.5 outline-none text-[13px] text-gray-700 font-mono focus:border-blue-500 focus:ring-1 focus:ring-blue-500",
70240
+ "data-id": "md-editor-custom-variable-input"
70241
+ }
70242
+ ),
70243
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "text-[14px] font-mono text-gray-500", children: "}}" })
70244
+ ] }),
70245
+ /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "mt-2 flex gap-2", children: [
70246
+ /* @__PURE__ */ jsxRuntimeExports.jsx(
70247
+ "button",
70248
+ {
70249
+ type: "button",
70250
+ onClick: handleCustomVariableSubmit,
70251
+ disabled: !customVariableInput.trim(),
70252
+ className: "px-3 py-1 text-[12px] bg-blue-600 text-white rounded hover:bg-blue-700 disabled:opacity-50 disabled:cursor-not-allowed",
70253
+ children: "Insert"
70254
+ }
70255
+ ),
70256
+ /* @__PURE__ */ jsxRuntimeExports.jsx(
70257
+ "button",
70258
+ {
70259
+ type: "button",
70260
+ onClick: onClose,
70261
+ className: "px-3 py-1 text-[12px] bg-gray-200 text-gray-700 rounded hover:bg-gray-300",
70262
+ children: "Cancel"
70263
+ }
70264
+ )
70265
+ ] })
70266
+ ] }) : /* @__PURE__ */ jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment, { children: [
70267
+ !editorControlled && /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "px-3 py-2 border-b border-gray-200", children: /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "flex items-center gap-2 px-2.5 py-1.5 bg-gray-50 rounded-md border border-gray-200", children: [
70268
+ /* @__PURE__ */ jsxRuntimeExports.jsx(Search, { size: 14, className: "text-gray-400" }),
70269
+ /* @__PURE__ */ jsxRuntimeExports.jsx(
70270
+ "input",
70271
+ {
70272
+ ref: inputRef,
70273
+ type: "text",
70274
+ value: query,
70275
+ onChange: (e3) => onQueryChange(e3.target.value),
70276
+ placeholder: "Search...",
70277
+ className: "flex-1 border-0 bg-transparent outline-none text-[13px] text-gray-700",
70278
+ "data-id": "md-editor-variable-search"
70279
+ }
70280
+ )
70281
+ ] }) }),
70282
+ editorControlled && query && /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "px-3 py-1.5 border-b border-gray-200 bg-gray-50", children: [
70283
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "text-[12px] text-gray-500", children: "Typing: " }),
70284
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "text-[12px] font-mono text-gray-700", children: `{{${query}` })
70285
+ ] })
70286
+ ] }),
70287
+ !customInputMode && /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "flex-1 overflow-y-auto p-1", children: items.length === 0 && !shouldShowCustomOption ? /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "p-4 text-center text-gray-400 text-[13px]", children: "No items found" }) : /* @__PURE__ */ jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment, { children: [
70288
+ items.map((item, index) => {
70289
+ var _a;
70290
+ const isCategory = "variables" in item;
70291
+ const Icon = isCategory ? item.icon : getIconForType(item.type);
70292
+ const hasChildren = !isCategory && ((_a = item.children) == null ? void 0 : _a.length);
70293
+ return /* @__PURE__ */ jsxRuntimeExports.jsxs(
70294
+ "button",
70295
+ {
70296
+ type: "button",
70297
+ onClick: () => handleItemClick(item),
70298
+ className: `flex items-center gap-2.5 w-full py-2 px-2.5 border-0 rounded-md text-left cursor-pointer transition-colors duration-100 ${index === selectedIndex ? "bg-gray-100" : "bg-transparent hover:bg-gray-100"}`,
70299
+ onMouseEnter: () => setSelectedIndex(index),
70300
+ "data-id": `md-editor-variable-item-${isCategory ? item.id : item.id}`,
70301
+ children: [
70302
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "flex items-center justify-center w-7 h-7 rounded-md bg-gray-100 text-gray-500 shrink-0", children: /* @__PURE__ */ jsxRuntimeExports.jsx(Icon, { size: 16 }) }),
70303
+ /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "flex-1 min-w-0", children: [
70304
+ /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "text-[13px] font-medium text-gray-800 truncate", children: isCategory ? item.label : item.name }),
70305
+ !isCategory && item.description && /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "text-[11px] text-gray-400 truncate", children: item.description })
70306
+ ] }),
70307
+ (isCategory || hasChildren) && /* @__PURE__ */ jsxRuntimeExports.jsx(ChevronRight, { size: 14, className: "text-gray-400 shrink-0" })
70308
+ ]
70309
+ },
70310
+ isCategory ? item.id : item.id
70311
+ );
70312
+ }),
70313
+ shouldShowCustomOption && /* @__PURE__ */ jsxRuntimeExports.jsxs(
70039
70314
  "button",
70040
70315
  {
70041
70316
  type: "button",
70042
- onClick: () => handleItemClick(item),
70043
- className: `flex items-center gap-2.5 w-full py-2 px-2.5 border-0 rounded-md text-left cursor-pointer transition-colors duration-100 ${index === selectedIndex ? "bg-gray-100" : "bg-transparent hover:bg-gray-100"}`,
70044
- onMouseEnter: () => setSelectedIndex(index),
70045
- "data-id": `md-editor-variable-item-${isCategory ? item.id : item.id}`,
70317
+ onClick: () => handleItemClick("custom"),
70318
+ className: `flex items-center gap-2.5 w-full py-2 px-2.5 border-0 rounded-md text-left cursor-pointer transition-colors duration-100 border-t border-gray-100 mt-1 pt-2 ${selectedIndex === items.length ? "bg-blue-50" : "bg-transparent hover:bg-blue-50"}`,
70319
+ onMouseEnter: () => setSelectedIndex(items.length),
70320
+ "data-id": "md-editor-variable-custom",
70046
70321
  children: [
70047
- /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "flex items-center justify-center w-7 h-7 rounded-md bg-gray-100 text-gray-500 shrink-0", children: /* @__PURE__ */ jsxRuntimeExports.jsx(Icon, { size: 16 }) }),
70322
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "flex items-center justify-center w-7 h-7 rounded-md bg-blue-100 text-blue-600 shrink-0", children: /* @__PURE__ */ jsxRuntimeExports.jsx(Plus, { size: 16 }) }),
70048
70323
  /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "flex-1 min-w-0", children: [
70049
- /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "text-[13px] font-medium text-gray-800 truncate", children: isCategory ? item.label : item.name }),
70050
- !isCategory && item.description && /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "text-[11px] text-gray-400 truncate", children: item.description })
70051
- ] }),
70052
- (isCategory || hasChildren) && /* @__PURE__ */ jsxRuntimeExports.jsx(ChevronRight, { size: 14, className: "text-gray-400 shrink-0" })
70324
+ /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "text-[13px] font-medium text-blue-700 truncate", children: [
70325
+ 'Use "',
70326
+ getCustomVariablePath(),
70327
+ '"'
70328
+ ] }),
70329
+ /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "text-[11px] text-blue-500 truncate", children: "Insert as custom variable" })
70330
+ ] })
70053
70331
  ]
70054
- },
70055
- isCategory ? item.id : item.id
70056
- );
70057
- }) }),
70058
- /* @__PURE__ */ jsxRuntimeExports.jsxs("div", { className: "px-3 py-1.5 border-t border-gray-200 text-[11px] text-gray-400 flex gap-3", children: [
70332
+ }
70333
+ )
70334
+ ] }) }),
70335
+ /* @__PURE__ */ jsxRuntimeExports.jsx("div", { className: "px-3 py-1.5 border-t border-gray-200 text-[11px] text-gray-400 flex gap-3 flex-wrap", children: customInputMode ? /* @__PURE__ */ jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment, { children: [
70336
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { children: " Insert" }),
70337
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { children: "Esc Cancel" })
70338
+ ] }) : editorControlled ? /* @__PURE__ */ jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment, { children: [
70339
+ /* @__PURE__ */ jsxRuntimeExports.jsx("span", { children: "Click to select" }),
70340
+ /* @__PURE__ */ jsxRuntimeExports.jsxs("span", { className: "text-blue-500 font-medium", children: [
70341
+ "{{{",
70342
+ " Custom input"
70343
+ ] }),
70344
+ /* @__PURE__ */ jsxRuntimeExports.jsxs("span", { children: [
70345
+ "Type ",
70346
+ "}}",
70347
+ " to close"
70348
+ ] })
70349
+ ] }) : /* @__PURE__ */ jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment, { children: [
70059
70350
  /* @__PURE__ */ jsxRuntimeExports.jsx("span", { children: "↑↓ Navigate" }),
70060
70351
  /* @__PURE__ */ jsxRuntimeExports.jsx("span", { children: "↵ Select" }),
70061
70352
  /* @__PURE__ */ jsxRuntimeExports.jsx("span", { children: "Esc Close" })
70062
- ] })
70353
+ ] }) })
70063
70354
  ]
70064
70355
  }
70065
70356
  );
@@ -70185,7 +70476,7 @@ const InlineToolbar = ({
70185
70476
  }) => {
70186
70477
  const [showLinkEditor, setShowLinkEditor] = useState(false);
70187
70478
  const isLinkActive = editor.isActive("link");
70188
- const currentLinkUrl = isLinkActive ? editor.getAttributes("link").href : "";
70479
+ const currentLinkUrl = isLinkActive ? editor.getAttributes("link")["href"] : "";
70189
70480
  const toolbarItems = [
70190
70481
  // Text style icons
70191
70482
  {
@@ -71914,7 +72205,9 @@ const MDEditor = forwardRef(
71914
72205
  readOnly = false,
71915
72206
  autoFocus = false,
71916
72207
  onFocus,
71917
- onBlur
72208
+ onBlur,
72209
+ onLoadSuggestions,
72210
+ suggestionsLoading: propSuggestionsLoading = false
71918
72211
  } = props;
71919
72212
  const mergedSlashConfig = { ...DEFAULT_SLASH_COMMAND_CONFIG, ...slashCommandConfig };
71920
72213
  const mergedAIConfig = { ...DEFAULT_AI_CONFIG, ...aiConfig };
@@ -71922,17 +72215,67 @@ const MDEditor = forwardRef(
71922
72215
  const lastEmittedMarkdownRef = useRef("");
71923
72216
  const isInternalUpdateRef = useRef(false);
71924
72217
  const editorContainerRef = useRef(null);
72218
+ const [asyncSuggestions, setAsyncSuggestions] = useState(null);
72219
+ const [suggestionsLoading, setSuggestionsLoading] = useState(false);
71925
72220
  const [variableMenuOpen, setVariableMenuOpen] = useState(false);
71926
72221
  const [variableMenuPosition, setVariableMenuPosition] = useState({ top: 0, left: 0 });
71927
72222
  const [variableMenuQuery, setVariableMenuQuery] = useState("");
72223
+ const [customInputMode, setCustomInputMode] = useState(false);
72224
+ const [editingVariableChip, setEditingVariableChip] = useState(null);
71928
72225
  const [aiPanelOpen, setAIPanelOpen] = useState(mergedAIConfig.alwaysShowPanel ?? false);
71929
72226
  const [aiRefineContext, setAIRefineContext] = useState(null);
71930
72227
  const variableTriggerPosRef = useRef(null);
71931
72228
  const [isRawMode, setIsRawMode] = useState(false);
71932
72229
  const [rawMarkdown, setRawMarkdown] = useState("");
72230
+ useEffect(() => {
72231
+ if (onLoadSuggestions) {
72232
+ setSuggestionsLoading(true);
72233
+ onLoadSuggestions().then((data) => {
72234
+ setAsyncSuggestions(data);
72235
+ setSuggestionsLoading(false);
72236
+ }).catch((error) => {
72237
+ console.error("Failed to load suggestions:", error);
72238
+ setSuggestionsLoading(false);
72239
+ });
72240
+ }
72241
+ }, [onLoadSuggestions]);
72242
+ const mergedAgents = (asyncSuggestions == null ? void 0 : asyncSuggestions.agents) ?? agents2;
72243
+ const mergedTools = (asyncSuggestions == null ? void 0 : asyncSuggestions.tools) ?? tools2;
72244
+ const mergedKnowledge = (asyncSuggestions == null ? void 0 : asyncSuggestions.knowledge) ?? knowledge2;
72245
+ const mergedEnvVariables = (asyncSuggestions == null ? void 0 : asyncSuggestions.envVariables) ?? envVariables2;
72246
+ const mergedMemoryVariables = (asyncSuggestions == null ? void 0 : asyncSuggestions.memoryVariables) ?? memoryVariables;
72247
+ const mergedSystemVariables = (asyncSuggestions == null ? void 0 : asyncSuggestions.systemVariables) ?? systemVariables2;
72248
+ const mergedContentVariables = (asyncSuggestions == null ? void 0 : asyncSuggestions.contentVariables) ?? contentVariables;
72249
+ const finalSuggestionsLoading = propSuggestionsLoading || suggestionsLoading;
72250
+ const suggestionsRef = useRef({
72251
+ agents: mergedAgents,
72252
+ tools: mergedTools,
72253
+ knowledge: mergedKnowledge,
72254
+ envVariables: mergedEnvVariables,
72255
+ memoryVariables: mergedMemoryVariables,
72256
+ systemVariables: mergedSystemVariables,
72257
+ contentVariables: mergedContentVariables,
72258
+ loading: finalSuggestionsLoading
72259
+ });
72260
+ suggestionsRef.current = {
72261
+ agents: mergedAgents,
72262
+ tools: mergedTools,
72263
+ knowledge: mergedKnowledge,
72264
+ envVariables: mergedEnvVariables,
72265
+ memoryVariables: mergedMemoryVariables,
72266
+ systemVariables: mergedSystemVariables,
72267
+ contentVariables: mergedContentVariables,
72268
+ loading: finalSuggestionsLoading
72269
+ };
72270
+ console.log("MDEditor render: suggestionsRef updated with:", {
72271
+ agentsCount: mergedAgents.length,
72272
+ toolsCount: mergedTools.length,
72273
+ knowledgeCount: mergedKnowledge.length,
72274
+ hasAsyncSuggestions: !!asyncSuggestions
72275
+ });
71933
72276
  const defaultCategories = useMemo(() => {
71934
72277
  const categories = [];
71935
- if (agents2.length > 0) {
72278
+ if (mergedAgents.length > 0) {
71936
72279
  categories.push({
71937
72280
  id: "agents",
71938
72281
  label: "Agents",
@@ -71940,7 +72283,7 @@ const MDEditor = forwardRef(
71940
72283
  hasSubmenu: true
71941
72284
  });
71942
72285
  }
71943
- if (knowledge2.length > 0) {
72286
+ if (mergedKnowledge.length > 0) {
71944
72287
  categories.push({
71945
72288
  id: "knowledge",
71946
72289
  label: "Knowledge",
@@ -71948,7 +72291,7 @@ const MDEditor = forwardRef(
71948
72291
  hasSubmenu: true
71949
72292
  });
71950
72293
  }
71951
- if (tools2.length > 0) {
72294
+ if (mergedTools.length > 0) {
71952
72295
  categories.push({
71953
72296
  id: "tools",
71954
72297
  label: "Tools",
@@ -71956,7 +72299,7 @@ const MDEditor = forwardRef(
71956
72299
  hasSubmenu: true
71957
72300
  });
71958
72301
  }
71959
- if (memoryVariables.length > 0) {
72302
+ if (mergedMemoryVariables.length > 0) {
71960
72303
  categories.push({
71961
72304
  id: "memory",
71962
72305
  label: "Memory",
@@ -71964,7 +72307,7 @@ const MDEditor = forwardRef(
71964
72307
  hasSubmenu: true
71965
72308
  });
71966
72309
  }
71967
- if (envVariables2.length > 0) {
72310
+ if (mergedEnvVariables.length > 0) {
71968
72311
  categories.push({
71969
72312
  id: "env",
71970
72313
  label: "Environment Variables",
@@ -71972,7 +72315,7 @@ const MDEditor = forwardRef(
71972
72315
  hasSubmenu: true
71973
72316
  });
71974
72317
  }
71975
- if (systemVariables2.length > 0) {
72318
+ if (mergedSystemVariables.length > 0) {
71976
72319
  categories.push({
71977
72320
  id: "system",
71978
72321
  label: "System Variables",
@@ -71980,7 +72323,7 @@ const MDEditor = forwardRef(
71980
72323
  hasSubmenu: true
71981
72324
  });
71982
72325
  }
71983
- if (contentVariables.length > 0) {
72326
+ if (mergedContentVariables.length > 0) {
71984
72327
  categories.push({
71985
72328
  id: "content",
71986
72329
  label: "Content Variables",
@@ -71989,11 +72332,26 @@ const MDEditor = forwardRef(
71989
72332
  });
71990
72333
  }
71991
72334
  return categories;
71992
- }, [agents2, tools2, knowledge2, memoryVariables, envVariables2, systemVariables2, contentVariables]);
72335
+ }, [mergedAgents, mergedTools, mergedKnowledge, mergedMemoryVariables, mergedEnvVariables, mergedSystemVariables, mergedContentVariables]);
71993
72336
  const insertVariable = useCallback(
71994
72337
  (variable, triggerPos) => {
71995
72338
  if (!editorRef.current) return;
71996
72339
  const editor2 = editorRef.current;
72340
+ if (editingVariableChip) {
72341
+ const { position, nodeSize: nodeSize2 } = editingVariableChip;
72342
+ editor2.chain().focus().deleteRange({ from: position, to: position + nodeSize2 }).insertContentAt(position, {
72343
+ type: "variableChip",
72344
+ attrs: {
72345
+ variableType: variable.type,
72346
+ path: variable.path,
72347
+ displayName: variable.name
72348
+ }
72349
+ }).run();
72350
+ setEditingVariableChip(null);
72351
+ setVariableMenuOpen(false);
72352
+ setVariableMenuQuery("");
72353
+ return;
72354
+ }
71997
72355
  const deleteFrom = triggerPos ?? variableTriggerPosRef.current;
71998
72356
  if (deleteFrom !== null) {
71999
72357
  const { from: from2 } = editor2.state.selection;
@@ -72017,9 +72375,63 @@ const MDEditor = forwardRef(
72017
72375
  }).insertContent(" ").run();
72018
72376
  }
72019
72377
  setVariableMenuOpen(false);
72378
+ setVariableMenuQuery("");
72020
72379
  variableTriggerPosRef.current = null;
72021
72380
  },
72022
- []
72381
+ [editingVariableChip]
72382
+ );
72383
+ const insertCustomVariable = useCallback(
72384
+ (variablePath) => {
72385
+ if (!editorRef.current) return;
72386
+ const editor2 = editorRef.current;
72387
+ let variableType = "custom";
72388
+ let displayPath = variablePath;
72389
+ if (variablePath.startsWith("env.")) {
72390
+ variableType = "env";
72391
+ displayPath = variablePath.substring(4);
72392
+ } else if (variablePath.startsWith("memory.")) {
72393
+ variableType = "memory";
72394
+ displayPath = variablePath.substring(7);
72395
+ } else if (variablePath.startsWith("content.")) {
72396
+ variableType = "content";
72397
+ displayPath = variablePath.substring(8);
72398
+ } else if (variablePath.startsWith("system.")) {
72399
+ variableType = "system";
72400
+ displayPath = variablePath.substring(7);
72401
+ }
72402
+ if (editingVariableChip) {
72403
+ const { position, nodeSize: nodeSize2 } = editingVariableChip;
72404
+ editor2.chain().focus().deleteRange({ from: position, to: position + nodeSize2 }).insertContentAt(position, {
72405
+ type: "variableChip",
72406
+ attrs: {
72407
+ variableType,
72408
+ path: displayPath,
72409
+ displayName: displayPath.split(".").pop() || displayPath
72410
+ }
72411
+ }).run();
72412
+ setEditingVariableChip(null);
72413
+ setVariableMenuOpen(false);
72414
+ setVariableMenuQuery("");
72415
+ return;
72416
+ }
72417
+ const deleteFrom = variableTriggerPosRef.current;
72418
+ if (deleteFrom !== null) {
72419
+ const { from: from2 } = editor2.state.selection;
72420
+ const deleteRange2 = { from: deleteFrom, to: from2 };
72421
+ editor2.chain().focus().deleteRange(deleteRange2).insertContent({
72422
+ type: "variableChip",
72423
+ attrs: {
72424
+ variableType,
72425
+ path: displayPath,
72426
+ displayName: displayPath.split(".").pop() || displayPath
72427
+ }
72428
+ }).insertContent(" ").run();
72429
+ }
72430
+ setVariableMenuOpen(false);
72431
+ setVariableMenuQuery("");
72432
+ variableTriggerPosRef.current = null;
72433
+ },
72434
+ [editingVariableChip]
72023
72435
  );
72024
72436
  const insertMention = useCallback(
72025
72437
  (mention) => {
@@ -72165,7 +72577,7 @@ const MDEditor = forwardRef(
72165
72577
  Placeholder.configure({
72166
72578
  placeholder: ({ node }) => {
72167
72579
  if (node.type.name === "heading") {
72168
- const level = node.attrs.level;
72580
+ const level = node.attrs["level"];
72169
72581
  return `Heading ${level}`;
72170
72582
  }
72171
72583
  if (node.type.name === "paragraph") {
@@ -72206,6 +72618,10 @@ const MDEditor = forwardRef(
72206
72618
  exts.push(MentionChipExtension);
72207
72619
  }
72208
72620
  if (mergedFeatures.slashCommands) {
72621
+ const getSuggestionsCallback = () => {
72622
+ console.log("MDEditor: getSuggestions callback invoked, ref.current =", suggestionsRef.current);
72623
+ return suggestionsRef.current;
72624
+ };
72209
72625
  exts.push(
72210
72626
  SlashCommandExtension.configure({
72211
72627
  suggestion: {
@@ -72213,24 +72629,18 @@ const MDEditor = forwardRef(
72213
72629
  startOfLine: false,
72214
72630
  items: () => defaultCategories
72215
72631
  },
72216
- agents: agents2,
72217
- tools: tools2,
72218
- knowledge: knowledge2,
72219
- envVariables: envVariables2,
72220
- memoryVariables,
72221
- systemVariables: systemVariables2,
72222
- contentVariables,
72632
+ // Pass getter function to always get latest data from ref
72633
+ getSuggestions: getSuggestionsCallback,
72223
72634
  onSelectItem: handleSlashCommandSelect,
72224
72635
  highlightMentions: mergedSlashConfig.highlightMentions
72225
72636
  })
72226
72637
  );
72227
72638
  }
72228
- if (mergedFeatures.mentions && (agents2.length > 0 || tools2.length > 0 || knowledge2.length > 0)) {
72639
+ if (mergedFeatures.mentions) {
72229
72640
  exts.push(
72230
72641
  MentionCommandExtension.configure({
72231
- agents: agents2,
72232
- tools: tools2,
72233
- knowledge: knowledge2,
72642
+ // Pass getter function to always get latest data from ref
72643
+ getSuggestions: () => suggestionsRef.current,
72234
72644
  onSelectItem: handleSlashCommandSelect
72235
72645
  })
72236
72646
  );
@@ -72244,7 +72654,7 @@ const MDEditor = forwardRef(
72244
72654
  );
72245
72655
  }
72246
72656
  return exts;
72247
- }, [mergedFeatures, placeholder, defaultCategories, agents2, tools2, knowledge2, envVariables2, memoryVariables, systemVariables2, contentVariables, handleSlashCommandSelect, mergedSlashConfig.highlightMentions, mergedAIConfig.enabled, mergedAIConfig.keyboardShortcut, onAIRefine, handleAIRefineTrigger]);
72657
+ }, [mergedFeatures, placeholder, defaultCategories, handleSlashCommandSelect, mergedSlashConfig.highlightMentions, mergedAIConfig.enabled, mergedAIConfig.keyboardShortcut, onAIRefine, handleAIRefineTrigger]);
72248
72658
  const editorRef = useRef(null);
72249
72659
  const editor = useEditor({
72250
72660
  extensions,
@@ -72282,9 +72692,14 @@ const MDEditor = forwardRef(
72282
72692
  const handleKeyDown2 = (event) => {
72283
72693
  if (event.key === "{") {
72284
72694
  const { from: from2 } = editor.state.selection;
72285
- const textBefore = editor.state.doc.textBetween(Math.max(0, from2 - 1), from2);
72286
- if (textBefore === "{") {
72695
+ const textBefore = editor.state.doc.textBetween(Math.max(0, from2 - 2), from2);
72696
+ const charBefore = editor.state.doc.textBetween(Math.max(0, from2 - 1), from2);
72697
+ if (textBefore === "{{" && variableMenuOpen) {
72287
72698
  event.preventDefault();
72699
+ setCustomInputMode(true);
72700
+ return;
72701
+ }
72702
+ if (charBefore === "{") {
72288
72703
  variableTriggerPosRef.current = from2 - 1;
72289
72704
  const coords = editor.view.coordsAtPos(from2);
72290
72705
  setVariableMenuPosition({
@@ -72293,20 +72708,41 @@ const MDEditor = forwardRef(
72293
72708
  });
72294
72709
  setVariableMenuQuery("");
72295
72710
  setVariableMenuOpen(true);
72711
+ setCustomInputMode(false);
72296
72712
  }
72297
72713
  }
72298
72714
  };
72715
+ const handleInput = () => {
72716
+ if (!variableMenuOpen || variableTriggerPosRef.current === null || customInputMode) return;
72717
+ const { from: from2 } = editor.state.selection;
72718
+ const triggerPos = variableTriggerPosRef.current;
72719
+ const textAfterTrigger = editor.state.doc.textBetween(
72720
+ triggerPos + 2,
72721
+ // After {{
72722
+ from2
72723
+ );
72724
+ if (textAfterTrigger.includes("}}")) {
72725
+ setVariableMenuOpen(false);
72726
+ setCustomInputMode(false);
72727
+ variableTriggerPosRef.current = null;
72728
+ return;
72729
+ }
72730
+ setVariableMenuQuery(textAfterTrigger);
72731
+ };
72299
72732
  const editorElement = editor.view.dom;
72300
72733
  editorElement.addEventListener("keydown", handleKeyDown2);
72734
+ editorElement.addEventListener("input", handleInput);
72301
72735
  return () => {
72302
72736
  editorElement.removeEventListener("keydown", handleKeyDown2);
72737
+ editorElement.removeEventListener("input", handleInput);
72303
72738
  };
72304
- }, [editor, mergedFeatures.variableChips]);
72739
+ }, [editor, mergedFeatures.variableChips, variableMenuOpen, customInputMode]);
72305
72740
  useEffect(() => {
72306
72741
  if (!variableMenuOpen) return;
72307
72742
  const handleKeyDown2 = (event) => {
72308
72743
  if (event.key === "Escape") {
72309
72744
  setVariableMenuOpen(false);
72745
+ setEditingVariableChip(null);
72310
72746
  variableTriggerPosRef.current = null;
72311
72747
  editor == null ? void 0 : editor.chain().focus().run();
72312
72748
  }
@@ -72314,6 +72750,32 @@ const MDEditor = forwardRef(
72314
72750
  document.addEventListener("keydown", handleKeyDown2);
72315
72751
  return () => document.removeEventListener("keydown", handleKeyDown2);
72316
72752
  }, [variableMenuOpen, editor]);
72753
+ useEffect(() => {
72754
+ if (!editor) return;
72755
+ const handleVariableChipEdit = (event) => {
72756
+ const customEvent = event;
72757
+ const { variableType, path, position, nodeSize: nodeSize2 } = customEvent.detail;
72758
+ const coords = editor.view.coordsAtPos(position);
72759
+ setEditingVariableChip({
72760
+ position,
72761
+ nodeSize: nodeSize2,
72762
+ variableType,
72763
+ path
72764
+ });
72765
+ setVariableMenuPosition({
72766
+ top: coords.bottom + 8,
72767
+ left: coords.left
72768
+ });
72769
+ setVariableMenuQuery("");
72770
+ setCustomInputMode(false);
72771
+ setVariableMenuOpen(true);
72772
+ };
72773
+ const editorElement = editor.view.dom;
72774
+ editorElement.addEventListener("variable-chip-edit", handleVariableChipEdit);
72775
+ return () => {
72776
+ editorElement.removeEventListener("variable-chip-edit", handleVariableChipEdit);
72777
+ };
72778
+ }, [editor]);
72317
72779
  useEffect(() => {
72318
72780
  if (!editor || isInternalUpdateRef.current) {
72319
72781
  isInternalUpdateRef.current = false;
@@ -72570,14 +73032,22 @@ const MDEditor = forwardRef(
72570
73032
  query: variableMenuQuery,
72571
73033
  onQueryChange: setVariableMenuQuery,
72572
73034
  onSelect: (variable) => insertVariable(variable),
73035
+ onCustomVariable: insertCustomVariable,
72573
73036
  onClose: () => {
72574
73037
  setVariableMenuOpen(false);
73038
+ setVariableMenuQuery("");
73039
+ setCustomInputMode(false);
73040
+ setEditingVariableChip(null);
72575
73041
  variableTriggerPosRef.current = null;
72576
73042
  },
72577
- envVariables: envVariables2,
72578
- memoryVariables,
72579
- systemVariables: systemVariables2,
72580
- contentVariables
73043
+ envVariables: mergedEnvVariables,
73044
+ memoryVariables: mergedMemoryVariables,
73045
+ systemVariables: mergedSystemVariables,
73046
+ contentVariables: mergedContentVariables,
73047
+ allowCustomVariables: true,
73048
+ editorControlled: !customInputMode && !editingVariableChip,
73049
+ customInputMode,
73050
+ isEditMode: !!editingVariableChip
72581
73051
  }
72582
73052
  ),
72583
73053
  isAIEnabled && mergedAIConfig.contextMenu && /* @__PURE__ */ jsxRuntimeExports.jsx(