@lark.js/mvc 0.0.2 → 0.0.4

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.
@@ -14638,17 +14638,17 @@ function restoreComments(source, comments) {
14638
14638
  }
14639
14639
  function processViewEvents(source) {
14640
14640
  return source.replace(
14641
- /v-(\w+)="([^"]+)"/g,
14641
+ /@(\w+)="([^"]+)"/g,
14642
14642
  (fullAttr, eventName, attrValue) => {
14643
14643
  const eventMatch = attrValue.match(/^(\w+)\((.*)\)$/s);
14644
14644
  if (!eventMatch) return fullAttr;
14645
14645
  const handlerName = eventMatch[1];
14646
14646
  const paramsStr = eventMatch[2].trim();
14647
14647
  if (!paramsStr) {
14648
- return `v-${eventName}="${VIEW_ID_PLACEHOLDER}${SPLITTER}${handlerName}()"`;
14648
+ return `@${eventName}="${VIEW_ID_PLACEHOLDER}${SPLITTER}${handlerName}()"`;
14649
14649
  }
14650
14650
  const urlParams = jsObjectToUrlParams(paramsStr);
14651
- return `v-${eventName}="${VIEW_ID_PLACEHOLDER}${SPLITTER}${handlerName}(${urlParams})"`;
14651
+ return `@${eventName}="${VIEW_ID_PLACEHOLDER}${SPLITTER}${handlerName}(${urlParams})"`;
14652
14652
  }
14653
14653
  );
14654
14654
  }
@@ -14721,7 +14721,7 @@ function convertArtSyntax(source, debug) {
14721
14721
  }
14722
14722
  if (blockStack.length > 0) {
14723
14723
  const unclosed = blockStack.map((b) => `"${b.ctrl}" at line ${b.line}`).join(", ");
14724
- throw new Error(`[@lark/mvc error] unclosed block(s): ${unclosed}`);
14724
+ throw new Error(`[@lark.js/mvc error] unclosed block(s): ${unclosed}`);
14725
14725
  }
14726
14726
  return result.join("");
14727
14727
  }
@@ -14815,12 +14815,12 @@ function convertArtExpression(code, debug, lineNo, blockStack = []) {
14815
14815
  }
14816
14816
  return `${debugPrefix}<%}else{%>`;
14817
14817
  }
14818
- case "each": {
14819
- blockStack.push({ ctrl: "each", line: lineNo });
14818
+ case "forOf": {
14819
+ blockStack.push({ ctrl: "forOf", line: lineNo });
14820
14820
  const object = tokens[0];
14821
14821
  if (tokens.length > 1 && tokens[1] !== "as") {
14822
14822
  throw new Error(
14823
- `[@lark/mvc error] bad each syntax: {{${code}}}. Expected "as" keyword, got "${tokens[1]}". Usage: {{each list as item [index]}}`
14823
+ `[@lark.js/mvc error] bad forOf syntax: {{${code}}}. Expected "as" keyword, got "${tokens[1]}". Usage: {{forOf list as item [index]}}`
14824
14824
  );
14825
14825
  }
14826
14826
  const restTokens = tokens.slice(2);
@@ -14842,12 +14842,12 @@ function convertArtExpression(code, debug, lineNo, blockStack = []) {
14842
14842
  }
14843
14843
  return `${debugPrefix}<%for(let ${index}=0${refExpr},${refObjCount}=${refObj}.length${lastCount};${index}<${refObjCount};${index}++){${firstAndLast}${valueDecl}%>`;
14844
14844
  }
14845
- case "parse": {
14846
- blockStack.push({ ctrl: "parse", line: lineNo });
14845
+ case "forIn": {
14846
+ blockStack.push({ ctrl: "forIn", line: lineNo });
14847
14847
  const object = tokens[0];
14848
14848
  if (tokens.length > 1 && tokens[1] !== "as") {
14849
14849
  throw new Error(
14850
- `[@lark/mvc error] bad parse syntax: {{${code}}}. Expected "as" keyword, got "${tokens[1]}". Usage: {{for-in obj as val [key]}}`
14850
+ `[@lark.js/mvc error] bad forIn syntax: {{${code}}}. Expected "as" keyword, got "${tokens[1]}". Usage: {{for-in obj as val [key]}}`
14851
14851
  );
14852
14852
  }
14853
14853
  const restTokens2 = tokens.slice(2);
@@ -14867,19 +14867,19 @@ function convertArtExpression(code, debug, lineNo, blockStack = []) {
14867
14867
  case "set":
14868
14868
  return `${debugPrefix}<%let ${tokens.join(" ")};%>`;
14869
14869
  case "/if":
14870
- case "/each":
14871
- case "/parse":
14870
+ case "/forOf":
14871
+ case "/forIn":
14872
14872
  case "/for": {
14873
14873
  const expectedCtrl = keyword.substring(1);
14874
14874
  const last = blockStack.pop();
14875
14875
  if (!last) {
14876
14876
  throw new Error(
14877
- `[@lark/mvc error(template] unexpected {{${code}}}: no matching open block`
14877
+ `[@lark.js/mvc error] unexpected {{${code}}}: no matching open block`
14878
14878
  );
14879
14879
  }
14880
14880
  if (last.ctrl !== expectedCtrl) {
14881
14881
  throw new Error(
14882
- `[@lark/mvc error(template] unexpected {{${code}}}: expected {{/${last.ctrl}}} to close block opened at line ${last.line}`
14882
+ `[@lark.js/mvc error] unexpected {{${code}}}: expected {{/${last.ctrl}}} to close block opened at line ${last.line}`
14883
14883
  );
14884
14884
  }
14885
14885
  return `${debugPrefix}<%}%>`;
@@ -14943,7 +14943,7 @@ function parseAsExpr(expr) {
14943
14943
  function compileToFunction(source, debug, file) {
14944
14944
  const matcher = /<%([@=!:])?([\s\S]*?)%>|$/g;
14945
14945
  let index = 0;
14946
- let funcSource = `$p+='`;
14946
+ let funcSource = `$out+='`;
14947
14947
  let hasAtRule = false;
14948
14948
  const escapeSlashRegExp = /\\|'/g;
14949
14949
  const escapeBreakReturnRegExp = /\r|\n/g;
@@ -14969,17 +14969,17 @@ function compileToFunction(source, debug, file) {
14969
14969
  }
14970
14970
  if (operate === "@") {
14971
14971
  hasAtRule = true;
14972
- funcSource += `'+($expr='<%${operate + expr}%>',$i($$ref,${content}))+'`;
14972
+ funcSource += `'+($dbgExpr='<%${operate + expr}%>',$refFn($refAlt,${content}))+'`;
14973
14973
  } else if (operate === "=" || operate === ":") {
14974
- funcSource += `'+($expr='<%${operate + expr}%>',$e(${content}))+'`;
14974
+ funcSource += `'+($dbgExpr='<%${operate + expr}%>',$encHtml(${content}))+'`;
14975
14975
  } else if (operate === "!") {
14976
- if (!content.startsWith("$eu(") || !content.endsWith(")")) {
14977
- content = `$n(${content})`;
14976
+ if (!content.startsWith("$encUri(") || !content.endsWith(")")) {
14977
+ content = `$strSafe(${content})`;
14978
14978
  }
14979
- funcSource += `'+($expr='<%${operate + expr}%>',${content})+'`;
14979
+ funcSource += `'+($dbgExpr='<%${operate + expr}%>',${content})+'`;
14980
14980
  } else if (content) {
14981
14981
  if (line > -1) {
14982
- funcSource += `';$line=${line};$art='${art}';`;
14982
+ funcSource += `';$dbgLine=${line};$dbgArt='${art}';`;
14983
14983
  content = "";
14984
14984
  } else {
14985
14985
  funcSource += `';`;
@@ -14988,19 +14988,19 @@ function compileToFunction(source, debug, file) {
14988
14988
  funcSource = funcSource.substring(0, funcSource.length - 4) + ";";
14989
14989
  }
14990
14990
  if (expr) {
14991
- funcSource += `$expr='<%${expr}%>';`;
14991
+ funcSource += `$dbgExpr='<%${expr}%>';`;
14992
14992
  }
14993
- funcSource += content + `;$p+='`;
14993
+ funcSource += content + `;$out+='`;
14994
14994
  }
14995
14995
  } else {
14996
14996
  if (operate === "@") {
14997
14997
  hasAtRule = true;
14998
- funcSource += `'+$i($$ref,${content})+'`;
14998
+ funcSource += `'+$refFn($refAlt,${content})+'`;
14999
14999
  } else if (operate === "=" || operate === ":") {
15000
- funcSource += `'+$e(${content})+'`;
15000
+ funcSource += `'+$encHtml(${content})+'`;
15001
15001
  } else if (operate === "!") {
15002
- if (!content.startsWith("$eu(") || !content.endsWith(")")) {
15003
- content = `$n(${content})`;
15002
+ if (!content.startsWith("$encUri(") || !content.endsWith(")")) {
15003
+ content = `$strSafe(${content})`;
15004
15004
  }
15005
15005
  funcSource += `'+${content}+'`;
15006
15006
  } else if (content) {
@@ -15008,28 +15008,28 @@ function compileToFunction(source, debug, file) {
15008
15008
  if (funcSource.endsWith(`+'';`)) {
15009
15009
  funcSource = funcSource.substring(0, funcSource.length - 4) + ";";
15010
15010
  }
15011
- funcSource += `${content};$p+='`;
15011
+ funcSource += `${content};$out+='`;
15012
15012
  }
15013
15013
  }
15014
15014
  return match;
15015
15015
  });
15016
15016
  funcSource += `';`;
15017
- funcSource = funcSource.replace(/\$p\+='';/g, "");
15018
- funcSource = funcSource.replace(/\$p\+=''\+/g, "$p+=");
15017
+ funcSource = funcSource.replace(/\$out\+='';/g, "");
15018
+ funcSource = funcSource.replace(/\$out\+=''\+/g, "$out+=");
15019
15019
  if (debug) {
15020
15020
  const filePart = file ? `\\r\\n\\tat file:${file}` : "";
15021
- funcSource = `let $expr,$art,$line;try{${funcSource}}catch(ex){let msg='render view error:'+(ex.message||ex);if($art)msg+='\\r\\n\\tsrc art:{{'+$art+'}}\\r\\n\\tat line:'+$line;msg+='\\r\\n\\t'+($art?'translate to:':'expr:');msg+=$expr+'${filePart}';throw msg;}`;
15021
+ funcSource = `let $dbgExpr,$dbgArt,$dbgLine;try{${funcSource}}catch(ex){let msg='render view error:'+(ex.message||ex);if($dbgArt)msg+='\\r\\n\\tsrc art:{{'+$dbgArt+'}}\\r\\n\\tat line:'+$dbgLine;msg+='\\r\\n\\t'+($dbgArt?'translate to:':'expr:');msg+=$dbgExpr+'${filePart}';throw msg;}`;
15022
15022
  }
15023
15023
  const viewIdRegExp = new RegExp(String.fromCharCode(31), "g");
15024
15024
  funcSource = funcSource.replace(viewIdRegExp, `'+$viewId+'`);
15025
- const atRule = hasAtRule ? `if(!$i){$i=(ref,v,k,f)=>{for(f=ref[$g];--f;)if(ref[k=$g+f]===v)return k;ref[k=$g+ref[$g]++]=v;return k;}}` : "";
15026
- const encode = `if(!$n){let $em={'&':'amp','<':'lt','>':'gt','"':'#34','\\'':'#39','\`':'#96'},$er=/[&<>"'\`]/g,$ef=m=>'&'+$em[m]+';';$n=v=>''+(v==null?'':v);$e=v=>$n(v).replace($er,$ef)}`;
15027
- const encodeURIMore = `if(!$eu){let $um={'!':'%21','\\'':'%27','(':'%28',')':'%29','*':'%2A'},$uf=m=>$um[m],$uq=/[!')(*]/g;$eu=v=>encodeURIComponent($n(v)).replace($uq,$uf)}`;
15028
- const encodeQuote = `if(!$eq){let $qr=/['"\\\\]/g;$eq=v=>$n(v).replace($qr,'\\\\$&')}`;
15029
- const refFallback = "if(!$$ref)$$ref=$$;";
15025
+ const atRule = hasAtRule ? `if(!$refFn){$refFn=(ref,v,k,f)=>{for(f=ref[$splitter];--f;)if(ref[k=$splitter+f]===v)return k;ref[k=$splitter+ref[$splitter]++]=v;return k;}}` : "";
15026
+ const encode = `if(!$strSafe){let $entMap={'&':'amp','<':'lt','>':'gt','"':'#34','\\'':'#39','\`':'#96'},$entReg=/[&<>"'\`]/g,$entFn=m=>'&'+$entMap[m]+';';$strSafe=v=>''+(v==null?'':v);$encHtml=v=>$strSafe(v).replace($entReg,$entFn)}`;
15027
+ const encodeURIMore = `if(!$encUri){let $uriMap={'!':'%21','\\'':'%27','(':'%28',')':'%29','*':'%2A'},$uriFn=m=>$uriMap[m],$uriReg=/[!')(*]/g;$encUri=v=>encodeURIComponent($strSafe(v)).replace($uriReg,$uriFn)}`;
15028
+ const encodeQuote = `if(!$encQuote){let $qReg=/['"\\\\]/g;$encQuote=v=>$strSafe(v).replace($qReg,'\\\\$&')}`;
15029
+ const refFallback = "if(!$refAlt)$refAlt=$data;";
15030
15030
  const fns = `${refFallback}${encode}${encodeURIMore}${encodeQuote}${atRule};`;
15031
- const fullSource = `${fns}let $g='\\x1e',$_temp,$p=''{{VARS}};${funcSource}return $p`;
15032
- return `($$,$viewId,$$ref,$e,$n,$eu,$i,$eq)=>{${fullSource}}`;
15031
+ const fullSource = `${fns}let $splitter='\\x1e',$tmp,$out=''{{VARS}};${funcSource}return $out`;
15032
+ return `($data,$viewId,$refAlt,$encHtml,$strSafe,$encUri,$refFn,$encQuote)=>{${fullSource}}`;
15033
15033
  }
15034
15034
  function compileTemplate(source, options = {}) {
15035
15035
  const { debug = false, globalVars = [], file } = options;
@@ -15038,17 +15038,17 @@ function compileTemplate(source, options = {}) {
15038
15038
  const viewEventProcessed = processViewEvents(converted);
15039
15039
  const finalSource = restoreComments(viewEventProcessed, comments);
15040
15040
  const funcBody = compileToFunction(finalSource, debug, file);
15041
- const varDeclarations = globalVars.map((key) => `,${key}=$$.${key}`).join("");
15041
+ const varDeclarations = globalVars.map((key) => `,${key}=$data.${key}`).join("");
15042
15042
  const funcWithVars = funcBody.replace("{{VARS}}", () => varDeclarations);
15043
15043
  return `export default function(data, selfId, refData) {
15044
- let $$ = data || {},
15044
+ let $data = data || {},
15045
15045
  $viewId = selfId || '';
15046
- return (${funcWithVars})($$, $viewId, refData,
15047
- /* $e */ v => String(v == null ? '' : v).replace(/[&<>"'\`]/g, m => '&' + ({'&':'amp','<':'lt','>':'gt','"':'#34',"'":'#39','\`':'#96'})[m] + ';'),
15048
- /* $n */ v => String(v == null ? '' : v),
15049
- /* $eu */ null,
15050
- /* $i */ null,
15051
- /* $eq */ null
15046
+ return (${funcWithVars})($data, $viewId, refData,
15047
+ /* $encHtml */ v => String(v == null ? '' : v).replace(/[&<>"'\`]/g, m => '&' + ({'&':'amp','<':'lt','>':'gt','"':'#34',"'":'#39','\`':'#96'})[m] + ';'),
15048
+ /* $strSafe */ v => String(v == null ? '' : v),
15049
+ /* $encUri */ null,
15050
+ /* $refFn */ null,
15051
+ /* $encQuote */ null
15052
15052
  );
15053
15053
  }`;
15054
15054
  }
@@ -15157,7 +15157,7 @@ function fallbackExtractVariables(source) {
15157
15157
  while ((m = outputRegExp.exec(source)) !== null) {
15158
15158
  vars.add(m[1]);
15159
15159
  }
15160
- const eachRegExp = /\{\{each\s+([a-zA-Z_$][\w$]*)\s+as/g;
15160
+ const eachRegExp = /\{\{forOf\s+([a-zA-Z_$][\w$]*)\s+as/g;
15161
15161
  while ((m = eachRegExp.exec(source)) !== null) {
15162
15162
  vars.add(m[1]);
15163
15163
  }
@@ -15203,77 +15203,88 @@ var BUILTIN_GLOBALS = {
15203
15203
  //
15204
15204
  // These variables appear in the generated template function signature
15205
15205
  // or body. They must be excluded from extractGlobalVars() so that
15206
- // they are not mistaken for user data variables and destructured from $$.
15206
+ // they are not mistaken for user data variables and destructured from $data.
15207
15207
  // SPLITTER character constant (same as \x1e), used as namespace separator
15208
15208
  // for refData keys, event attribute encoding, and internal data structures.
15209
- // Declared as: let $g='\x1e'
15210
- $g: 1,
15211
- // refData — the data object passed from Updater to the template function.
15212
- // User variables are destructured from $$ at the top of the function:
15213
- // let {name, age} = $$;
15209
+ // Declared as: let $splitter='\x1e'
15210
+ $splitter: 1,
15211
+ // Data — the data object passed from Updater to the template function.
15212
+ // User variables are destructured from $data at the top of the function:
15213
+ // let {name, age} = $data;
15214
15214
  // This is the first parameter of the generated arrow function.
15215
- $$: 1,
15215
+ $data: 1,
15216
15216
  // Null-safe toString: v => '' + (v == null ? '' : v)
15217
15217
  // Converts null/undefined to empty string, otherwise calls toString().
15218
15218
  // Wraps every {{!raw}} output to prevent "null" / "undefined" rendering.
15219
- $n: 1,
15220
- // HTML entity encoder: v => $n(v).replace(/[&<>"'`]/g, entityMap)
15219
+ $strSafe: 1,
15220
+ // HTML entity encoder: v => $strSafe(v).replace(/[&<>"'`]/g, entityMap)
15221
15221
  // Encodes &, <, >, ", ', ` to HTML entities (&amp; &lt; etc.)
15222
15222
  // Applied to all {{=escaped}} and {{:binding}} outputs.
15223
- $e: 1,
15224
- // HTML entity map — internal object used by $e:
15223
+ $encHtml: 1,
15224
+ // HTML entity map — internal object used by $encHtml:
15225
15225
  // {'&':'amp','<':'gt','>':'gt','"':'#34','\'':'#39','`':'#96'}
15226
- // Not a standalone function; referenced inside $e's closure.
15227
- $em: 1,
15228
- // HTML entity RegExp — internal regexp used by $e:
15226
+ // Not a standalone function; referenced inside $encHtml's closure.
15227
+ $entMap: 1,
15228
+ // HTML entity RegExp — internal regexp used by $encHtml:
15229
15229
  // /[&<>"'`]/g
15230
- $er: 1,
15231
- // HTML entity replacer function — internal helper used by $e:
15232
- // m => '&' + $em[m] + ';'
15233
- // Maps each matched character to its entity string.
15234
- $ef: 1,
15230
+ $entReg: 1,
15231
+ // HTML entity replacer function — internal helper used by $encHtml:
15232
+ // m => '&' + $entMap[m] + ';'
15233
+ // Maps matched character to its entity string.
15234
+ $entFn: 1,
15235
15235
  // Output buffer — the string accumulator for rendered HTML.
15236
- // All template output is appended via $p += '...'.
15237
- // Declared as: let $p = ''
15238
- $p: 1,
15236
+ // All template output is appended via $out += '...'.
15237
+ // Declared as: let $out = ''
15238
+ $out: 1,
15239
15239
  // Reference lookup: (refData, value) => key
15240
15240
  // Finds or allocates a SPLITTER-prefixed key in refData for a given
15241
15241
  // object reference. Used by {{@ref}} operator for passing object
15242
- // references to child views via lark-view attributes.
15243
- // Aligned with mx.js Updater_Ref.
15244
- $i: 1,
15245
- // URI encoder: v => encodeURIComponent($n(v)).replace(/[!')(*]/g, extraMap)
15242
+ // references to child views via v-lark attributes.
15243
+ $refFn: 1,
15244
+ // URI encoder: v => encodeURIComponent($strSafe(v)).replace(/[!')(*]/g, extraMap)
15246
15245
  // Extends encodeURIComponent with encoding of ! ' ( ) *.
15247
- // Applied to values in v-event URL parameters and {{!uri}} contexts.
15248
- $eu: 1,
15249
- // Quote encoder: v => $n(v).replace(/['"\\]/g, '\\$&')
15246
+ // Applied to values in @event URL parameters and {{!uri}} contexts.
15247
+ $encUri: 1,
15248
+ // URI encode map internal object used by $encUri:
15249
+ // {'!':'%21','\'':'%27','(':'%28',')':'%29','*':'%2A'}
15250
+ $uriMap: 1,
15251
+ // URI encode replacer — internal helper used by $encUri:
15252
+ // m => $uriMap[m]
15253
+ $uriFn: 1,
15254
+ // URI encode regexp — internal regexp used by $encUri:
15255
+ // /[!')(*]/g
15256
+ $uriReg: 1,
15257
+ // Quote encoder: v => $strSafe(v).replace(/['"\\]/g, '\\$&')
15250
15258
  // Escapes quotes and backslashes for safe embedding in HTML attribute
15251
15259
  // values (e.g. data-json='...').
15252
- $eq: 1,
15260
+ $encQuote: 1,
15261
+ // Quote encode regexp — internal regexp used by $encQuote:
15262
+ // /['"\\]/g
15263
+ $qReg: 1,
15253
15264
  // View ID — the unique identifier of the owning View instance.
15254
- // Injected into v-event attribute values at render time so that
15265
+ // Injected into @event attribute values at render time so that
15255
15266
  // EventDelegator can dispatch events to the correct View handler.
15256
15267
  // The \x1f placeholder in compiled output is replaced with '+$viewId+'.
15257
15268
  $viewId: 1,
15258
15269
  // Debug: current expression text — stores the template expression being
15259
15270
  // evaluated, for error reporting. Only present in debug mode.
15260
- // e.g. $expr='<%=user.name%>'
15261
- $expr: 1,
15271
+ // e.g. $dbgExpr='<%=user.name%>'
15272
+ $dbgExpr: 1,
15262
15273
  // Debug: original art syntax — stores the {{}} template syntax before
15263
15274
  // conversion, for error reporting. Only present in debug mode.
15264
- // e.g. $art='{{=user.name}}'
15265
- $art: 1,
15275
+ // e.g. $dbgArt='{{=user.name}}'
15276
+ $dbgArt: 1,
15266
15277
  // Debug: source line number — tracks the current line in the template
15267
15278
  // source, for error reporting. Only present in debug mode.
15268
- $line: 1,
15269
- // refData alias — fallback reference lookup table.
15270
- // Defaults to $$ when no explicit $$ref is provided.
15271
- // Ensures $i() does not crash when @ operator is used without refData.
15272
- $$ref: 1,
15279
+ $dbgLine: 1,
15280
+ // RefData alias — fallback reference lookup table.
15281
+ // Defaults to $data when no explicit $refAlt is provided.
15282
+ // Ensures $refFn() does not crash when @ operator is used without refData.
15283
+ $refAlt: 1,
15273
15284
  // Temporary variable — used by the compiler for intermediate
15274
15285
  // expression results in generated code (e.g. loop variables,
15275
- // conditional branches). Declared as: let $_temp
15276
- $_temp: 1,
15286
+ // conditional branches). Declared as: let $tmp
15287
+ $tmp: 1,
15277
15288
  // JS literals
15278
15289
  undefined: 1,
15279
15290
  null: 1,