parseman 0.20.0 → 0.22.0

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.
@@ -1254,13 +1254,25 @@ function tryFastLabeledScan(input, cur, trivia2) {
1254
1254
  }
1255
1255
  function recordTriviaChunks(ctx, chunks) {
1256
1256
  const kinds = ctx.triviaKindLabels;
1257
+ const mask = ctx._triviaCaptureMask;
1257
1258
  for (const ch of chunks) {
1258
1259
  pushTriviaLogEntry(ctx, ch.start, ch.end, kinds ? ch.kindIndex : void 0);
1259
1260
  if (ctx.captureTrivia && (ctx._cstBuf !== void 0 || ctx._cstTriviaLog !== void 0)) {
1260
- pushCstTriviaEntry(ctx, ch.start, ch.end, kinds ? ch.kindIndex : void 0);
1261
+ if (mask === void 0 || kinds === void 0 || (mask & 1 << ch.kindIndex) !== 0) {
1262
+ pushCstTriviaEntry(ctx, ch.start, ch.end, kinds ? ch.kindIndex : void 0);
1263
+ }
1261
1264
  }
1262
1265
  }
1263
1266
  }
1267
+ function triviaKindMask(labels, keep) {
1268
+ if (!labels) return void 0;
1269
+ let mask = 0;
1270
+ for (const name of keep) {
1271
+ const idx = labels.indexOf(name);
1272
+ if (idx >= 0) mask |= 1 << idx;
1273
+ }
1274
+ return mask;
1275
+ }
1264
1276
 
1265
1277
  // src/combinators/trivia-skip.ts
1266
1278
  var NOOP_COMMIT = () => {
@@ -1717,7 +1729,9 @@ function tagRule(r, key) {
1717
1729
  r._ruleName = key;
1718
1730
  if (r._def.tag === "node" && r._def.type === void 0) r._def.type = key;
1719
1731
  }
1720
- function rules(factory) {
1732
+ function rules(a, b) {
1733
+ const factory = typeof a === "function" ? a : b;
1734
+ const options = typeof a === "function" ? b : a;
1721
1735
  const cache = {};
1722
1736
  const proxy = new Proxy(cache, {
1723
1737
  get(target, key) {
@@ -1745,6 +1759,12 @@ function rules(factory) {
1745
1759
  cache[key] = parser2;
1746
1760
  }
1747
1761
  }
1762
+ if (options?.trivia !== void 0) {
1763
+ for (const key of Object.keys(definitions)) {
1764
+ const rule = cache[key];
1765
+ if (rule && !rule._meta.isTrivia) rule._meta.grammarTrivia = options.trivia;
1766
+ }
1767
+ }
1748
1768
  for (const key of Object.keys(definitions)) {
1749
1769
  markUnusedValues(cache[key]);
1750
1770
  }
@@ -1912,10 +1932,15 @@ function node(typeOrCombinator, combinatorOrBuild, buildOrOpts, maybeOpts) {
1912
1932
  const saved = beginCstNodeCapture(ctx);
1913
1933
  const savedFields = ctx._fields;
1914
1934
  ctx._fields = capturesFields ? [] : void 0;
1935
+ const savedMask = ctx._triviaCaptureMask;
1936
+ if (build === void 0 && ctx.build?._parsemanTriviaKinds !== void 0 && def.type !== void 0) {
1937
+ ctx._triviaCaptureMask = ctx.build._parsemanTriviaKinds(def.type);
1938
+ }
1915
1939
  if (!capturesTrivia) ctx.captureTrivia = false;
1916
1940
  const r = combinator.parse(input, pos, ctx);
1917
1941
  const fields = capturesFields ? buildFieldMap(ctx._fields) : void 0;
1918
1942
  ctx._fields = savedFields;
1943
+ ctx._triviaCaptureMask = savedMask;
1919
1944
  const { children, rawChildren, triviaLog } = endCstNodeCapture(ctx, saved);
1920
1945
  if (!r.ok) return r;
1921
1946
  const st = clonesState && ctx.state !== void 0 ? Object.assign({}, ctx.state) : void 0;
@@ -2053,7 +2078,13 @@ function parser(opts, root) {
2053
2078
  trivia: opts.trivia,
2054
2079
  ...opts.trivia._meta.triviaKindLabels ? { triviaKindLabels: opts.trivia._meta.triviaKindLabels } : {}
2055
2080
  } : {},
2056
- ...opts.captureTrivia || _ctx?.captureTrivia ? { captureTrivia: true } : {}
2081
+ ...opts.captureTrivia || _ctx?.captureTrivia ? { captureTrivia: true } : {},
2082
+ // Kind-filter for per-node capture. Resolve against this scope's trivia
2083
+ // labels — this parser's own trivia if it declares one, else the INHERITED
2084
+ // labels (`_ctx.triviaKindLabels`), so captureTriviaKinds still applies when
2085
+ // trivia is inherited rather than re-declared here. No labels → undefined
2086
+ // (capture all).
2087
+ ...opts.captureTriviaKinds && !clearTrivia ? { _triviaCaptureMask: triviaKindMask(opts.trivia?._meta.triviaKindLabels ?? _ctx?.triviaKindLabels, opts.captureTriviaKinds) } : {}
2057
2088
  };
2058
2089
  const result = root.parse(input, pos ?? 0, ctx);
2059
2090
  if (trackLines) {
@@ -3203,7 +3234,7 @@ function scanBranchLabeled(shape, kindIndex, mint) {
3203
3234
  ` if (${m.end} > _e) {`,
3204
3235
  ` if (_cap) {`,
3205
3236
  ` if (_ctx._triviaLog !== undefined) _ctx._triviaLog.push(_e, ${m.end}, ${kindIndex})`,
3206
- ` if (_ctx._cstTriviaLog !== undefined) _ctx._cstTriviaLog.push(_e, ${m.end}, _ctx._cstRawChildren ? _ctx._cstRawChildren.length : 0, ${kindIndex})`,
3237
+ ` if (_ctx._cstTriviaLog !== undefined && (_ctx._triviaCaptureMask === undefined || (_ctx._triviaCaptureMask & ${1 << kindIndex}))) _ctx._cstTriviaLog.push(_e, ${m.end}, _ctx._cstRawChildren ? _ctx._cstRawChildren.length : 0, ${kindIndex})`,
3207
3238
  ` }`,
3208
3239
  ` _e = ${m.end}`,
3209
3240
  ` continue`,
@@ -3319,7 +3350,7 @@ function buildLabeledRegexTriviaFnDecl(fnName, spec, reNames) {
3319
3350
  ` const _ce = _e + _m${i}[0].length`,
3320
3351
  ` if (_cap) {`,
3321
3352
  ` if (_ctx._triviaLog !== undefined) _ctx._triviaLog.push(_e, _ce, ${k})`,
3322
- ` if (_ctx._cstTriviaLog !== undefined) _ctx._cstTriviaLog.push(_e, _ce, _ctx._cstRawChildren ? _ctx._cstRawChildren.length : 0, ${k})`,
3353
+ ` if (_ctx._cstTriviaLog !== undefined && (_ctx._triviaCaptureMask === undefined || (_ctx._triviaCaptureMask & ${1 << k}))) _ctx._cstTriviaLog.push(_e, _ce, _ctx._cstRawChildren ? _ctx._cstRawChildren.length : 0, ${k})`,
3323
3354
  ` }`,
3324
3355
  ` _e = _ce`,
3325
3356
  ` _matched = true`,
@@ -3357,7 +3388,7 @@ function buildLabeledRuntimeTriviaFnDecl(fnName, spec, rpStartIndex) {
3357
3388
  ` const _ce = _r${i}.span.end`,
3358
3389
  ` if (_cap) {`,
3359
3390
  ` if (_ctx._triviaLog !== undefined) _ctx._triviaLog.push(_e, _ce, ${k})`,
3360
- ` if (_ctx._cstTriviaLog !== undefined) _ctx._cstTriviaLog.push(_e, _ce, _ctx._cstRawChildren ? _ctx._cstRawChildren.length : 0, ${k})`,
3391
+ ` if (_ctx._cstTriviaLog !== undefined && (_ctx._triviaCaptureMask === undefined || (_ctx._triviaCaptureMask & ${1 << k}))) _ctx._cstTriviaLog.push(_e, _ce, _ctx._cstRawChildren ? _ctx._cstRawChildren.length : 0, ${k})`,
3361
3392
  ` }`,
3362
3393
  ` _e = _ce`,
3363
3394
  ` _matched = true`,
@@ -4755,6 +4786,7 @@ function emitNode(def, ctx, pos) {
4755
4786
  const tlV = capturesTrivia || structural ? v(ctx, "_tl") : "_EMPTY_TL";
4756
4787
  if (!capturesTrivia) ctx.needsEmptyTl = true;
4757
4788
  const sc = v(ctx, "_sc"), sl = v(ctx, "_sl"), sr = v(ctx, "_sr"), st = v(ctx, "_st"), stl = v(ctx, "_stl");
4789
+ const smk = structural ? v(ctx, "_smk") : null;
4758
4790
  if (structural) ctx.needsHostReads = true;
4759
4791
  const hostTriviaGate = `_ctx.build !== undefined && (_ctx.build._parsemanCaptureTrivia !== undefined ? _ctx.build._parsemanCaptureTrivia(${JSON.stringify(def.type)}) : (_ctx._pmCapTL ??= _hostReads(_ctx.build, 5)))`;
4760
4792
  const allocStmt = structural ? `${i}const ${capTLv} = ${hostTriviaGate}, ${capSTv} = _ctx._pmCapST ??= (_ctx.build === undefined || _hostReads(_ctx.build, 6))${capFv ? `, ${capFv} = _ctx.build !== undefined && _hostReads(_ctx.build, 2)` : ""}
@@ -4766,15 +4798,15 @@ ${i}const ${chV} = [], ${rawV} = [], ${tlV} = ${capTLv} ? [] : _EMPTY_TL` : capt
4766
4798
  const fObj = hasFields ? v(ctx, "_fields") : "undefined";
4767
4799
  const stmts = [
4768
4800
  allocStmt,
4769
- `${i}const ${sc} = _ctx._cstChildren, ${sl} = _ctx._cstLeaves, ${sr} = _ctx._cstRawChildren, ${st} = _ctx.captureTrivia, ${stl} = _ctx._cstTriviaLog${sf ? `, ${sf} = _ctx._fields` : ""}`,
4770
- `${i}_ctx._cstChildren = ${chV}; _ctx._cstLeaves = ${chV}; _ctx._cstRawChildren = ${rawV}; _ctx.captureTrivia = true; _ctx._cstTriviaLog = ${innerTl}${sf ? `; _ctx._fields = ${fieldsOn} ? [] : undefined` : ""}`
4801
+ `${i}const ${sc} = _ctx._cstChildren, ${sl} = _ctx._cstLeaves, ${sr} = _ctx._cstRawChildren, ${st} = _ctx.captureTrivia, ${stl} = _ctx._cstTriviaLog${smk ? `, ${smk} = _ctx._triviaCaptureMask` : ""}${sf ? `, ${sf} = _ctx._fields` : ""}`,
4802
+ `${i}_ctx._cstChildren = ${chV}; _ctx._cstLeaves = ${chV}; _ctx._cstRawChildren = ${rawV}; _ctx.captureTrivia = true; _ctx._cstTriviaLog = ${innerTl}${smk ? `; _ctx._triviaCaptureMask = ${capTLv} && _ctx.build._parsemanTriviaKinds !== undefined ? _ctx.build._parsemanTriviaKinds(${JSON.stringify(def.type)}) : ${smk}` : ""}${sf ? `; _ctx._fields = ${fieldsOn} ? [] : undefined` : ""}`
4771
4803
  ];
4772
4804
  const { stmts: innerStmts, okVar, endVar } = emitFallible(def.parser, ctx, pos);
4773
4805
  stmts.push(...innerStmts);
4774
4806
  if (sf && fArr) {
4775
4807
  stmts.push(`${i}const ${fArr} = _ctx._fields`);
4776
4808
  }
4777
- stmts.push(`${i}_ctx._cstChildren = ${sc}; _ctx._cstLeaves = ${sl}; _ctx._cstRawChildren = ${sr}; _ctx.captureTrivia = ${st}; _ctx._cstTriviaLog = ${stl}${sf ? `; _ctx._fields = ${sf}` : ""}`);
4809
+ stmts.push(`${i}_ctx._cstChildren = ${sc}; _ctx._cstLeaves = ${sl}; _ctx._cstRawChildren = ${sr}; _ctx.captureTrivia = ${st}; _ctx._cstTriviaLog = ${stl}${smk ? `; _ctx._triviaCaptureMask = ${smk}` : ""}${sf ? `; _ctx._fields = ${sf}` : ""}`);
4778
4810
  stmts.push(...emitIfFail(ctx, `!${okVar}`, propagateFailBody(ctx)));
4779
4811
  let stV = "undefined";
4780
4812
  if (structural) {
@@ -5327,6 +5359,7 @@ function ruleDependencies(ruleMap) {
5327
5359
  }
5328
5360
  function compile(combinator, mapFnSources) {
5329
5361
  markUnusedValues(combinator);
5362
+ const grammarTrivia = combinator._meta.grammarTrivia;
5330
5363
  const ctx = {
5331
5364
  vars: 0,
5332
5365
  indent: 1,
@@ -5345,7 +5378,8 @@ function compile(combinator, mapFnSources) {
5345
5378
  triviaFnNames: /* @__PURE__ */ new Map(),
5346
5379
  namedFnDecls: [],
5347
5380
  capturing: hasNodeDef(combinator),
5348
- lazyUsage: analyzeLazyUsage(combinator)
5381
+ lazyUsage: analyzeLazyUsage(combinator),
5382
+ ...grammarTrivia ? { activeTrivia: grammarTrivia, triviaKindLabels: grammarTrivia._meta.triviaKindLabels } : {}
5349
5383
  };
5350
5384
  const r = emit(combinator, ctx, "_pos");
5351
5385
  const namedPrelude = ctx.namedFnDecls.length > 0 ? [...namedFnPrelude(), ""] : [];
@@ -5421,8 +5455,9 @@ function publicRuleWrapperSource(rule, fnSource) {
5421
5455
  if (labels === void 0) return fnSource;
5422
5456
  return `Object.assign(${fnSource}, { _meta: { triviaKindLabels: ${JSON.stringify(labels)} } })`;
5423
5457
  }
5424
- function compileRuleMap(ruleMap) {
5458
+ function compileRuleMap(ruleMap, opts) {
5425
5459
  for (const [, rule] of ruleMap) markUnusedValues(rule);
5460
+ const grammarTrivia = opts?.trivia;
5426
5461
  const ctx = {
5427
5462
  vars: 0,
5428
5463
  indent: 1,
@@ -5441,7 +5476,8 @@ function compileRuleMap(ruleMap) {
5441
5476
  triviaFnNames: /* @__PURE__ */ new Map(),
5442
5477
  namedFnDecls: [],
5443
5478
  capturing: ruleMap.some(([, rule]) => hasNodeDef(rule)),
5444
- lazyUsage: analyzeLazyUsageMulti(ruleMap.map(([, rule]) => rule))
5479
+ lazyUsage: analyzeLazyUsageMulti(ruleMap.map(([, rule]) => rule)),
5480
+ ...grammarTrivia ? { activeTrivia: grammarTrivia, triviaKindLabels: grammarTrivia._meta.triviaKindLabels } : {}
5445
5481
  };
5446
5482
  const seenNames = /* @__PURE__ */ new Map();
5447
5483
  const ruleNames = /* @__PURE__ */ new Map();
@@ -5453,7 +5489,13 @@ function compileRuleMap(ruleMap) {
5453
5489
  ruleNames.set(rule, n === 0 ? base : `${base}$${n}`);
5454
5490
  }
5455
5491
  ctx.ruleNames = ruleNames;
5456
- const perEntry = ruleMap.map(([key, rule]) => ({ key, rule, r: emit(rule, ctx, "_pos") }));
5492
+ const perEntry = ruleMap.map(([key, rule]) => {
5493
+ const savedTrivia = ctx.activeTrivia;
5494
+ if (rule._meta.isTrivia) ctx.activeTrivia = void 0;
5495
+ const r = emit(rule, ctx, "_pos");
5496
+ ctx.activeTrivia = savedTrivia;
5497
+ return { key, rule, r };
5498
+ });
5457
5499
  const derivedSrcs = ctx.mapFnSrcs.length === ctx.mapFns.length && ctx.mapFnSrcs.every((s) => s !== null) ? ctx.mapFnSrcs : void 0;
5458
5500
  const buildCovered = ctx.buildFns.length === 0 || ctx.buildSrcs.every((s) => s !== null);
5459
5501
  const buildSources = ctx.buildFns.length === 0 ? void 0 : ctx.buildSrcs;
@@ -6832,7 +6874,10 @@ function transformMacro(code, id, moduleAliases = /* @__PURE__ */ new Set([PARSE
6832
6874
  };
6833
6875
  const compileRulesFactory = (init, label2) => {
6834
6876
  const args = init.arguments;
6835
- const factoryArg = args[0];
6877
+ const arg0 = args[0];
6878
+ const arg1 = args[1];
6879
+ const optionsFirst = arg0?.type === "ObjectExpression";
6880
+ const factoryArg = optionsFirst ? arg1 : arg0;
6836
6881
  if (!factoryArg) {
6837
6882
  warn(init.start, `${label2}: rules() needs a factory argument`);
6838
6883
  return null;
@@ -6842,7 +6887,12 @@ function transformMacro(code, id, moduleAliases = /* @__PURE__ */ new Set([PARSE
6842
6887
  warn(init.start, `${label2}: rules(...) factory isn't statically evaluable`);
6843
6888
  return null;
6844
6889
  }
6845
- const compiled = compileRuleMap([...ruleMap]);
6890
+ const optionsArg = optionsFirst ? arg0 : arg1;
6891
+ const triviaValue = optionsArg?.type === "ObjectExpression" ? (optionsArg.properties ?? []).find(
6892
+ (p) => p.key?.name === "trivia"
6893
+ )?.value : void 0;
6894
+ const gTrivia = triviaValue ? evaluateExpr(triviaValue, scope, code, []) : void 0;
6895
+ const compiled = compileRuleMap([...ruleMap], gTrivia ? { trivia: gTrivia } : void 0);
6846
6896
  if (!compiled) {
6847
6897
  warn(init.start, `${label2}: rule map couldn't be inlined`);
6848
6898
  return null;