@bablr/agast-helpers 0.8.0 → 0.9.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.
package/lib/print.js CHANGED
@@ -10,18 +10,15 @@ import {
10
10
  LiteralTag,
11
11
  AttributeDefinition,
12
12
  BindingTag,
13
+ Document,
13
14
  } from './symbols.js';
14
- import { referenceFlags } from './tree.js';
15
+ import { referenceFlags } from './builders.js';
15
16
 
16
17
  let { isInteger, isFinite } = Number;
17
18
  let { isArray } = Array;
18
19
  let isString = (val) => typeof val === 'string';
19
20
  let isNumber = (val) => typeof val === 'number';
20
21
  let isObject = (val) => val && typeof val === 'object' && !isArray(val);
21
- let isFunction = (val) => typeof val === 'function';
22
-
23
- let when = (condition, value) =>
24
- condition ? (isFunction(value) ? value() : value) : { *[Symbol.iterator]() {} };
25
22
 
26
23
  export const printArray = (arr) => `[${arr.map((v) => printExpression(v)).join(', ')}]`;
27
24
 
@@ -122,23 +119,29 @@ export const printShiftTag = (tag) => {
122
119
  return `^^^`;
123
120
  };
124
121
 
125
- export const printReferenceTag = (tag) => {
126
- if (tag?.type !== ReferenceTag) throw new Error();
127
-
128
- let { type, name, isArray, flags } = tag.value;
122
+ export const printReference = (ref) => {
123
+ let { type, name, isArray, flags } = ref;
129
124
  let pathBraces = isArray ? `[]` : '';
130
125
 
131
- if (type && name) throw new Error();
132
- if (type && !['.', '#', '@'].includes(type)) throw new Error();
126
+ if (type && type !== '#' && name) throw new Error();
127
+ if (type && !['.', '#', '@', '_'].includes(type)) throw new Error();
133
128
 
134
- return `${type || printIdentifier(name) || ''}${pathBraces}${printReferenceFlags(flags)}:`;
129
+ return `${type || ''}${printIdentifier(name) || ''}${pathBraces}${printReferenceFlags(flags)}:`;
135
130
  };
136
131
 
137
- export const printBindingTag = (tag) => {
138
- let { languagePath } = tag.value;
132
+ export const printBinding = (binding) => {
133
+ let { languagePath } = binding;
139
134
  return `:${languagePath ? printIdentifierPath(languagePath) : ''}:`;
140
135
  };
141
136
 
137
+ export const printReferenceTag = (tag) => {
138
+ return printReference(tag.value);
139
+ };
140
+
141
+ export const printBindingTag = (tag) => {
142
+ return printBinding(tag.value);
143
+ };
144
+
142
145
  export const printNullTag = (tag) => {
143
146
  if (tag && tag.type !== NullTag) {
144
147
  throw new Error();
@@ -181,35 +184,45 @@ export const printReferenceFlags = (flags = referenceFlags) => {
181
184
 
182
185
  export const printNodeFlags = (flags) => {
183
186
  if (flags.cover && !flags.fragment) throw new Error();
187
+
184
188
  let star = flags.token ? '*' : '';
185
189
  let dollar = flags.hasGap ? '$' : '';
190
+ let fragment = flags.fragment ? '_' : '';
191
+ let multiFragment = fragment && !flags.cover ? '_' : '';
186
192
 
187
- return `${star}${dollar}`;
193
+ return `${star}${dollar}${fragment}${multiFragment}`;
188
194
  };
189
195
 
190
196
  export const printOpenNodeTag = (tag) => {
191
197
  if (tag?.type !== OpenNodeTag) throw new Error();
192
198
 
193
- let { flags, type, attributes } = tag.value;
199
+ let { flags, type, literalValue, attributes, selfClosing } = tag.value;
200
+
201
+ if (!type && !flags.fragment) throw new Error();
202
+ if (literalValue && !selfClosing) throw new Error();
194
203
 
195
204
  if (!type) {
196
- return `<${printNodeFlags(flags)}_>`;
205
+ return `<${printNodeFlags(flags)}>`;
197
206
  }
198
207
 
199
208
  let printedAttributes = printAttributes(attributes);
200
209
  let attributesFrag = printedAttributes ? ` ${printedAttributes}` : '';
210
+ let literalFrag = literalValue ? ` ${printString(literalValue)}` : '';
211
+ let selfClosingFrag = selfClosing ? ' /' : '';
201
212
 
202
- return `<${printNodeFlags(flags)}${printType(type)}${attributesFrag}>`;
213
+ return `<${printNodeFlags(flags)}${printType(
214
+ type,
215
+ )}${literalFrag}${attributesFrag}${selfClosingFrag}>`;
203
216
  };
204
217
 
205
- export const printSelfClosingNodeTag = (tag, intrinsicValue) => {
218
+ export const printSelfClosingNodeTag = (tag, literalValue) => {
206
219
  if (tag?.type !== OpenNodeTag) throw new Error();
207
220
 
208
221
  let { flags, type, attributes } = tag.value;
209
222
 
210
223
  let printedAttributes = printAttributes(attributes);
211
224
  let attributesFrag = printedAttributes ? ` ${printedAttributes}` : '';
212
- let intrinsicFrag = intrinsicValue ? ` ${printString(intrinsicValue)}` : '';
225
+ let intrinsicFrag = literalValue ? ` ${printString(literalValue)}` : '';
213
226
 
214
227
  return `<${printNodeFlags(flags)}${printType(type)}${intrinsicFrag}${attributesFrag} />`;
215
228
  };
@@ -222,6 +235,7 @@ export const printCloseNodeTag = (tag) => {
222
235
 
223
236
  export const printAttributeDefinition = (tag) => {
224
237
  if (tag?.type !== AttributeDefinition) throw new Error();
238
+ if (!tag.value.path?.length) throw new Error();
225
239
  let { path, value } = tag.value;
226
240
 
227
241
  return `{ ${printIdentifierPath(path)}: ${printExpression(value)} }`;
package/lib/shorthand.js CHANGED
@@ -31,7 +31,7 @@ export const parseReference = (str) => {
31
31
  4: index,
32
32
  5: expressionToken,
33
33
  6: hasGapToken,
34
- } = /^\s*(?:([.#@])|([a-zA-Z\u{80}-\u{10ffff}][a-zA-Z0-9_\u{80}-\u{10ffff}-]*))\s*(\[\s*(\d+\s*)?\])?\s*(\+)?(\$)?\s*$/u.exec(
34
+ } = /^\s*(?:([.#@_])|([a-zA-Z\u{80}-\u{10ffff}][a-zA-Z0-9_\u{80}-\u{10ffff}-]*))\s*(\[\s*(\d+\s*)?\])?\s*(\+)?(\$)?\s*$/u.exec(
35
35
  str,
36
36
  );
37
37
 
package/lib/stream.js CHANGED
@@ -1,153 +1,25 @@
1
1
  import { Coroutine } from '@bablr/coroutine';
2
2
  import emptyStack from '@iter-tools/imm-stack';
3
- import { printSelfClosingNodeTag, printTag } from './print.js';
4
- import { buildOpenNodeTag, buildTokenGroup } from './builders.js';
3
+ import { getStreamIterator, StreamIterable, StreamGenerator } from '@bablr/stream-iterator';
4
+ import { printTag } from './print.js';
5
+ import { buildOpenNodeTag } from './builders.js';
5
6
  import {
6
- DoctypeTag,
7
7
  OpenNodeTag,
8
8
  CloseNodeTag,
9
9
  ReferenceTag,
10
- ShiftTag,
11
10
  GapTag,
12
11
  NullTag,
13
12
  InitializerTag,
14
13
  LiteralTag,
15
- TokenGroup,
16
14
  BindingTag,
15
+ DoctypeTag,
16
+ ShiftTag,
17
17
  AttributeDefinition,
18
18
  } from './symbols.js';
19
19
 
20
- export * from './print.js';
21
-
22
- export const getStreamIterator = (obj) => {
23
- return obj[Symbol.for('@@streamIterator')]?.() || obj[Symbol.iterator]?.();
24
- };
25
-
26
- export class SyncGenerator {
27
- constructor(embeddedGenerator) {
28
- if (!embeddedGenerator.next) throw new Error();
29
-
30
- this.generator = embeddedGenerator;
31
- }
32
-
33
- next(value) {
34
- const step = this.generator.next(value);
35
-
36
- if (step instanceof Promise) {
37
- throw new Error('invalid embedded generator');
38
- }
39
-
40
- if (step.done) {
41
- return step;
42
- } else if (step.value instanceof Promise) {
43
- throw new Error('sync generators cannot resolve promises');
44
- } else {
45
- return step;
46
- }
47
- }
48
-
49
- return(value) {
50
- const step = this.generator.return(value);
51
- if (step instanceof Promise) {
52
- throw new Error('invalid embedded generator');
53
- }
54
-
55
- if (step.value instanceof Promise) {
56
- throw new Error('sync generators cannot resolve promises');
57
- }
58
- return step;
59
- }
60
-
61
- [Symbol.iterator]() {
62
- return this;
63
- }
64
- }
65
-
66
- export class AsyncGenerator {
67
- constructor(embeddedGenerator) {
68
- this.generator = embeddedGenerator;
69
- }
70
-
71
- next(value) {
72
- const step = this.generator.next(value);
73
-
74
- if (step instanceof Promise) {
75
- throw new Error('invalid embedded generator');
76
- }
77
-
78
- if (step.done) {
79
- return Promise.resolve(step);
80
- } else if (step.value instanceof Promise) {
81
- return step.value.then((value) => {
82
- return this.next(value);
83
- });
84
- } else {
85
- return Promise.resolve(step);
86
- }
87
- }
88
-
89
- return(value) {
90
- const result = this.generator.return(value);
91
- if (result instanceof Promise) {
92
- throw new Error('sync generators cannot resolve promises');
93
- }
94
- return result;
95
- }
96
-
97
- [Symbol.asyncIterator]() {
98
- return this;
99
- }
100
- }
101
-
102
- export class StreamGenerator {
103
- constructor(embeddedGenerator) {
104
- this.generator = embeddedGenerator;
105
- }
106
-
107
- next(value) {
108
- const step = this.generator.next(value);
109
-
110
- if (step.done) {
111
- return step;
112
- } else if (step.value instanceof Promise) {
113
- return step.value.then((value) => {
114
- return this.next(value);
115
- });
116
- } else {
117
- return step;
118
- }
119
- }
120
-
121
- return(value) {
122
- return this.generator.return(value);
123
- }
124
-
125
- [Symbol.iterator]() {
126
- return this;
127
- }
128
-
129
- [Symbol.for('@@streamIterator')]() {
130
- return this;
131
- }
132
- }
133
-
134
- export class StreamIterable {
135
- constructor(embeddedStreamIterable) {
136
- this.iterable = embeddedStreamIterable;
137
- }
138
-
139
- [Symbol.iterator]() {
140
- return new SyncGenerator(this.iterable);
141
- }
142
-
143
- [Symbol.asyncIterator]() {
144
- return new AsyncGenerator(this.iterable);
145
- }
20
+ export { getStreamIterator, StreamIterable, StreamGenerator };
146
21
 
147
- [Symbol.for('@@streamIterator')]() {
148
- return new StreamGenerator(this.iterable);
149
- }
150
- }
22
+ export * from './print.js';
151
23
 
152
24
  export const maybeWait = (maybePromise, callback) => {
153
25
  if (maybePromise instanceof Promise) {
@@ -181,6 +53,8 @@ function* __isEmpty(tags) {
181
53
  case OpenNodeTag:
182
54
  ++depth;
183
55
 
56
+ if (tag.value.literalValue) return false;
57
+
184
58
  if (depth === 0 && ref.value.type === '@') {
185
59
  return false;
186
60
  }
@@ -224,9 +98,9 @@ export const asyncStringFromStream = async (stream) => {
224
98
 
225
99
  if (co.done) break;
226
100
 
227
- const tag = co.value;
101
+ const chr = co.value;
228
102
 
229
- str += printTag(tag);
103
+ str += chr;
230
104
  }
231
105
 
232
106
  return str;
@@ -277,12 +151,7 @@ function* __generateCSTML(tags, options) {
277
151
  continue;
278
152
  }
279
153
 
280
- if (tag.type === TokenGroup) {
281
- const intrinsicValue = getCooked(tag.value);
282
- yield* printSelfClosingNodeTag(tag.value[0], intrinsicValue);
283
- } else {
284
- yield* printTag(tag);
285
- }
154
+ yield* printTag(tag);
286
155
 
287
156
  prevTag = tag;
288
157
  }
@@ -353,8 +222,14 @@ function* __prettyGroupTags(tags) {
353
222
 
354
223
  if (tag.type === CloseNodeTag) {
355
224
  if (!state.broken && (isToken(state.open) || state.holding.length === 1)) {
356
- state.holding.push(tag);
357
- yield buildTokenGroup(state.holding);
225
+ let { flags, type, attributes } = state.holding[0].value;
226
+
227
+ let literal = state.holding
228
+ .slice(1)
229
+ .map((lit) => lit.value)
230
+ .join('');
231
+
232
+ yield buildOpenNodeTag(flags, type, attributes, literal, true);
358
233
  } else {
359
234
  if (state.holding.length) {
360
235
  yield* state.holding;
@@ -367,9 +242,13 @@ function* __prettyGroupTags(tags) {
367
242
  }
368
243
 
369
244
  if (tag.type === OpenNodeTag) {
370
- states = states.push({ holding: [tag], broken: false, open: tag });
245
+ if (tag.value.literalValue) {
246
+ yield tag;
247
+ } else {
248
+ states = states.push({ holding: [tag], broken: false, open: tag });
371
249
 
372
- state = states.value;
250
+ state = states.value;
251
+ }
373
252
  }
374
253
  }
375
254
  }
@@ -415,7 +294,7 @@ function* __generatePrettyCSTML(tags, options) {
415
294
  tag.type === GapTag ||
416
295
  tag.type === BindingTag ||
417
296
  tag.type === InitializerTag ||
418
- tag.type === TokenGroup);
297
+ (tag.type === OpenNodeTag && tag.value.selfClosing));
419
298
 
420
299
  if (!first && !inline) {
421
300
  yield* '\n';
@@ -428,23 +307,12 @@ function* __generatePrettyCSTML(tags, options) {
428
307
  }
429
308
 
430
309
  if (!inline) {
431
- yield* indent.repeat(indentLevel);
310
+ yield* indent.repeat(Math.max(0, indentLevel));
432
311
  } else {
433
312
  yield* ' ';
434
313
  }
435
314
 
436
- if (tag.type === TokenGroup) {
437
- ref = null;
438
- const intrinsicValue = tag.value[0].value.flags.token ? getCooked(tag.value) : null;
439
- let openTag = tag.value[0];
440
- let { flags, type, attributes } = openTag.value;
441
- yield* printSelfClosingNodeTag(buildOpenNodeTag(flags, type, attributes), intrinsicValue);
442
- } else if (tag.type === OpenNodeTag) {
443
- let { flags, type, attributes } = tag.value;
444
- yield* printTag(buildOpenNodeTag(flags, type, attributes));
445
- } else {
446
- yield* printTag(tag);
447
- }
315
+ yield* printTag(tag);
448
316
 
449
317
  if (tag.type === ReferenceTag) {
450
318
  inline = true;
@@ -452,7 +320,7 @@ function* __generatePrettyCSTML(tags, options) {
452
320
  }
453
321
 
454
322
  if (tag.type === OpenNodeTag) {
455
- indentLevel++;
323
+ indentLevel += tag.value.selfClosing ? 0 : 1;
456
324
  }
457
325
 
458
326
  first = false;
@@ -494,9 +362,9 @@ export const getCooked = (tags) => {
494
362
  }
495
363
 
496
364
  case OpenNodeTag: {
497
- const { flags, attributes } = tag.value;
365
+ const { flags, attributes, literalValue, selfClosing } = tag.value;
498
366
 
499
- depth++;
367
+ depth += selfClosing ? 0 : 1;
500
368
 
501
369
  if (first) {
502
370
  if (flags.token) {
@@ -516,6 +384,8 @@ export const getCooked = (tags) => {
516
384
  if (!cookedValue) throw new Error('cannot cook string: it contains uncooked escapes');
517
385
 
518
386
  cooked += cookedValue;
387
+ } else if (literalValue) {
388
+ cooked += literalValue;
519
389
  }
520
390
 
521
391
  break;
@@ -553,7 +423,9 @@ export const printSource = (tags) => {
553
423
  if (!tags) return printed;
554
424
 
555
425
  for (const tag of tags) {
556
- if (tag.type === LiteralTag) {
426
+ if (tag.type === OpenNodeTag && tag.value.literalValue) {
427
+ printed += tag.value.literalValue;
428
+ } else if (tag.type === LiteralTag) {
557
429
  printed += tag.value;
558
430
  } else if (tag.type === GapTag) {
559
431
  throw new Error('use generateSourceTextFor');
package/lib/symbols.js CHANGED
@@ -10,6 +10,8 @@ export const InitializerTag = Symbol.for('InitializerTag');
10
10
  export const AttributeDefinition = Symbol.for('AttributeDefinition');
11
11
  export const LiteralTag = Symbol.for('LiteralTag');
12
12
 
13
- export const TokenGroup = Symbol.for('TokenGroup');
13
+ export const Document = Symbol.for('Document');
14
+ export const Node = Symbol.for('Node');
14
15
 
15
16
  export const Property = Symbol.for('Property');
17
+ export const PropertyWrapper = Symbol.for('PropertyWrapper');
package/lib/tags.js ADDED
@@ -0,0 +1,236 @@
1
+ import { buildModule, defaultNodeSize } from '@bablr/btree/enhanceable';
2
+ import { CloseNodeTag, LiteralTag, OpenNodeTag, PropertyWrapper, ReferenceTag } from './symbols.js';
3
+ import { isObject } from './object.js';
4
+
5
+ const { isArray } = Array;
6
+ const { freeze } = Object;
7
+
8
+ export { defaultNodeSize };
9
+
10
+ const __getAtName = (name, sortedArray, startIdx = 0, endIdx = sortedArray.length - 1) => {
11
+ if (!sortedArray.length || endIdx < startIdx) return null;
12
+
13
+ let idx = startIdx + Math.floor((endIdx - startIdx) / 2 + 0.1);
14
+ let entry = sortedArray[idx];
15
+ let { 0: key, 1: value } = entry;
16
+
17
+ let direction = compareNames(name, key);
18
+
19
+ if (direction === 0) {
20
+ return value;
21
+ } else {
22
+ if (startIdx === endIdx) return null;
23
+
24
+ if (direction > 0) {
25
+ return __getAtName(name, sortedArray, idx + 1, endIdx);
26
+ } else {
27
+ return __getAtName(name, sortedArray, startIdx, idx - 1);
28
+ }
29
+ }
30
+ };
31
+
32
+ export const getAtName = (name, sortedArray, startIdx = 0, endIdx = sortedArray.length - 1) => {
33
+ return __getAtName(name, sortedArray, startIdx, endIdx);
34
+ };
35
+
36
+ export const compareNames = (a, b) => (a > b ? 1 : b > a ? -1 : 0);
37
+
38
+ const module_ = buildModule(
39
+ defaultNodeSize,
40
+ (acc, val) => {
41
+ const { references, specialTypes } = acc;
42
+ if (isArray(val)) {
43
+ acc.lineBreaks += getSums(val).lineBreaks;
44
+
45
+ for (const { 0: key, 1: value } of getSums(val).references) {
46
+ references.set(key, (references.get(key) ?? 0) + value);
47
+ }
48
+
49
+ for (const { 0: key, 1: value } of getSums(val).specialTypes) {
50
+ specialTypes.set(key, (specialTypes.get(key) ?? 0) + value);
51
+ }
52
+ } else if (val) {
53
+ if (val.type === LiteralTag) {
54
+ let text = val.value;
55
+ let idx = 0;
56
+ while ((idx = text.indexOf('\n', idx + 1)) >= 0) {
57
+ acc.lineBreaks++;
58
+ }
59
+ } else if (val.type === PropertyWrapper) {
60
+ let { tags } = val.value;
61
+ let refOrShiftTag = tags[0];
62
+
63
+ if (refOrShiftTag.type === ReferenceTag) {
64
+ const { type, name } = refOrShiftTag.value;
65
+ if (name) {
66
+ references.set(name, (references.get(name) ?? 0) + 1);
67
+ } else {
68
+ specialTypes.set(type, (specialTypes.get(type) ?? 0) + 1);
69
+ }
70
+ }
71
+ }
72
+ }
73
+ return acc;
74
+ },
75
+ () => ({
76
+ lineBreaks: 0,
77
+ references: new Map(),
78
+ specialTypes: new Map(),
79
+ }),
80
+ (mapStats) => {
81
+ let { lineBreaks } = mapStats;
82
+ let stats = {
83
+ lineBreaks,
84
+ references: [...mapStats.references].sort((a, b) => compareNames(a[0], b[0])),
85
+ specialTypes: [...mapStats.specialTypes].sort((a, b) => compareNames(a[0], b[0])),
86
+ };
87
+ freeze(stats);
88
+ freeze(stats.references);
89
+ freeze(stats.specialTypes);
90
+ return stats;
91
+ },
92
+ );
93
+
94
+ const {
95
+ from,
96
+ fromValues,
97
+ addAt,
98
+ isValidNode,
99
+ assertValidNode,
100
+ getValues,
101
+ getSums,
102
+ setValues,
103
+ traverse,
104
+ getSize,
105
+ findPath,
106
+ } = module_;
107
+
108
+ const getAt = (idx, tags, wrapperIndex) => {
109
+ let result = module_.getAt(idx, tags);
110
+ return wrapperIndex == null || result?.type !== PropertyWrapper
111
+ ? result
112
+ : result.value.tags[wrapperIndex];
113
+ };
114
+
115
+ const push = (tags, tag) => {
116
+ let firstTag = getAt(0, tags);
117
+ if (isArray(tag)) {
118
+ if (!firstTag || firstTag.type !== OpenNodeTag) {
119
+ return module_.concat(tags, tag);
120
+ }
121
+ let children = getValues(tags)[1] ?? module_.fromValues([]);
122
+
123
+ let { 0: open } = getValues(tags);
124
+
125
+ children = module_.concat(children, tag);
126
+
127
+ return module_.fromValues([open, children]);
128
+ } else {
129
+ if (tag.type === OpenNodeTag) {
130
+ if (getSize(tags) !== 0) throw new Error();
131
+ return module_.push(tags, tag);
132
+ } else {
133
+ if (!firstTag || firstTag.type !== OpenNodeTag) {
134
+ return module_.push(tags, tag);
135
+ }
136
+
137
+ let children = getValues(tags)[1] ?? [];
138
+
139
+ // sometimes this is the top level
140
+ if (firstTag) {
141
+ if (tag.type === CloseNodeTag) {
142
+ let { 0: open, 1: children = module_.fromValues([]) } = getValues(tags);
143
+
144
+ return module_.fromValues([open, children, tag]);
145
+ } else {
146
+ let { 0: open } = getValues(tags);
147
+
148
+ children = module_.push(children, tag);
149
+
150
+ return module_.fromValues([open, children]);
151
+ }
152
+ } else {
153
+ return module_.push(tags, tag);
154
+ }
155
+ }
156
+ }
157
+ };
158
+
159
+ const replaceAt = (idx, tree, value) => {
160
+ let idx_ = idx < 0 ? getSize(tree) + idx : idx;
161
+
162
+ if (value.type !== getAt(idx_, tree).type) throw new Error();
163
+ let firstTag = getAt(0, tree);
164
+
165
+ if (firstTag && firstTag.type === OpenNodeTag) {
166
+ let newTags = [...getValues(tree)];
167
+ if (idx_ === 0) {
168
+ newTags[0] = value;
169
+ } else if (isObject(value) && value.type === CloseNodeTag) {
170
+ if (idx_ !== getSize(tree) - 1) throw new Error();
171
+ newTags[2] = value;
172
+ } else {
173
+ let children = getValues(tree)[1];
174
+
175
+ children = module_.replaceAt(idx_ - 1, children, value);
176
+
177
+ newTags[1] = children;
178
+ }
179
+ return module_.fromValues(newTags);
180
+ } else {
181
+ return module_.replaceAt(idx_, tree, value);
182
+ }
183
+ };
184
+
185
+ const removeAt = (idx, tree) => {
186
+ let idx_ = idx < 0 ? getSize(tree) + idx : idx;
187
+
188
+ let firstTag = getAt(0, tree);
189
+
190
+ if (firstTag && firstTag.type === OpenNodeTag) {
191
+ let newTags = [...getValues(tree)];
192
+ if (idx_ === 0) {
193
+ newTags.splice(0, 1);
194
+ } else if (idx_ === getSize(tree - 1)) {
195
+ newTags.splice(2, 1);
196
+ } else {
197
+ let children = getValues(tree)[1];
198
+
199
+ children = module_.removeAt(idx_ - 1, children);
200
+
201
+ newTags[1] = children;
202
+ }
203
+ return module_.fromValues(newTags);
204
+ } else {
205
+ return module_.removeAt(idx_, tree);
206
+ }
207
+ };
208
+
209
+ function* traverseInner(tree) {
210
+ for (let tag of module_.traverse(tree)) {
211
+ if (tag.type === PropertyWrapper) {
212
+ yield* tag.value.tags;
213
+ } else {
214
+ yield tag;
215
+ }
216
+ }
217
+ }
218
+
219
+ export {
220
+ from,
221
+ fromValues,
222
+ push,
223
+ addAt,
224
+ isValidNode,
225
+ assertValidNode,
226
+ getSize,
227
+ getValues,
228
+ getSums,
229
+ setValues,
230
+ traverse,
231
+ traverseInner,
232
+ findPath,
233
+ getAt,
234
+ replaceAt,
235
+ removeAt,
236
+ };