react-ai-renderer 0.1.24 → 0.1.25

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.cjs CHANGED
@@ -838,33 +838,37 @@ var MDXStreamingParser = /** @class */function () {
838
838
  // 处理 JSON 值(对象或数组)
839
839
  var startChar = input[j];
840
840
  var startBracket = j;
841
- // 使用局部变量跟踪属性值内部的括号嵌套
842
841
  var localBracketCount = 0;
843
842
  var localSquareBracketCount = 0;
844
843
  var inValueQuote = false;
845
844
  var valueQuoteChar = '';
845
+ var inBacktick = false;
846
+ var closingStack = [];
846
847
  if (startChar === '{') {
847
848
  localBracketCount = 1;
849
+ closingStack.push('}');
848
850
  } else {
849
851
  localSquareBracketCount = 1;
852
+ closingStack.push(']');
850
853
  }
851
854
  j++;
852
- // 同时跟踪花括号和方括号的嵌套
853
855
  while (j < input.length && (localBracketCount > 0 || localSquareBracketCount > 0)) {
854
- if (input[j] === '"' || input[j] === "'") {
855
- // 在字符串内,跳过整个字符串
856
+ if (input[j] === '`' && !inValueQuote) {
857
+ inBacktick = !inBacktick;
858
+ j++;
859
+ } else if (inBacktick) {
860
+ j++;
861
+ } else if (input[j] === '"' || input[j] === "'") {
856
862
  if (!inValueQuote) {
857
863
  inValueQuote = true;
858
864
  valueQuoteChar = input[j];
859
865
  } else if (input[j] === valueQuoteChar) {
860
- // 检查是否是转义的引号
861
866
  var escapeCount = 0;
862
867
  var k = j - 1;
863
868
  while (k >= 0 && input[k] === '\\') {
864
869
  escapeCount++;
865
870
  k--;
866
871
  }
867
- // 如果是偶数个反斜杠,说明引号没有被转义
868
872
  if (escapeCount % 2 === 0) {
869
873
  inValueQuote = false;
870
874
  }
@@ -872,15 +876,23 @@ var MDXStreamingParser = /** @class */function () {
872
876
  j++;
873
877
  } else if (input[j] === '{' && !inValueQuote) {
874
878
  localBracketCount++;
879
+ closingStack.push('}');
875
880
  j++;
876
881
  } else if (input[j] === '}' && !inValueQuote) {
877
882
  localBracketCount--;
883
+ if (closingStack.length > 0 && closingStack[closingStack.length - 1] === '}') {
884
+ closingStack.pop();
885
+ }
878
886
  j++;
879
887
  } else if (input[j] === '[' && !inValueQuote) {
880
888
  localSquareBracketCount++;
889
+ closingStack.push(']');
881
890
  j++;
882
891
  } else if (input[j] === ']' && !inValueQuote) {
883
892
  localSquareBracketCount--;
893
+ if (closingStack.length > 0 && closingStack[closingStack.length - 1] === ']') {
894
+ closingStack.pop();
895
+ }
884
896
  j++;
885
897
  } else {
886
898
  j++;
@@ -888,31 +900,46 @@ var MDXStreamingParser = /** @class */function () {
888
900
  }
889
901
  var rawValue = input.slice(startBracket, j);
890
902
  value = input.slice(startBracket + 1, j - 1);
903
+ // 流式修复:输入未结束但括号未闭合,尝试关闭不完整的表达式
904
+ if (j >= input.length && closingStack.length > 0) {
905
+ var healed = rawValue;
906
+ if (inBacktick) healed += '`';
907
+ if (inValueQuote) healed += valueQuoteChar;
908
+ healed += closingStack.reverse().join('');
909
+ // 剥离外层 JSX 表达式括号 {{ → {,用 (...) 包裹强制表达式上下文
910
+ var inner = healed.slice(1, -1);
911
+ try {
912
+ props[propName] = new Function('return (' + inner + ')')();
913
+ } catch (_a) {
914
+ try {
915
+ var jv = inner.replace(/`([^`]*)`/g, function (_, p1) {
916
+ return JSON.stringify(p1);
917
+ }).replace(/'([^'\\]*(\\.[^'\\]*)*)'/g, function (m) {
918
+ var s = m.slice(1, -1).replace(/\\/g, '\\\\').replace(/"/g, '\\"');
919
+ return "\"".concat(s, "\"");
920
+ }).replace(/([{,]\s*)([\p{L}_$][\p{L}\p{N}_$]*)\s*:/gu, '$1"$2":');
921
+ props[propName] = JSON.parse(jv);
922
+ } catch (_b) {
923
+ // 修复失败,不设置 prop,组件以骨架态渲染
924
+ }
925
+ }
926
+ i = j;
927
+ continue;
928
+ }
891
929
  try {
892
- // 直接使用 Function 构造器来评估 JavaScript 表达式
893
- // 这比手动转换 JavaScript 对象字面量为 JSON 更可靠
894
930
  props[propName] = new Function('return ' + rawValue)();
895
931
  } catch (e) {
896
- // 如果 Function 构造器失败,尝试手动转换并解析为 JSON
897
932
  try {
898
- // 将 JavaScript 对象字面量转换为有效的 JSON
899
- // 1. 将单引号字符串转换为双引号字符串
900
933
  var jsonValue = value.replace(/'([^'\\]*(\\.[^'\\]*)*)'/g, function (match) {
901
- // 将单引号内容转换为双引号,并转义内部的双引号和反斜杠
902
934
  var inner = match.slice(1, -1).replace(/\\/g, '\\\\').replace(/"/g, '\\"');
903
935
  return "\"".concat(inner, "\"");
904
936
  });
905
- // 2. 为对象键名添加引号(如果还没有引号)
906
- // 修复:使用 \p{L} 匹配 Unicode 字母(包括中文),使用 u 标志
907
937
  jsonValue = jsonValue.replace(/([{,]\s*)([\p{L}_$][\p{L}\p{N}_$]*)\s*:/gu, '$1"$2":');
908
- // 3. 处理属性值中的模板字符串
909
938
  jsonValue = jsonValue.replace(/`([^`]*)`/g, function (match, p1) {
910
939
  return JSON.stringify(p1);
911
940
  });
912
- // 4. 尝试解析为 JSON
913
941
  props[propName] = JSON.parse(jsonValue);
914
942
  } catch (jsonError) {
915
- // 如果都失败了,保持原值
916
943
  props[propName] = value;
917
944
  }
918
945
  }
@@ -59509,7 +59536,8 @@ function convertComponentsToHandlers(components, componentHandlers) {
59509
59536
  onRenderProcess: config.onRenderProcess,
59510
59537
  onRenderFinished: config.onRenderFinished,
59511
59538
  loader: config.loader,
59512
- label: config.label
59539
+ label: config.label,
59540
+ streamable: config.streamable
59513
59541
  });
59514
59542
  } else {
59515
59543
  handlers.push({
@@ -59584,11 +59612,12 @@ function parsedStructureSignature(parsedData) {
59584
59612
  }
59585
59613
  function hasPendingLoaderComponents(parsedData, handlers) {
59586
59614
  return parsedData.some(function (item) {
59587
- var _a;
59588
59615
  if (item.type !== 'component' || item.isComplete === true) return false;
59589
- return Boolean((_a = handlers.find(function (h) {
59616
+ var handler = handlers.find(function (h) {
59590
59617
  return h.name === item.value;
59591
- })) === null || _a === void 0 ? void 0 : _a.loader);
59618
+ });
59619
+ if (handler === null || handler === void 0 ? void 0 : handler.streamable) return false;
59620
+ return Boolean(handler === null || handler === void 0 ? void 0 : handler.loader);
59592
59621
  });
59593
59622
  }
59594
59623
  function ReactAIRenderer(_a) {
@@ -59724,7 +59753,7 @@ function ReactAIRenderer(_a) {
59724
59753
  finalComponent = [];
59725
59754
  fallbackComponent = [];
59726
59755
  _loop_3 = function (i) {
59727
- var item, currentParsedItem, _result, placeholderForFallback, componentNameMatch, componentName_1, componentHandler, displayName, cacheKey;
59756
+ var item, currentParsedItem, _result, placeholderForFallback, componentNameMatch, componentName_1, componentHandler, displayName, cacheKey, cacheKey;
59728
59757
  return __generator(this, function (_d) {
59729
59758
  switch (_d.label) {
59730
59759
  case 0:
@@ -59737,10 +59766,10 @@ function ReactAIRenderer(_a) {
59737
59766
  case 1:
59738
59767
  _result = _d.sent();
59739
59768
  finalComponent.push(_result);
59740
- return [3 /*break*/, 12];
59769
+ return [3 /*break*/, 14];
59741
59770
  case 2:
59742
59771
  componentNameMatch = item.value.match(/<([A-Z][A-Za-z0-9]*)/);
59743
- if (!componentNameMatch) return [3 /*break*/, 10];
59772
+ if (!componentNameMatch) return [3 /*break*/, 12];
59744
59773
  componentName_1 = componentNameMatch[1];
59745
59774
  componentHandler = allComponentHandlers.find(function (c) {
59746
59775
  return c.name === componentName_1;
@@ -59754,14 +59783,21 @@ function ReactAIRenderer(_a) {
59754
59783
  loader: componentHandler === null || componentHandler === void 0 ? void 0 : componentHandler.loader,
59755
59784
  key: "fallback-loader-".concat(componentName_1)
59756
59785
  });
59757
- if (!(currentParsedItem.isComplete === true || !(componentHandler === null || componentHandler === void 0 ? void 0 : componentHandler.loader))) return [3 /*break*/, 6];
59786
+ if (!(currentParsedItem.isComplete === true || !(componentHandler === null || componentHandler === void 0 ? void 0 : componentHandler.loader))) return [3 /*break*/, 7];
59758
59787
  cacheKey = "mdx-component-".concat(componentName_1, "-").concat(i);
59759
59788
  if (!completedComponentsCacheRef.current.has(cacheKey)) return [3 /*break*/, 3];
59760
59789
  _result = completedComponentsCacheRef.current.get(cacheKey);
59761
- return [3 /*break*/, 5];
59790
+ return [3 /*break*/, 6];
59762
59791
  case 3:
59763
- return [4 /*yield*/, renderMdx(item.value, scope, allComponents)];
59792
+ if (!(componentHandler === null || componentHandler === void 0 ? void 0 : componentHandler.streamable)) return [3 /*break*/, 4];
59793
+ _result = /*#__PURE__*/React.createElement(componentHandler.component, __assign(__assign({}, currentParsedItem.props), {
59794
+ key: cacheKey
59795
+ }));
59796
+ completedComponentsCacheRef.current.set(cacheKey, _result);
59797
+ return [3 /*break*/, 6];
59764
59798
  case 4:
59799
+ return [4 /*yield*/, renderMdx(item.value, scope, allComponents)];
59800
+ case 5:
59765
59801
  _result = _d.sent();
59766
59802
  if (/*#__PURE__*/React.isValidElement(_result)) {
59767
59803
  _result = /*#__PURE__*/React.cloneElement(_result, {
@@ -59773,29 +59809,37 @@ function ReactAIRenderer(_a) {
59773
59809
  }, _result);
59774
59810
  }
59775
59811
  completedComponentsCacheRef.current.set(cacheKey, _result);
59776
- _d.label = 5;
59777
- case 5:
59778
- finalComponent.push(_result);
59779
- return [3 /*break*/, 9];
59812
+ _d.label = 6;
59780
59813
  case 6:
59781
- if (!placeholderForFallback) return [3 /*break*/, 7];
59782
- finalComponent.push(placeholderForFallback);
59783
- return [3 /*break*/, 9];
59814
+ finalComponent.push(_result);
59815
+ return [3 /*break*/, 11];
59784
59816
  case 7:
59785
- return [4 /*yield*/, renderMdx(item.value, scope, allComponents)];
59786
- case 8:
59787
- _result = _d.sent();
59817
+ if (!(componentHandler === null || componentHandler === void 0 ? void 0 : componentHandler.streamable)) return [3 /*break*/, 8];
59818
+ cacheKey = "mdx-component-".concat(componentName_1, "-").concat(i);
59819
+ _result = /*#__PURE__*/React.createElement(componentHandler.component, __assign(__assign({}, currentParsedItem.props), {
59820
+ key: cacheKey
59821
+ }));
59788
59822
  finalComponent.push(_result);
59789
- _d.label = 9;
59823
+ return [3 /*break*/, 11];
59824
+ case 8:
59825
+ if (!placeholderForFallback) return [3 /*break*/, 9];
59826
+ finalComponent.push(placeholderForFallback);
59827
+ return [3 /*break*/, 11];
59790
59828
  case 9:
59791
- return [3 /*break*/, 12];
59792
- case 10:
59793
59829
  return [4 /*yield*/, renderMdx(item.value, scope, allComponents)];
59794
- case 11:
59830
+ case 10:
59795
59831
  _result = _d.sent();
59796
59832
  finalComponent.push(_result);
59797
- _d.label = 12;
59833
+ _d.label = 11;
59834
+ case 11:
59835
+ return [3 /*break*/, 14];
59798
59836
  case 12:
59837
+ return [4 /*yield*/, renderMdx(item.value, scope, allComponents)];
59838
+ case 13:
59839
+ _result = _d.sent();
59840
+ finalComponent.push(_result);
59841
+ _d.label = 14;
59842
+ case 14:
59799
59843
  fallbackComponent.length = 0;
59800
59844
  fallbackComponent.push.apply(fallbackComponent, __spreadArray([], __read(finalComponent.slice(0, i)), false));
59801
59845
  if (placeholderForFallback) {