@dimina-kit/compiler 0.0.2-dev.20260718085557 → 0.0.2-dev.20260718143821

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.
@@ -1,6 +1,7 @@
1
1
  import {
2
- checkTemplateCompatibility
3
- } from "./chunk-S7VHZTMY.js";
2
+ checkTemplateCompatibility,
3
+ takeCompatibilityWarnings
4
+ } from "./chunk-DQNLDQGT.js";
4
5
  import {
5
6
  isMainThread,
6
7
  parentPort
@@ -18,8 +19,9 @@ import {
18
19
  getWorkPath,
19
20
  resetStoreInfo,
20
21
  tagWhiteList,
22
+ toMiniProgramModuleId,
21
23
  transformRpx
22
- } from "./chunk-QLBB5HQB.js";
24
+ } from "./chunk-7F3E2G42.js";
23
25
 
24
26
  // ../../dimina/fe/packages/compiler/src/core/view-compiler.js
25
27
  import fs from "node:fs";
@@ -300,7 +302,10 @@ if (!isMainThread) {
300
302
  compileResCache.clear();
301
303
  wxsModuleRegistry.clear();
302
304
  wxsFilePathMap.clear();
303
- parentPort.postMessage({ success: true });
305
+ parentPort.postMessage({
306
+ success: true,
307
+ compatibilityWarnings: takeCompatibilityWarnings()
308
+ });
304
309
  } catch (error) {
305
310
  compileResCache.clear();
306
311
  wxsModuleRegistry.clear();
@@ -321,18 +326,27 @@ async function compileML(pages, root, progress) {
321
326
  initWxsFilePathMap(workPath);
322
327
  for (const page of pages) {
323
328
  const scriptRes = /* @__PURE__ */ new Map();
324
- buildCompileView(page, false, scriptRes, [], /* @__PURE__ */ new Set());
329
+ buildCompileView(page, false, scriptRes, /* @__PURE__ */ new Set(), /* @__PURE__ */ new Set());
325
330
  let mergeRender = "";
326
331
  for (const [key, value] of scriptRes.entries()) {
327
332
  const amdFormat = `modDefine('${key}', function(require, module, exports) {
328
333
  ${value}
329
334
  });`;
330
- const { code: minifiedCode } = await transform(amdFormat, {
331
- minify: true,
332
- target: ["es2020"],
333
- platform: "browser"
334
- });
335
- mergeRender += minifiedCode;
335
+ try {
336
+ const { code: minifiedCode } = await transform(amdFormat, {
337
+ minify: true,
338
+ target: ["es2020"],
339
+ platform: "browser"
340
+ });
341
+ mergeRender += minifiedCode;
342
+ } catch (error) {
343
+ const location = error.errors?.[0]?.location;
344
+ const sourceLines = amdFormat.split("\n");
345
+ const sourceHint = location?.line ? sourceLines.slice(Math.max(0, location.line - 3), location.line + 2).map((line, index) => `${Math.max(1, location.line - 2) + index}: ${line.trim()}`).join("\n") : "";
346
+ error.message = `\u89C6\u56FE\u6A21\u5757 ${key} \u8F6C\u6362\u5931\u8D25: ${error.message}${sourceHint ? `
347
+ ${sourceHint}` : ""}`;
348
+ throw error;
349
+ }
336
350
  }
337
351
  scriptRes.clear();
338
352
  const filename = `${page.path.replace(/\//g, "_")}`;
@@ -379,20 +393,31 @@ function scanWxsFiles(dir, workPath) {
379
393
  function registerWxsModule(modulePath) {
380
394
  wxsModuleRegistry.add(modulePath);
381
395
  }
396
+ function getTemplateCompilerOptions(scopeId) {
397
+ return {
398
+ // https://template-explorer.vuejs.org/
399
+ prefixIdentifiers: true,
400
+ hoistStatic: false,
401
+ cacheHandlers: true,
402
+ scopeId,
403
+ mode: "function",
404
+ inline: true,
405
+ // transTag has already rewritten registered built-ins and custom
406
+ // components to the reserved dd-* namespace. Every remaining unknown WXML
407
+ // tag follows glass-easel's unused-native-node fallback instead of Vue's
408
+ // component resolution.
409
+ isCustomElement: (tag) => !tag.startsWith("dd-")
410
+ };
411
+ }
382
412
  function isRegisteredWxsModule(modulePath) {
383
413
  return wxsModuleRegistry.has(modulePath);
384
414
  }
385
- function buildCompileView(module, isComponent = false, scriptRes, depthChain = [], inheritedTemplatePaths = /* @__PURE__ */ new Set()) {
415
+ function buildCompileView(module, isComponent = false, scriptRes, activePaths = /* @__PURE__ */ new Set(), inheritedTemplatePaths = /* @__PURE__ */ new Set()) {
386
416
  const currentPath = module.path;
387
- if (depthChain.includes(currentPath)) {
388
- console.warn("[view]", `\u68C0\u6D4B\u5230\u5FAA\u73AF\u4F9D\u8D56: ${[...depthChain, currentPath].join(" -> ")}`);
417
+ if (activePaths.has(currentPath)) {
389
418
  return;
390
419
  }
391
- if (depthChain.length > 20) {
392
- console.warn("[view]", `\u68C0\u6D4B\u5230\u6DF1\u5EA6\u4F9D\u8D56: ${[...depthChain, currentPath].join(" -> ")}`);
393
- return;
394
- }
395
- depthChain = [...depthChain, currentPath];
420
+ activePaths.add(currentPath);
396
421
  const allScriptModules = [];
397
422
  const currentInstruction = compileModule(module, isComponent, scriptRes, {
398
423
  skipTemplatePaths: isComponent ? inheritedTemplatePaths : /* @__PURE__ */ new Set()
@@ -411,10 +436,9 @@ function buildCompileView(module, isComponent = false, scriptRes, depthChain = [
411
436
  continue;
412
437
  }
413
438
  if (componentModule.path === module.path) {
414
- console.warn("[view]", `\u68C0\u6D4B\u5230\u5FAA\u73AF\u4F9D\u8D56\uFF0C\u8DF3\u8FC7\u5904\u7406: ${module.path}`);
415
439
  continue;
416
440
  }
417
- const componentInstruction = buildCompileView(componentModule, true, scriptRes, depthChain, childInheritedTemplatePaths);
441
+ const componentInstruction = buildCompileView(componentModule, true, scriptRes, activePaths, childInheritedTemplatePaths);
418
442
  if (componentInstruction && componentInstruction.scriptModule) {
419
443
  for (const sm of componentInstruction.scriptModule) {
420
444
  if (!allScriptModules.find((existing) => existing.path === sm.path)) {
@@ -432,6 +456,7 @@ function buildCompileView(module, isComponent = false, scriptRes, depthChain = [
432
456
  }
433
457
  compileModuleWithAllWxs(module, scriptRes, allScriptModules);
434
458
  }
459
+ activePaths.delete(currentPath);
435
460
  return { scriptModule: allScriptModules, templateModule: currentInstruction?.templateModule || [] };
436
461
  }
437
462
  function compileModule(module, isComponent, scriptRes, options = {}) {
@@ -489,15 +514,7 @@ function compileModule(module, isComponent, scriptRes, options = {}) {
489
514
  // 用于错误提示
490
515
  id: `data-v-${module.id}`,
491
516
  scoped: true,
492
- compilerOptions: {
493
- // https://template-explorer.vuejs.org/
494
- prefixIdentifiers: true,
495
- hoistStatic: false,
496
- cacheHandlers: true,
497
- scopeId: `data-v-${module.id}`,
498
- mode: "function",
499
- inline: true
500
- }
517
+ compilerOptions: getTemplateCompilerOptions(`data-v-${module.id}`)
501
518
  });
502
519
  let tplComponents = "{";
503
520
  for (const tm of compileInstruction.templateModule) {
@@ -506,14 +523,7 @@ function compileModule(module, isComponent, scriptRes, options = {}) {
506
523
  filename: tm.path,
507
524
  id: `data-v-${module.id}`,
508
525
  scoped: true,
509
- compilerOptions: {
510
- prefixIdentifiers: true,
511
- hoistStatic: false,
512
- cacheHandlers: true,
513
- scopeId: `data-v-${module.id}`,
514
- mode: "function",
515
- inline: true
516
- }
526
+ compilerOptions: getTemplateCompilerOptions(`data-v-${module.id}`)
517
527
  });
518
528
  code2 = insertWxsToRenderCode(code2, compileInstruction.scriptModule, scriptRes, tm.path);
519
529
  tplComponents += `'${tm.path}':${code2},`;
@@ -523,8 +533,12 @@ function compileModule(module, isComponent, scriptRes, options = {}) {
523
533
  const code = `Module({
524
534
  path: '${module.path}',
525
535
  id: '${module.id}',
536
+ appStyleScopeId: ${JSON.stringify(module.appStyleScopeId || null)},
537
+ sharedStyleScopeIds: ${JSON.stringify(module.sharedStyleScopeIds || [])},
538
+ styleIsolation: ${JSON.stringify(module.styleIsolation || "isolated")},
526
539
  render: ${transCode},
527
540
  usingComponents: ${JSON.stringify(module.usingComponents)},
541
+ customTabBar: ${JSON.stringify(module.customTabBar || null)},
528
542
  tplComponents: ${tplComponents},
529
543
  });`;
530
544
  const allWxsModules = collectAllWxsModules(scriptRes, /* @__PURE__ */ new Set(), compileInstruction.scriptModule || []);
@@ -678,14 +692,7 @@ function compileModuleWithAllWxs(module, scriptRes, allScriptModules) {
678
692
  filename: module.path,
679
693
  id: `data-v-${module.id}`,
680
694
  scoped: true,
681
- compilerOptions: {
682
- prefixIdentifiers: true,
683
- hoistStatic: false,
684
- cacheHandlers: true,
685
- scopeId: `data-v-${module.id}`,
686
- mode: "function",
687
- inline: true
688
- }
695
+ compilerOptions: getTemplateCompilerOptions(`data-v-${module.id}`)
689
696
  });
690
697
  let tplComponents = "{";
691
698
  for (const tm of mergedInstruction.templateModule) {
@@ -694,14 +701,7 @@ function compileModuleWithAllWxs(module, scriptRes, allScriptModules) {
694
701
  filename: tm.path,
695
702
  id: `data-v-${module.id}`,
696
703
  scoped: true,
697
- compilerOptions: {
698
- prefixIdentifiers: true,
699
- hoistStatic: false,
700
- cacheHandlers: true,
701
- scopeId: `data-v-${module.id}`,
702
- mode: "function",
703
- inline: true
704
- }
704
+ compilerOptions: getTemplateCompilerOptions(`data-v-${module.id}`)
705
705
  });
706
706
  code2 = insertWxsToRenderCode(code2, allScriptModules, scriptRes, tm.path);
707
707
  tplComponents += `'${tm.path}':${code2},`;
@@ -711,8 +711,12 @@ function compileModuleWithAllWxs(module, scriptRes, allScriptModules) {
711
711
  const code = `Module({
712
712
  path: '${module.path}',
713
713
  id: '${module.id}',
714
+ appStyleScopeId: ${JSON.stringify(module.appStyleScopeId || null)},
715
+ sharedStyleScopeIds: ${JSON.stringify(module.sharedStyleScopeIds || [])},
716
+ styleIsolation: ${JSON.stringify(module.styleIsolation || "isolated")},
714
717
  render: ${transCode},
715
718
  usingComponents: ${JSON.stringify(module.usingComponents)},
719
+ customTabBar: ${JSON.stringify(module.customTabBar || null)},
716
720
  tplComponents: ${tplComponents},
717
721
  });`;
718
722
  const cacheData = {
@@ -791,6 +795,7 @@ function toCompileTemplate(isComponent, path2, components, componentPlaceholder,
791
795
  if (!fullPath) {
792
796
  return { tpl: void 0 };
793
797
  }
798
+ const sourcePath = toMiniProgramModuleId(fullPath, workPath).replace(buildExtStripRegex(getTemplateExts()), "");
794
799
  const diagnosticSource = fullPath.startsWith(workPath) ? fullPath.slice(workPath.length) : path2;
795
800
  let content = getContentByPath(fullPath).trim();
796
801
  if (!content) {
@@ -798,7 +803,7 @@ function toCompileTemplate(isComponent, path2, components, componentPlaceholder,
798
803
  } else {
799
804
  checkTemplateCompatibility(content, diagnosticSource, components);
800
805
  if (isComponent) {
801
- content = `<wrapper name="${path2}">${content}</wrapper>`;
806
+ content = `<component-host name="${path2}">${content}</component-host>`;
802
807
  } else {
803
808
  const tempRoot = cheerio.load(content, {
804
809
  xmlMode: true,
@@ -824,7 +829,7 @@ function toCompileTemplate(isComponent, path2, components, componentPlaceholder,
824
829
  includeNodes.each((_, elem) => {
825
830
  const src = $(elem).attr("src");
826
831
  if (src) {
827
- const includeFullPath = getAbsolutePath(workPath, path2, src);
832
+ const includeFullPath = resolveTemplateDependencyPath(workPath, sourcePath, src);
828
833
  let includePath = includeFullPath.replace(workPath, "").replace(buildExtStripRegex(getTemplateExts()), "");
829
834
  const includeDiagnosticSource = includeFullPath.startsWith(workPath) ? includeFullPath.slice(workPath.length) : includePath;
830
835
  if (!includePath.startsWith("/")) {
@@ -861,13 +866,13 @@ function toCompileTemplate(isComponent, path2, components, componentPlaceholder,
861
866
  $(elem).remove();
862
867
  }
863
868
  });
864
- transTagTemplate($, templateModule, path2, components, componentPlaceholder);
865
- transTagWxs($, scriptModule, path2);
869
+ transTagTemplate($, templateModule, sourcePath, components, componentPlaceholder);
870
+ transTagWxs($, scriptModule, sourcePath);
866
871
  const importNodes = $("import");
867
872
  importNodes.each((_, elem) => {
868
873
  const src = $(elem).attr("src");
869
874
  if (src) {
870
- const importFullPath = getAbsolutePath(workPath, path2, src);
875
+ const importFullPath = resolveTemplateDependencyPath(workPath, sourcePath, src);
871
876
  let importPath = importFullPath.replace(workPath, "").replace(buildExtStripRegex(getTemplateExts()), "");
872
877
  const importDiagnosticSource = importFullPath.startsWith(workPath) ? importFullPath.slice(workPath.length) : importPath;
873
878
  if (!importPath.startsWith("/")) {
@@ -883,7 +888,7 @@ function toCompileTemplate(isComponent, path2, components, componentPlaceholder,
883
888
  transTagTemplate(
884
889
  $$,
885
890
  templateModule,
886
- path2,
891
+ importPath,
887
892
  components,
888
893
  componentPlaceholder
889
894
  );
@@ -897,7 +902,7 @@ function toCompileTemplate(isComponent, path2, components, componentPlaceholder,
897
902
  }
898
903
  });
899
904
  importNodes.remove();
900
- transAsses($, $("image"), path2);
905
+ transAsses($, $("image"), sourcePath);
901
906
  const res = [];
902
907
  transHtmlTag($.html(), res, components, componentPlaceholder);
903
908
  return {
@@ -934,6 +939,76 @@ function transAsses($, imageNodes, path2) {
934
939
  }
935
940
  });
936
941
  }
942
+ var DIMINA_SLOT_GROUP_TAG = "dimina-slot-group";
943
+ var DIMINA_FOR_SCOPE_TAG = "dimina-for-scope";
944
+ function getDirectiveAttributeNames(attrs, suffixes) {
945
+ return Object.keys(attrs || {}).filter((name) => suffixes.some((suffix) => name.endsWith(suffix)));
946
+ }
947
+ function hasForAndIf(attrs) {
948
+ return getDirectiveAttributeNames(attrs, [":for", ":for-items"]).length > 0 && getDirectiveAttributeNames(attrs, [":if"]).length > 0;
949
+ }
950
+ function groupDuplicateNamedSlots($, components) {
951
+ const slotHosts = $("*").toArray().filter((element) => {
952
+ const tag = element.tagName;
953
+ return tag === "component" || Boolean(components?.[tag]);
954
+ });
955
+ for (const host of slotHosts) {
956
+ const groups = /* @__PURE__ */ new Map();
957
+ for (const child of $(host).children().toArray()) {
958
+ const slotName = child.attribs?.slot;
959
+ if (!slotName) continue;
960
+ const group = groups.get(slotName) || [];
961
+ group.push(child);
962
+ groups.set(slotName, group);
963
+ }
964
+ for (const [slotName, nodes] of groups) {
965
+ if (nodes.length === 1 && !hasForAndIf(nodes[0].attribs)) {
966
+ continue;
967
+ }
968
+ const wrapper = $(`<${DIMINA_SLOT_GROUP_TAG}></${DIMINA_SLOT_GROUP_TAG}>`);
969
+ wrapper.attr("name", slotName);
970
+ $(nodes[0]).before(wrapper);
971
+ for (const node of nodes) {
972
+ $(node).removeAttr("slot");
973
+ wrapper.append(node);
974
+ }
975
+ }
976
+ }
977
+ }
978
+ function wrapForIfScopes($) {
979
+ const nodes = $("*").toArray();
980
+ for (const node of nodes) {
981
+ if (node.tagName === DIMINA_FOR_SCOPE_TAG || !hasForAndIf(node.attribs)) {
982
+ continue;
983
+ }
984
+ const attrsToMove = getDirectiveAttributeNames(node.attribs, [
985
+ ":for",
986
+ ":for-items",
987
+ ":for-item",
988
+ ":for-index",
989
+ ":key"
990
+ ]);
991
+ const wrapper = $(`<${DIMINA_FOR_SCOPE_TAG}></${DIMINA_FOR_SCOPE_TAG}>`);
992
+ for (const name of attrsToMove) {
993
+ wrapper.attr(name, node.attribs[name]);
994
+ $(node).removeAttr(name);
995
+ }
996
+ $(node).before(wrapper);
997
+ wrapper.append(node);
998
+ }
999
+ }
1000
+ function normalizeTemplateSyntax(html, components) {
1001
+ const $ = cheerio.load(html, {
1002
+ xmlMode: true,
1003
+ decodeEntities: false,
1004
+ _useHtmlParser2: true,
1005
+ lowerCaseTags: false,
1006
+ lowerCaseAttributeNames: false
1007
+ });
1008
+ groupDuplicateNamedSlots($, components);
1009
+ wrapForIfScopes($);
1010
+ return $.html();
1011
+ }
937
1012
  function transHtmlTag(html, res, components, componentPlaceholder) {
938
1013
  const attrsList = [];
939
1014
  const parser = new htmlparser2.Parser(
@@ -954,22 +1029,29 @@ function transHtmlTag(html, res, components, componentPlaceholder) {
954
1029
  },
955
1030
  { xmlMode: true }
956
1031
  );
957
- parser.write(html);
1032
+ parser.write(normalizeTemplateSyntax(html, components));
958
1033
  parser.end();
959
1034
  }
960
1035
  function transTag(opts) {
961
1036
  const { isStart, tag, attrs, components } = opts;
962
1037
  let res;
963
- if (tag === "slot") {
1038
+ if (tag === DIMINA_SLOT_GROUP_TAG) {
1039
+ if (isStart) {
1040
+ return `<template ${generateSlotDirective(attrs.name)}>`;
1041
+ }
1042
+ return "</template>";
1043
+ } else if (tag === DIMINA_FOR_SCOPE_TAG) {
1044
+ res = "template";
1045
+ } else if (tag === "slot") {
964
1046
  res = tag;
965
1047
  } else if (components && components[tag]) {
966
1048
  res = `dd-${tag}`;
967
1049
  } else if (tag === "component" || tag === "canvas") {
968
1050
  res = tag;
969
- } else if (!tagWhiteList.includes(tag)) {
970
- res = "dd-text";
971
- } else {
1051
+ } else if (tagWhiteList.includes(tag)) {
972
1052
  res = `dd-${tag}`;
1053
+ } else {
1054
+ res = tag;
973
1055
  }
974
1056
  let tagRes;
975
1057
  const propsAry = isStart ? getProps(attrs, tag, components) : [];
@@ -1022,7 +1104,21 @@ function generateSlotDirective(slotValue) {
1022
1104
  }
1023
1105
  function getProps(attrs, tag, components) {
1024
1106
  const attrsList = [];
1107
+ const isCustomComponent = Boolean(components && components[tag]);
1025
1108
  const propBindings = {};
1109
+ const hasEventBindings = Object.keys(attrs).some((name) => /^(?:capture-)?(?:bind|catch)(?::)?.+/.test(name));
1110
+ if (tag === "page-meta") {
1111
+ attrsList.push({
1112
+ name: "dimina-rpx-unit",
1113
+ value: "vw"
1114
+ });
1115
+ }
1116
+ if (hasEventBindings) {
1117
+ attrsList.push({
1118
+ name: "v-c-event-node",
1119
+ value: components && components[tag] ? "'component'" : "'node'"
1120
+ });
1121
+ }
1026
1122
  Object.entries(attrs).forEach(([name, value]) => {
1027
1123
  if (name.endsWith(":if")) {
1028
1124
  attrsList.push({
@@ -1052,10 +1148,20 @@ function getProps(attrs, tag, components) {
1052
1148
  value: tranValue
1053
1149
  });
1054
1150
  } else if (name === "style") {
1151
+ const parsedStyle = parseSafeBraceExp(value);
1055
1152
  attrsList.push({
1056
1153
  name: "v-c-style",
1057
- value: transformRpx(parseSafeBraceExp(value))
1154
+ value: transformRpx(parsedStyle)
1058
1155
  });
1156
+ if (isCustomComponent) {
1157
+ attrsList.push({
1158
+ name: ":dimina-wxml-style",
1159
+ value: parsedStyle
1160
+ });
1161
+ if (isWrappedByBraces(value) && parsedStyle) {
1162
+ propBindings.style = parsedStyle;
1163
+ }
1164
+ }
1059
1165
  } else if (name === "class") {
1060
1166
  if (isWrappedByBraces(value)) {
1061
1167
  attrsList.push({
@@ -1118,7 +1224,7 @@ function getProps(attrs, tag, components) {
1118
1224
  }
1119
1225
  } else if (isWrappedByBraces(value)) {
1120
1226
  const pVal = tag === "template" && name === "data" ? parseTemplateDataExp(value) : parseSafeBraceExp(value);
1121
- if (components && components[tag]) {
1227
+ if (isCustomComponent) {
1122
1228
  if (pVal && typeof pVal === "string") {
1123
1229
  propBindings[name] = pVal;
1124
1230
  }
@@ -1145,7 +1251,7 @@ function getProps(attrs, tag, components) {
1145
1251
  propsRes.push(`${name}="${escapeQuotes(value)}"`);
1146
1252
  }
1147
1253
  });
1148
- if (components && components[tag] && Object.keys(propBindings).length > 0) {
1254
+ if (isCustomComponent && Object.keys(propBindings).length > 0) {
1149
1255
  try {
1150
1256
  const validBindings = {};
1151
1257
  for (const [key, value] of Object.entries(propBindings)) {
@@ -1233,6 +1339,22 @@ function getViewPath(workPath, src) {
1233
1339
  }
1234
1340
  }
1235
1341
  }
1342
+ function resolveTemplateDependencyPath(workPath, ownerPath, src) {
1343
+ const resolvedPath = getAbsolutePath(workPath, ownerPath, src);
1344
+ if (fs.existsSync(resolvedPath) && fs.statSync(resolvedPath).isFile()) {
1345
+ return resolvedPath;
1346
+ }
1347
+ if (path.extname(resolvedPath)) {
1348
+ return resolvedPath;
1349
+ }
1350
+ for (const ext of getTemplateExts()) {
1351
+ const candidate = `${resolvedPath}${ext}`;
1352
+ if (fs.existsSync(candidate) && fs.statSync(candidate).isFile()) {
1353
+ return candidate;
1354
+ }
1355
+ }
1356
+ return resolvedPath;
1357
+ }
1236
1358
  function escapeQuotes(input) {
1237
1359
  return input.replace(/"/g, "'");
1238
1360
  }
@@ -1270,7 +1392,7 @@ function splitWithBraces(str) {
1270
1392
  function parseClassRules(cssRule) {
1271
1393
  let list = splitWithBraces(cssRule);
1272
1394
  list = list.map((item) => {
1273
- return parseBraceExp(item);
1395
+ return parseSafeBraceExp(item);
1274
1396
  });
1275
1397
  if (list.length === 1) {
1276
1398
  return list.pop();
@@ -1296,12 +1418,21 @@ function getForIndexName(attrs) {
1296
1418
  function parseForExp(exp, attrs) {
1297
1419
  const item = getForItemName(attrs);
1298
1420
  const index = getForIndexName(attrs);
1299
- const listVariableName = parseBraceExp(exp);
1421
+ const listVariableName = parseSafeBraceExp(exp);
1300
1422
  return `(${item}, ${index}) in ${listVariableName}`;
1301
1423
  }
1302
1424
  var braceRegex = /(\{\{(?:[^{}]|\{(?:[^{}]|\{[^{}]*\})*\})*\}\})|([^{}]+)/g;
1303
1425
  var noBraceRegex = /\{\{((?:[^{}]|\{(?:[^{}]|\{[^{}]*\})*\})*)\}\}/;
1304
1426
  var ternaryRegex = /[^?]+\?.+:.+/;
1427
+ var RESERVED_TEMPLATE_CONTEXT_ALIASES = /* @__PURE__ */ new Map([
1428
+ ["class", "__dimina_reserved_class"]
1429
+ ]);
1430
+ var RESERVED_TEMPLATE_CONTEXT_NAMES = new Map(
1431
+ [...RESERVED_TEMPLATE_CONTEXT_ALIASES].map(([name, alias]) => [alias, name])
1432
+ );
1433
+ function encodeReservedTemplateContextIdentifier(expression) {
1434
+ return RESERVED_TEMPLATE_CONTEXT_ALIASES.get(expression) || expression;
1435
+ }
1305
1436
  function parseBraceExp(exp) {
1306
1437
  let result;
1307
1438
  const group = [];
@@ -1309,7 +1440,7 @@ function parseBraceExp(exp) {
1309
1440
  if (result[1]) {
1310
1441
  const matchResult = result[1].match(noBraceRegex);
1311
1442
  if (matchResult) {
1312
- const statement = matchResult[1].trim();
1443
+ const statement = encodeReservedTemplateContextIdentifier(matchResult[1].trim());
1313
1444
  if (ternaryRegex.test(statement)) {
1314
1445
  group.push(`(${statement})`);
1315
1446
  } else {
@@ -1326,9 +1457,9 @@ function parseBraceExp(exp) {
1326
1457
  function parseTemplateDataExp(exp) {
1327
1458
  const matchResult = exp.trim().match(/^\{\{([\s\S]*)\}\}$/);
1328
1459
  if (matchResult) {
1329
- return `{${matchResult[1].trim()}}`;
1460
+ return addOptionalChaining(`{${matchResult[1].trim()}}`);
1330
1461
  }
1331
- return `{${parseBraceExp(exp)}}`;
1462
+ return `{${parseSafeBraceExp(exp)}}`;
1332
1463
  }
1333
1464
  function transTagWxs($, scriptModule, filePath) {
1334
1465
  const wxsNodes = $(getViewScriptTags().join(","));
@@ -1476,10 +1607,7 @@ function insertWxsToRenderCode(code, scriptModule, scriptRes, filename = "render
1476
1607
  });
1477
1608
  declarations.push(`const ${localIdentifier} = require(${JSON.stringify(requireModuleName)});`);
1478
1609
  }
1479
- if (wxsBindings.length === 0) {
1480
- return getProgramCode(code, ast);
1481
- }
1482
- if (renderBody?.type === "BlockStatement") {
1610
+ if (wxsBindings.length > 0 && renderBody?.type === "BlockStatement") {
1483
1611
  codeReplacements.push({
1484
1612
  type: "insert",
1485
1613
  start: renderBody.start + 1,
@@ -1491,6 +1619,15 @@ ${declarations.join("\n")}`
1491
1619
  walk(ast, {
1492
1620
  enter(node) {
1493
1621
  if (node.type === "MemberExpression" && node.object?.type === "Identifier" && node.object.name === "_ctx" && !node.computed && node.property?.type === "Identifier") {
1622
+ const reservedName = RESERVED_TEMPLATE_CONTEXT_NAMES.get(node.property.name);
1623
+ if (reservedName) {
1624
+ codeReplacements.push({
1625
+ start: node.property.start,
1626
+ end: node.property.end,
1627
+ value: reservedName
1628
+ });
1629
+ return;
1630
+ }
1494
1631
  const replacement = wxsBindings.find((item) => item.templatePropertyName === node.property.name);
1495
1632
  if (replacement) {
1496
1633
  codeReplacements.push({
@@ -1502,6 +1639,9 @@ ${declarations.join("\n")}`
1502
1639
  }
1503
1640
  }
1504
1641
  });
1642
+ if (codeReplacements.length === 0) {
1643
+ return getProgramCode(code, ast);
1644
+ }
1505
1645
  const transformed = applyCodeReplacements(code, codeReplacements);
1506
1646
  const transformedAst = parseJs(transformed, filename);
1507
1647
  return getProgramCode(transformed, transformedAst);
@@ -1518,6 +1658,7 @@ export {
1518
1658
  generateVModelTemplate,
1519
1659
  initWxsFilePathMap,
1520
1660
  loadWxsModule,
1661
+ normalizeTemplateSyntax,
1521
1662
  parseBraceExp,
1522
1663
  parseClassRules,
1523
1664
  parseKeyExpression,
package/dist/pool.node.js CHANGED
@@ -3,12 +3,12 @@ import {
3
3
  publishToDist,
4
4
  resetCompilerState,
5
5
  setupCompile
6
- } from "./pool.node-chunks/chunk-LVUKEB4F.js";
6
+ } from "./pool.node-chunks/chunk-LKL7FBHG.js";
7
7
  import {
8
8
  getAppConfigInfo,
9
9
  getAppId,
10
10
  getAppName
11
- } from "./pool.node-chunks/chunk-QLBB5HQB.js";
11
+ } from "./pool.node-chunks/chunk-7F3E2G42.js";
12
12
 
13
13
  // src/pool-node.js
14
14
  import { createRequire } from "node:module";