poe-code 3.0.181 → 3.0.183

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.
Files changed (187) hide show
  1. package/dist/bin/poe-agent.js +1 -1
  2. package/dist/cli/commands/config.js +3 -4
  3. package/dist/cli/commands/config.js.map +1 -1
  4. package/dist/cli/commands/configure.js +12 -3
  5. package/dist/cli/commands/configure.js.map +1 -1
  6. package/dist/cli/commands/dashboard-loop-shared.d.ts +7 -9
  7. package/dist/cli/commands/dashboard-loop-shared.js +16 -9
  8. package/dist/cli/commands/dashboard-loop-shared.js.map +1 -1
  9. package/dist/cli/commands/experiment.js +41 -32
  10. package/dist/cli/commands/experiment.js.map +1 -1
  11. package/dist/cli/commands/mcp.js +7 -2
  12. package/dist/cli/commands/mcp.js.map +1 -1
  13. package/dist/cli/commands/memory.d.ts +3 -0
  14. package/dist/cli/commands/memory.js +181 -0
  15. package/dist/cli/commands/memory.js.map +1 -0
  16. package/dist/cli/commands/pipeline-init.d.ts +17 -0
  17. package/dist/cli/commands/pipeline-init.js +166 -0
  18. package/dist/cli/commands/pipeline-init.js.map +1 -0
  19. package/dist/cli/commands/pipeline.js +187 -45
  20. package/dist/cli/commands/pipeline.js.map +1 -1
  21. package/dist/cli/commands/plan.d.ts +1 -0
  22. package/dist/cli/commands/plan.js +196 -39
  23. package/dist/cli/commands/plan.js.map +1 -1
  24. package/dist/cli/commands/ralph.js +24 -24
  25. package/dist/cli/commands/ralph.js.map +1 -1
  26. package/dist/cli/commands/shared.d.ts +3 -0
  27. package/dist/cli/commands/shared.js +27 -1
  28. package/dist/cli/commands/shared.js.map +1 -1
  29. package/dist/cli/commands/skill.js +21 -10
  30. package/dist/cli/commands/skill.js.map +1 -1
  31. package/dist/cli/commands/spawn-poe-agent.d.ts +2 -0
  32. package/dist/cli/commands/spawn-poe-agent.js +47 -0
  33. package/dist/cli/commands/spawn-poe-agent.js.map +1 -0
  34. package/dist/cli/commands/spawn.js +21 -1
  35. package/dist/cli/commands/spawn.js.map +1 -1
  36. package/dist/cli/commands/utils-symlink-agents.d.ts +6 -0
  37. package/dist/cli/commands/utils-symlink-agents.js +78 -0
  38. package/dist/cli/commands/utils-symlink-agents.js.map +1 -0
  39. package/dist/cli/commands/utils-symlink-ops.d.ts +29 -0
  40. package/dist/cli/commands/utils-symlink-ops.js +76 -0
  41. package/dist/cli/commands/utils-symlink-ops.js.map +1 -0
  42. package/dist/cli/commands/utils-symlink-skills.d.ts +15 -0
  43. package/dist/cli/commands/utils-symlink-skills.js +136 -0
  44. package/dist/cli/commands/utils-symlink-skills.js.map +1 -0
  45. package/dist/cli/commands/utils-symlink.d.ts +3 -0
  46. package/dist/cli/commands/utils-symlink.js +40 -0
  47. package/dist/cli/commands/utils-symlink.js.map +1 -0
  48. package/dist/cli/commands/utils.js +2 -0
  49. package/dist/cli/commands/utils.js.map +1 -1
  50. package/dist/cli/constants.d.ts +2 -2
  51. package/dist/cli/constants.js +1 -1
  52. package/dist/cli/constants.js.map +1 -1
  53. package/dist/cli/poe-agent-main.d.ts +10 -1
  54. package/dist/cli/poe-agent-main.js +89 -47
  55. package/dist/cli/poe-agent-main.js.map +1 -1
  56. package/dist/cli/program.js +13 -1
  57. package/dist/cli/program.js.map +1 -1
  58. package/dist/corpus/001-archaeoastronomy.md +479 -0
  59. package/dist/corpus/002-magnetohydrodynamics.md +475 -0
  60. package/dist/corpus/003-biosemiotics.md +483 -0
  61. package/dist/corpus/004-cryopedology.md +483 -0
  62. package/dist/corpus/005-geomicrobiology.md +479 -0
  63. package/dist/corpus/006-aeronomy.md +487 -0
  64. package/dist/corpus/007-paleoclimatology.md +479 -0
  65. package/dist/corpus/008-hydrogeophysics.md +479 -0
  66. package/dist/corpus/009-magnetostratigraphy.md +475 -0
  67. package/dist/corpus/010-isotope-hydrology.md +481 -0
  68. package/dist/corpus/011-speleothem-geochemistry.md +474 -0
  69. package/dist/corpus/012-astrobiogeochemistry.md +475 -0
  70. package/dist/corpus/013-neuroethology.md +483 -0
  71. package/dist/corpus/014-chronophysiology.md +483 -0
  72. package/dist/corpus/015-limnogeochemistry.md +475 -0
  73. package/dist/corpus/016-palynology.md +483 -0
  74. package/dist/corpus/017-volcanotectonics.md +473 -0
  75. package/dist/corpus/018-seismotectonics.md +473 -0
  76. package/dist/corpus/019-biogeomorphology.md +475 -0
  77. package/dist/corpus/020-geobiophysics.md +479 -0
  78. package/dist/corpus/021-phytolith-analysis.md +481 -0
  79. package/dist/corpus/022-archaeometallurgy.md +479 -0
  80. package/dist/corpus/023-paleomagnetism.md +479 -0
  81. package/dist/corpus/024-biocalorimetry.md +475 -0
  82. package/dist/corpus/025-atmospheric-chemiluminescence.md +473 -0
  83. package/dist/corpus/026-cryoseismology.md +479 -0
  84. package/dist/corpus/027-extremophile-radiobiology.md +475 -0
  85. package/dist/corpus/028-heliophysics.md +479 -0
  86. package/dist/corpus/029-astroparticle-geophysics.md +474 -0
  87. package/dist/corpus/030-glaciohydrology.md +479 -0
  88. package/dist/corpus/031-permafrost-microbiology.md +477 -0
  89. package/dist/corpus/032-ecoacoustics.md +479 -0
  90. package/dist/corpus/033-dendroclimatology.md +473 -0
  91. package/dist/corpus/034-ionospheric-tomography.md +477 -0
  92. package/dist/corpus/035-marine-geodesy.md +481 -0
  93. package/dist/corpus/036-sedimentary-ancient-dna.md +481 -0
  94. package/dist/corpus/037-myrmecochory-dynamics.md +474 -0
  95. package/dist/corpus/038-chemosensory-ecology.md +477 -0
  96. package/dist/corpus/039-spintronics-materials.md +479 -0
  97. package/dist/corpus/040-nanotoxicology.md +483 -0
  98. package/dist/corpus/041-cosmochemistry.md +483 -0
  99. package/dist/corpus/042-quaternary-geochronology.md +471 -0
  100. package/dist/corpus/043-biophotonics.md +479 -0
  101. package/dist/corpus/044-evolutionary-morphometrics.md +481 -0
  102. package/dist/corpus/045-cryovolcanology.md +475 -0
  103. package/dist/corpus/046-exoplanet-atmospheric-dynamics.md +479 -0
  104. package/dist/corpus/047-microbial-electrosynthesis.md +477 -0
  105. package/dist/corpus/048-paleoseismology.md +479 -0
  106. package/dist/corpus/049-actinide-geochemistry.md +477 -0
  107. package/dist/corpus/050-quantum-biology.md +489 -0
  108. package/dist/index.d.ts +3 -2
  109. package/dist/index.js +31666 -23440
  110. package/dist/index.js.map +4 -4
  111. package/dist/plan/document-schema.d.ts +21 -0
  112. package/dist/plan/document-schema.js +16 -0
  113. package/dist/plan/document-schema.js.map +1 -0
  114. package/dist/providers/claude-code.js +31 -13
  115. package/dist/providers/claude-code.js.map +4 -4
  116. package/dist/providers/codex.js +31 -13
  117. package/dist/providers/codex.js.map +4 -4
  118. package/dist/providers/goose.js +32 -14
  119. package/dist/providers/goose.js.map +4 -4
  120. package/dist/providers/kimi.js +31 -13
  121. package/dist/providers/kimi.js.map +4 -4
  122. package/dist/providers/opencode.js +32 -14
  123. package/dist/providers/opencode.js.map +4 -4
  124. package/dist/providers/poe-agent.d.ts +5 -0
  125. package/dist/providers/poe-agent.js +21214 -4016
  126. package/dist/providers/poe-agent.js.map +4 -4
  127. package/dist/sdk/container.js +4 -0
  128. package/dist/sdk/container.js.map +1 -1
  129. package/dist/sdk/pipeline.d.ts +27 -0
  130. package/dist/sdk/pipeline.js +91 -1
  131. package/dist/sdk/pipeline.js.map +1 -1
  132. package/dist/sdk/spawn.js +8 -2
  133. package/dist/sdk/spawn.js.map +1 -1
  134. package/dist/sdk/types.d.ts +5 -1
  135. package/dist/services/config.d.ts +47 -33
  136. package/dist/services/config.js +22 -20
  137. package/dist/services/config.js.map +1 -1
  138. package/dist/templates/pipeline/SKILL_plan.md +22 -8
  139. package/dist/templates/pipeline/steps.yaml.mustache +1 -1
  140. package/dist/templates/skill/poe-generate.md +47 -0
  141. package/dist/templates/skill/terminal-pilot.md +45 -0
  142. package/dist/utils/dry-run.d.ts +8 -0
  143. package/dist/utils/dry-run.js +16 -0
  144. package/dist/utils/dry-run.js.map +1 -1
  145. package/dist/utils/file-system.d.ts +4 -0
  146. package/package.json +19 -9
  147. package/packages/cmdkit/dist/cli.js +42 -22
  148. package/packages/cmdkit/dist/cli.js.map +3 -3
  149. package/packages/cmdkit/dist/index.js +52 -9
  150. package/packages/cmdkit/dist/index.js.map +2 -2
  151. package/packages/cmdkit/dist/mcp.d.ts +15 -0
  152. package/packages/cmdkit/dist/mcp.js +121 -20
  153. package/packages/cmdkit/dist/mcp.js.map +3 -3
  154. package/packages/cmdkit/dist/number-schema.d.ts +3 -0
  155. package/packages/cmdkit/dist/number-schema.js +8 -0
  156. package/packages/cmdkit/dist/schema-scope.d.ts +4 -0
  157. package/packages/cmdkit/dist/schema-scope.js +34 -0
  158. package/packages/cmdkit/dist/sdk.js +58 -3
  159. package/packages/cmdkit/dist/sdk.js.map +3 -3
  160. package/packages/cmdkit-schema/dist/index.compile-check.js +1 -0
  161. package/packages/cmdkit-schema/dist/index.d.ts +59 -16
  162. package/packages/cmdkit-schema/dist/index.js +53 -8
  163. package/packages/design-system/dist/dashboard/components/footer.js +2 -3
  164. package/packages/design-system/dist/dashboard/components/output-pane.d.ts +1 -10
  165. package/packages/design-system/dist/dashboard/components/output-pane.js +5 -74
  166. package/packages/design-system/dist/dashboard/dashboard.js +6 -26
  167. package/packages/design-system/dist/dashboard/index.d.ts +1 -0
  168. package/packages/design-system/dist/dashboard/index.js +1 -0
  169. package/packages/design-system/dist/dashboard/keymap.js +4 -19
  170. package/packages/design-system/dist/dashboard/should-use-dashboard.d.ts +10 -0
  171. package/packages/design-system/dist/dashboard/should-use-dashboard.js +7 -0
  172. package/packages/design-system/dist/dashboard/snapshot.js +1 -5
  173. package/packages/design-system/dist/dashboard/store.d.ts +1 -2
  174. package/packages/design-system/dist/dashboard/store.js +6 -62
  175. package/packages/design-system/dist/dashboard/terminal.d.ts +2 -0
  176. package/packages/design-system/dist/dashboard/terminal.js +18 -0
  177. package/packages/design-system/dist/dashboard/types.d.ts +1 -11
  178. package/packages/design-system/dist/index.d.ts +1 -1
  179. package/packages/design-system/dist/index.js +1 -1
  180. package/packages/design-system/dist/terminal-markdown/ast.d.ts +10 -2
  181. package/packages/design-system/dist/terminal-markdown/parser/block.d.ts +2 -1
  182. package/packages/design-system/dist/terminal-markdown/parser/block.js +400 -110
  183. package/packages/design-system/dist/terminal-markdown/parser/frontmatter.d.ts +2 -0
  184. package/packages/design-system/dist/terminal-markdown/parser/frontmatter.js +28 -11
  185. package/packages/design-system/dist/terminal-markdown/parser/inline.d.ts +4 -0
  186. package/packages/design-system/dist/terminal-markdown/parser/inline.js +134 -55
  187. package/packages/design-system/dist/terminal-markdown/parser.js +36 -7
@@ -65,18 +65,25 @@ const BLOCK_HTML_TAGS = new Set([
65
65
  "ul"
66
66
  ]);
67
67
  const VOID_BLOCK_HTML_TAGS = new Set(["base", "basefont", "col", "hr", "link", "param", "track"]);
68
+ const SOURCE_OFFSETS = Symbol("sourceOffsets");
68
69
  export function parseBlocks(input) {
69
70
  return parseBlockDocument(input).children;
70
71
  }
71
72
  export function parseBlockDocument(input) {
72
- const { frontmatter, body } = extractFrontmatter(input);
73
- const children = applyInlineParsing(parseBlocksWithOptions(body, { preferListToThematicBreak: false }));
74
- return frontmatter === undefined ? { children } : { frontmatter, children };
73
+ const { frontmatter, body, range } = extractFrontmatter(input);
74
+ const children = applyInlineParsing(parseBlocksWithOptions(body, {
75
+ preferListToThematicBreak: false,
76
+ offsets: createOffsetMap(body, range?.end ?? 0)
77
+ }));
78
+ return frontmatter === undefined
79
+ ? { children }
80
+ : { frontmatter, frontmatterRange: range, children };
75
81
  }
76
82
  function parseBlocksWithOptions(input, options) {
77
83
  const state = {
78
- input: stripBom(input),
84
+ input,
79
85
  position: 0,
86
+ offsets: options.offsets,
80
87
  preferListToThematicBreak: options.preferListToThematicBreak
81
88
  };
82
89
  const blocks = [];
@@ -125,28 +132,35 @@ function collectFootnoteLabelsFromNode(node, labels) {
125
132
  }
126
133
  function applyInlineParsingToNode(node, footnoteLabels) {
127
134
  if (node.type === "paragraph" || node.type === "heading" || node.type === "tableCell") {
128
- return {
129
- ...node,
130
- children: applyInlineParsingToTextChildren(node.children, footnoteLabels)
131
- };
135
+ return replaceNodeChildren(node, applyInlineParsingToTextChildren(node.children, footnoteLabels));
132
136
  }
133
137
  if (hasBlockChildren(node)) {
134
- return {
135
- ...node,
136
- children: node.children.map((child) => applyInlineParsingToNode(child, footnoteLabels))
137
- };
138
+ return replaceNodeChildren(node, node.children.map((child) => applyInlineParsingToNode(child, footnoteLabels)));
138
139
  }
139
140
  return node;
140
141
  }
141
142
  function applyInlineParsingToTextChildren(children, footnoteLabels) {
142
143
  let rawText = "";
144
+ let offsets;
143
145
  for (const child of children) {
144
146
  if (child.type !== "text") {
145
147
  return children;
146
148
  }
147
149
  rawText += child.value;
150
+ const childOffsets = getTextNodeSourceOffsets(child);
151
+ if (childOffsets === undefined) {
152
+ return children;
153
+ }
154
+ if (offsets === undefined) {
155
+ offsets = [...childOffsets];
156
+ continue;
157
+ }
158
+ offsets.push(...childOffsets.slice(1));
148
159
  }
149
- return parseInline(rawText, { footnoteLabels });
160
+ return parseInline(rawText, {
161
+ footnoteLabels,
162
+ ...(offsets === undefined ? {} : { offsets })
163
+ });
150
164
  }
151
165
  function hasBlockChildren(node) {
152
166
  return (node.type === "root" ||
@@ -172,6 +186,7 @@ function createBlockRules(preferListToThematicBreak) {
172
186
  ];
173
187
  }
174
188
  function parseFencedCodeBlock(state) {
189
+ const rangeStart = state.position;
175
190
  const openingLine = readLine(state.input, state.position);
176
191
  const fence = parseOpeningFence(openingLine.text);
177
192
  if (fence === null) {
@@ -183,35 +198,39 @@ function parseFencedCodeBlock(state) {
183
198
  const line = readLine(state.input, state.position);
184
199
  if (isClosingFence(line.text, fence)) {
185
200
  state.position = line.nextPosition;
186
- return createCodeNode(fence, contentLines);
201
+ return withRange(createCodeNode(fence, contentLines), createNodeRange(state, rangeStart));
187
202
  }
188
203
  contentLines.push(line.text);
189
204
  state.position = line.nextPosition;
190
205
  }
191
- return createCodeNode(fence, contentLines);
206
+ return withRange(createCodeNode(fence, contentLines), createNodeRange(state, rangeStart));
192
207
  }
193
208
  function parseAtxHeading(state) {
209
+ const rangeStart = state.position;
194
210
  const line = readLine(state.input, state.position);
195
211
  const heading = parseAtxHeadingLine(line.text);
196
212
  if (heading === null) {
197
213
  return null;
198
214
  }
199
215
  state.position = line.nextPosition;
200
- return {
216
+ const content = createMappedTextFromLineSlice(state, line, heading.contentStart, heading.contentEnd);
217
+ return withRange({
201
218
  type: "heading",
202
219
  depth: heading.depth,
203
- children: createTextChildren(heading.text)
204
- };
220
+ children: createTextChildren(heading.text, { start: content.offsets[0] ?? 0, end: content.offsets[content.offsets.length - 1] ?? 0 }, content.offsets)
221
+ }, createNodeRange(state, rangeStart));
205
222
  }
206
223
  function parseThematicBreak(state) {
224
+ const rangeStart = state.position;
207
225
  const line = readLine(state.input, state.position);
208
226
  if (!isThematicBreakLine(line.text)) {
209
227
  return null;
210
228
  }
211
229
  state.position = line.nextPosition;
212
- return { type: "thematicBreak" };
230
+ return withRange({ type: "thematicBreak" }, createNodeRange(state, rangeStart));
213
231
  }
214
232
  function parseSetextHeading(state) {
233
+ const rangeStart = state.position;
215
234
  const contentLine = readLine(state.input, state.position);
216
235
  if (isBlankLine(contentLine.text)) {
217
236
  return null;
@@ -225,64 +244,96 @@ function parseSetextHeading(state) {
225
244
  return null;
226
245
  }
227
246
  state.position = underlineLine.nextPosition;
228
- return {
247
+ const content = trimAsciiWhitespaceRange(contentLine.text);
248
+ const mappedContent = createMappedTextFromLineSlice(state, contentLine, content.start, content.end);
249
+ return withRange({
229
250
  type: "heading",
230
251
  depth,
231
- children: createTextChildren(trimAsciiWhitespace(contentLine.text))
232
- };
252
+ children: createTextChildren(content.value, {
253
+ start: mappedContent.offsets[0] ?? 0,
254
+ end: mappedContent.offsets[mappedContent.offsets.length - 1] ?? 0
255
+ }, mappedContent.offsets)
256
+ }, createNodeRange(state, rangeStart));
233
257
  }
234
258
  function parseBlockquote(state) {
259
+ const rangeStart = state.position;
235
260
  const firstLine = readLine(state.input, state.position);
236
- if (stripBlockquoteMarker(firstLine.text) === null) {
261
+ if (parseBlockquoteLine(firstLine.text) === null) {
237
262
  return null;
238
263
  }
239
- const contentLines = [];
264
+ const contentParts = [];
265
+ let previousContentLine;
240
266
  while (state.position < state.input.length) {
241
267
  const line = readLine(state.input, state.position);
242
- const content = stripBlockquoteMarker(line.text);
268
+ const content = parseBlockquoteLine(line.text);
243
269
  if (content === null) {
244
270
  break;
245
271
  }
246
- contentLines.push(content);
272
+ if (previousContentLine !== undefined) {
273
+ const lineBreak = createMappedLineBreak(state, previousContentLine);
274
+ if (lineBreak !== null) {
275
+ contentParts.push(lineBreak);
276
+ }
277
+ }
278
+ contentParts.push(createMappedTextFromLineSlice(state, line, content.contentStart, line.text.length));
247
279
  state.position = line.nextPosition;
280
+ previousContentLine = line;
248
281
  }
249
- return {
282
+ const content = joinMappedTexts(contentParts);
283
+ return withRange({
250
284
  type: "blockquote",
251
- children: parseBlocksWithOptions(contentLines.join("\n"), {
252
- preferListToThematicBreak: state.preferListToThematicBreak
285
+ children: parseBlocksWithOptions(content.text, {
286
+ preferListToThematicBreak: state.preferListToThematicBreak,
287
+ offsets: content.offsets
253
288
  })
254
- };
289
+ }, createNodeRange(state, rangeStart));
255
290
  }
256
291
  function parseAlert(state) {
292
+ const rangeStart = state.position;
257
293
  const firstLine = readLine(state.input, state.position);
258
- const firstLineContent = stripBlockquoteMarker(firstLine.text);
294
+ const firstLineContent = parseBlockquoteLine(firstLine.text);
259
295
  if (firstLineContent === null) {
260
296
  return null;
261
297
  }
262
- const alertMarker = parseAlertMarker(firstLineContent);
298
+ const alertMarker = parseAlertMarker(firstLineContent.content);
263
299
  if (alertMarker === null) {
264
300
  return null;
265
301
  }
266
302
  state.position = firstLine.nextPosition;
267
- const contentLines = alertMarker.content.length === 0 ? [] : [alertMarker.content];
303
+ const contentParts = [];
304
+ let previousContentLine;
305
+ if (alertMarker.content.length > 0) {
306
+ contentParts.push(createMappedTextFromLineSlice(state, firstLine, firstLineContent.contentStart + alertMarker.contentStart, firstLine.text.length));
307
+ previousContentLine = firstLine;
308
+ }
268
309
  while (state.position < state.input.length) {
269
310
  const line = readLine(state.input, state.position);
270
- const content = stripBlockquoteMarker(line.text);
311
+ const content = parseBlockquoteLine(line.text);
271
312
  if (content === null) {
272
313
  break;
273
314
  }
274
- contentLines.push(content);
315
+ if (previousContentLine !== undefined) {
316
+ const previousLineBreak = createMappedLineBreak(state, previousContentLine);
317
+ if (previousLineBreak !== null) {
318
+ contentParts.push(previousLineBreak);
319
+ }
320
+ }
321
+ contentParts.push(createMappedTextFromLineSlice(state, line, content.contentStart, line.text.length));
275
322
  state.position = line.nextPosition;
323
+ previousContentLine = line;
276
324
  }
277
- return {
325
+ const content = joinMappedTexts(contentParts);
326
+ return withRange({
278
327
  type: "alert",
279
328
  kind: alertMarker.kind,
280
- children: parseBlocksWithOptions(contentLines.join("\n"), {
281
- preferListToThematicBreak: state.preferListToThematicBreak
329
+ children: parseBlocksWithOptions(content.text, {
330
+ preferListToThematicBreak: state.preferListToThematicBreak,
331
+ offsets: content.offsets
282
332
  })
283
- };
333
+ }, createNodeRange(state, rangeStart));
284
334
  }
285
335
  function parseList(state) {
336
+ const rangeStart = state.position;
286
337
  const firstLine = readLine(state.input, state.position);
287
338
  const firstMarker = parseListMarker(firstLine.text);
288
339
  if (firstMarker === null) {
@@ -303,29 +354,31 @@ function parseList(state) {
303
354
  }
304
355
  children.push(item);
305
356
  }
306
- return {
357
+ return withRange({
307
358
  type: "list",
308
359
  ordered,
309
360
  ...(ordered && start !== undefined ? { start } : {}),
310
361
  children
311
- };
362
+ }, createNodeRange(state, rangeStart));
312
363
  }
313
364
  function parseTable(state) {
365
+ const rangeStart = state.position;
314
366
  const table = parseTableAt(state.input, state.position, state.preferListToThematicBreak);
315
367
  if (table === null) {
316
368
  return null;
317
369
  }
318
370
  state.position = table.nextPosition;
319
- return {
371
+ return withRange({
320
372
  type: "table",
321
373
  align: table.align,
322
374
  children: [
323
- createTableRowNode(table.headerCells),
324
- ...table.rows.map((row) => createTableRowNode(row))
375
+ createTableRowNode(state, table.header.line, table.header.cells),
376
+ ...table.rows.map((row) => createTableRowNode(state, row.line, row.cells))
325
377
  ]
326
- };
378
+ }, createNodeRange(state, rangeStart));
327
379
  }
328
380
  function parseHtmlBlock(state) {
381
+ const rangeStart = state.position;
329
382
  const firstLine = readLine(state.input, state.position);
330
383
  const openingTag = parseBlockHtmlTagStart(firstLine.text);
331
384
  if (openingTag === null) {
@@ -347,9 +400,10 @@ function parseHtmlBlock(state) {
347
400
  }
348
401
  }
349
402
  }
350
- return { type: "html", value: lines.join("\n") };
403
+ return withRange({ type: "html", value: lines.join("\n") }, createNodeRange(state, rangeStart));
351
404
  }
352
405
  function parseFootnoteDefinition(state) {
406
+ const rangeStart = state.position;
353
407
  const firstLine = readLine(state.input, state.position);
354
408
  const definition = parseFootnoteDefinitionMarker(firstLine.text);
355
409
  if (definition === null) {
@@ -361,11 +415,15 @@ function parseFootnoteDefinition(state) {
361
415
  while (state.position < state.input.length) {
362
416
  const line = readLine(state.input, state.position);
363
417
  if (isBlankLine(line.text)) {
364
- pendingBlankLines.push("");
418
+ pendingBlankLines.push({
419
+ text: "",
420
+ offsets: [state.offsets[line.end] ?? 0],
421
+ lineBreakEnd: state.offsets[line.nextPosition] ?? state.offsets[state.offsets.length - 1] ?? 0
422
+ });
365
423
  state.position = line.nextPosition;
366
424
  continue;
367
425
  }
368
- const strippedLine = stripIndent(line.text, 4);
426
+ const strippedLine = stripIndentLine(state, line, 4);
369
427
  if (strippedLine === null) {
370
428
  break;
371
429
  }
@@ -373,13 +431,14 @@ function parseFootnoteDefinition(state) {
373
431
  continuationLines.push(...pendingBlankLines, strippedLine);
374
432
  pendingBlankLines.length = 0;
375
433
  }
376
- return {
434
+ return withRange({
377
435
  type: "footnoteDefinition",
378
436
  label: definition.label,
379
- children: parseListItemChildren(firstLine.text.slice(definition.contentStart), continuationLines, state.preferListToThematicBreak)
380
- };
437
+ children: parseListItemChildren(createMappedTextFromLineSlice(state, firstLine, definition.contentStart, firstLine.text.length), continuationLines, state.preferListToThematicBreak)
438
+ }, createNodeRange(state, rangeStart));
381
439
  }
382
440
  function parseParagraph(state) {
441
+ const rangeStart = state.position;
383
442
  const lines = [];
384
443
  while (state.position < state.input.length) {
385
444
  const line = readLine(state.input, state.position);
@@ -390,13 +449,17 @@ function parseParagraph(state) {
390
449
  startsBlockAt(state.input, state.position, state.preferListToThematicBreak)) {
391
450
  break;
392
451
  }
393
- lines.push(line.text);
452
+ lines.push(line);
394
453
  state.position = line.nextPosition;
395
454
  }
396
- return {
455
+ const content = createMappedTextFromLines(state, lines);
456
+ return withRange({
397
457
  type: "paragraph",
398
- children: [{ type: "text", value: lines.join("\n") }]
399
- };
458
+ children: createTextChildren(content.text, {
459
+ start: content.offsets[0] ?? 0,
460
+ end: content.offsets[content.offsets.length - 1] ?? 0
461
+ }, content.offsets)
462
+ }, createNodeRange(state, rangeStart));
400
463
  }
401
464
  function createCodeNode(fence, contentLines) {
402
465
  return {
@@ -406,18 +469,146 @@ function createCodeNode(fence, contentLines) {
406
469
  value: contentLines.join("\n")
407
470
  };
408
471
  }
409
- function createTextChildren(value) {
410
- return value.length === 0 ? [] : [{ type: "text", value }];
472
+ function createTextChildren(value, range, offsets) {
473
+ return value.length === 0 ? [] : [createTextNode(value, range, offsets)];
411
474
  }
412
- function createTableRowNode(values) {
413
- return {
475
+ function createTableRowNode(state, line, cells) {
476
+ return withRange({
414
477
  type: "tableRow",
415
- children: values.map((value) => ({
416
- type: "tableCell",
417
- children: createTextChildren(value)
418
- }))
478
+ children: cells.map((cell) => {
479
+ const content = createMappedTextFromLineSlice(state, line, cell.start, cell.end);
480
+ return withRange({
481
+ type: "tableCell",
482
+ children: createTextChildren(cell.value, {
483
+ start: content.offsets[0] ?? 0,
484
+ end: content.offsets[content.offsets.length - 1] ?? 0
485
+ }, content.offsets)
486
+ }, {
487
+ start: content.offsets[0] ?? 0,
488
+ end: content.offsets[content.offsets.length - 1] ?? 0
489
+ });
490
+ })
491
+ }, {
492
+ start: state.offsets[line.start] ?? 0,
493
+ end: state.offsets[line.nextPosition] ?? state.offsets[line.end] ?? 0
494
+ });
495
+ }
496
+ function createTextNode(value, range, sourceOffsets) {
497
+ const node = range === undefined ? { type: "text", value } : withRange({ type: "text", value }, range);
498
+ if (sourceOffsets !== undefined) {
499
+ Object.defineProperty(node, SOURCE_OFFSETS, {
500
+ value: [...sourceOffsets],
501
+ enumerable: false,
502
+ configurable: true,
503
+ writable: true
504
+ });
505
+ }
506
+ return node;
507
+ }
508
+ function createNodeRange(state, start, end = state.position) {
509
+ return {
510
+ start: state.offsets[start] ?? state.offsets[state.offsets.length - 1] ?? 0,
511
+ end: state.offsets[end] ?? state.offsets[state.offsets.length - 1] ?? 0
512
+ };
513
+ }
514
+ function withRange(node, range) {
515
+ Object.defineProperty(node, "range", {
516
+ value: range,
517
+ enumerable: false,
518
+ configurable: true,
519
+ writable: true
520
+ });
521
+ return node;
522
+ }
523
+ function replaceNodeChildren(node, children) {
524
+ const nextNode = { ...node, children };
525
+ return node.range === undefined ? nextNode : withRange(nextNode, node.range);
526
+ }
527
+ function getTextNodeSourceOffsets(node) {
528
+ const sourceOffsets = node[SOURCE_OFFSETS];
529
+ if (sourceOffsets !== undefined) {
530
+ return sourceOffsets;
531
+ }
532
+ return node.range === undefined ? undefined : createOffsetMap(node.value, node.range.start, node.range.end);
533
+ }
534
+ function createOffsetMap(input, absoluteStart = 0, absoluteEnd) {
535
+ const offsets = new Array(input.length + 1).fill(absoluteStart);
536
+ let byteOffset = absoluteStart;
537
+ let index = 0;
538
+ while (index < input.length) {
539
+ offsets[index] = byteOffset;
540
+ const codePoint = input.codePointAt(index) ?? 0;
541
+ const codeUnitLength = codePoint > 0xffff ? 2 : 1;
542
+ const byteLength = codePoint <= 0x7f ? 1 : codePoint <= 0x7ff ? 2 : codePoint <= 0xffff ? 3 : 4;
543
+ for (let offsetIndex = 1; offsetIndex < codeUnitLength; offsetIndex += 1) {
544
+ offsets[index + offsetIndex] = byteOffset;
545
+ }
546
+ byteOffset += byteLength;
547
+ index += codeUnitLength;
548
+ offsets[index] = byteOffset;
549
+ }
550
+ offsets[input.length] = absoluteEnd ?? byteOffset;
551
+ return offsets;
552
+ }
553
+ function createMappedText(value, offsets) {
554
+ return { text: value, offsets };
555
+ }
556
+ function createMappedTextFromSlice(state, start, end) {
557
+ return createMappedText(state.input.slice(start, end), state.offsets.slice(start, end + 1));
558
+ }
559
+ function createMappedTextFromLineSlice(state, line, start, end) {
560
+ return {
561
+ ...createMappedTextFromSlice(state, line.start + start, line.start + end),
562
+ lineBreakEnd: state.offsets[line.nextPosition] ?? state.offsets[state.offsets.length - 1] ?? 0
419
563
  };
420
564
  }
565
+ function createMappedLineBreak(state, line) {
566
+ if (line.nextPosition <= line.end) {
567
+ return null;
568
+ }
569
+ return createMappedText("\n", [state.offsets[line.end] ?? 0, state.offsets[line.nextPosition] ?? 0]);
570
+ }
571
+ function joinMappedTexts(parts) {
572
+ if (parts.length === 0) {
573
+ return createMappedText("", [0]);
574
+ }
575
+ let text = "";
576
+ const offsets = [];
577
+ for (const [index, part] of parts.entries()) {
578
+ text += part.text;
579
+ if (index === 0) {
580
+ offsets.push(...part.offsets);
581
+ continue;
582
+ }
583
+ offsets.push(...part.offsets.slice(1));
584
+ }
585
+ return createMappedText(text, offsets);
586
+ }
587
+ function createMappedTextFromLines(state, lines) {
588
+ const parts = [];
589
+ for (const [index, line] of lines.entries()) {
590
+ parts.push(createMappedTextFromLineSlice(state, line, 0, line.text.length));
591
+ if (index + 1 < lines.length) {
592
+ const lineBreak = createMappedLineBreak(state, line);
593
+ if (lineBreak !== null) {
594
+ parts.push(lineBreak);
595
+ }
596
+ }
597
+ }
598
+ return joinMappedTexts(parts);
599
+ }
600
+ function joinMappedLines(lines) {
601
+ const parts = [];
602
+ for (const [index, line] of lines.entries()) {
603
+ parts.push(createMappedText(line.text, line.offsets));
604
+ if (index + 1 < lines.length) {
605
+ const lineBreakStart = line.offsets[line.offsets.length - 1] ?? 0;
606
+ const lineBreakEnd = line.lineBreakEnd ?? lineBreakStart;
607
+ parts.push(createMappedText("\n", [lineBreakStart, lineBreakEnd]));
608
+ }
609
+ }
610
+ return joinMappedTexts(parts);
611
+ }
421
612
  function startsBlockAt(input, position, preferListToThematicBreak) {
422
613
  const line = readLine(input, position);
423
614
  if (startsSimpleBlock(line.text, preferListToThematicBreak)) {
@@ -430,12 +621,12 @@ function startsBlockAt(input, position, preferListToThematicBreak) {
430
621
  return parseTableHeaderAndSeparator(line.text, nextLine.text) !== null;
431
622
  }
432
623
  function startsBlockInLines(lines, lineIndex, preferListToThematicBreak) {
433
- const line = lines[lineIndex];
624
+ const line = lines[lineIndex]?.text ?? "";
434
625
  if (startsSimpleBlock(line, preferListToThematicBreak)) {
435
626
  return true;
436
627
  }
437
628
  return (lineIndex + 1 < lines.length &&
438
- parseTableHeaderAndSeparator(line, lines[lineIndex + 1]) !== null);
629
+ parseTableHeaderAndSeparator(line, lines[lineIndex + 1]?.text ?? "") !== null);
439
630
  }
440
631
  function startsSimpleBlock(line, preferListToThematicBreak) {
441
632
  if (parseOpeningFence(line) !== null ||
@@ -444,7 +635,7 @@ function startsSimpleBlock(line, preferListToThematicBreak) {
444
635
  parseFootnoteDefinitionMarker(line) !== null) {
445
636
  return true;
446
637
  }
447
- if (stripBlockquoteMarker(line) !== null) {
638
+ if (parseBlockquoteLine(line) !== null) {
448
639
  return true;
449
640
  }
450
641
  if (preferListToThematicBreak) {
@@ -499,10 +690,17 @@ function parseAtxHeadingLine(line) {
499
690
  if (markerEnd < line.length && line[markerEnd] !== " " && line[markerEnd] !== "\t") {
500
691
  return null;
501
692
  }
502
- const rawContent = trimAsciiWhitespaceStart(line.slice(markerEnd));
693
+ let contentStart = markerEnd;
694
+ while (contentStart < line.length && (line[contentStart] === " " || line[contentStart] === "\t")) {
695
+ contentStart += 1;
696
+ }
697
+ const rawContent = line.slice(contentStart);
698
+ const text = stripClosingHeadingSequence(rawContent);
503
699
  return {
504
700
  depth: depth,
505
- text: stripClosingHeadingSequence(rawContent)
701
+ text,
702
+ contentStart,
703
+ contentEnd: contentStart + text.length
506
704
  };
507
705
  }
508
706
  function stripClosingHeadingSequence(value) {
@@ -600,7 +798,7 @@ function parseSetextUnderline(line) {
600
798
  function parseTableAt(input, position, preferListToThematicBreak) {
601
799
  const headerLine = readLine(input, position);
602
800
  if (parseListMarker(headerLine.text) !== null ||
603
- stripBlockquoteMarker(headerLine.text) !== null) {
801
+ parseBlockquoteLine(headerLine.text) !== null) {
604
802
  return null;
605
803
  }
606
804
  if (headerLine.nextPosition >= input.length) {
@@ -621,22 +819,25 @@ function parseTableAt(input, position, preferListToThematicBreak) {
621
819
  if (startsSimpleBlock(rowLine.text, preferListToThematicBreak)) {
622
820
  break;
623
821
  }
624
- const cells = parsePipeTableCells(rowLine.text);
822
+ const cells = parsePipeTableCellSegments(rowLine.text);
625
823
  if (cells === null) {
626
824
  break;
627
825
  }
628
- rows.push(normalizeTableCells(cells, header.headerCells.length));
826
+ rows.push({
827
+ line: rowLine,
828
+ cells: normalizeTableCellSegments(cells, header.headerCells.length)
829
+ });
629
830
  nextPosition = rowLine.nextPosition;
630
831
  }
631
832
  return {
632
833
  align: header.align,
633
- headerCells: header.headerCells,
834
+ header: { line: headerLine, cells: header.headerCells },
634
835
  rows,
635
836
  nextPosition
636
837
  };
637
838
  }
638
839
  function parseTableHeaderAndSeparator(headerLine, separatorLine) {
639
- const headerCells = parsePipeTableCells(headerLine);
840
+ const headerCells = parsePipeTableCellSegments(headerLine);
640
841
  if (headerCells === null || headerCells.length === 0) {
641
842
  return null;
642
843
  }
@@ -647,6 +848,9 @@ function parseTableHeaderAndSeparator(headerLine, separatorLine) {
647
848
  return { align, headerCells };
648
849
  }
649
850
  function parsePipeTableCells(line) {
851
+ return parsePipeTableCellSegments(line)?.map((cell) => cell.value) ?? null;
852
+ }
853
+ function parsePipeTableCellSegments(line) {
650
854
  const start = skipLeadingBlockIndent(line);
651
855
  if (start === -1 || start >= line.length) {
652
856
  return null;
@@ -654,36 +858,51 @@ function parsePipeTableCells(line) {
654
858
  const content = trimAsciiWhitespaceEnd(line.slice(start));
655
859
  let hasPipe = false;
656
860
  const cells = [];
657
- let cell = "";
861
+ let cellStart = 0;
658
862
  let index = 0;
659
863
  while (index < content.length) {
660
864
  const char = content[index];
661
865
  if (char === "\\" && index + 1 < content.length && content[index + 1] === "|") {
662
- cell += "|";
663
866
  index += 2;
664
867
  continue;
665
868
  }
666
869
  if (char === "|") {
667
- cells.push(trimAsciiWhitespace(cell));
668
- cell = "";
870
+ cells.push({ start: cellStart, end: index });
871
+ cellStart = index + 1;
669
872
  hasPipe = true;
670
873
  index += 1;
671
874
  continue;
672
875
  }
673
- cell += char;
674
876
  index += 1;
675
877
  }
676
878
  if (!hasPipe) {
677
879
  return null;
678
880
  }
679
- cells.push(trimAsciiWhitespace(cell));
881
+ cells.push({ start: cellStart, end: content.length });
680
882
  if (content[0] === "|") {
681
883
  cells.shift();
682
884
  }
683
885
  if (content[content.length - 1] === "|") {
684
886
  cells.pop();
685
887
  }
686
- return cells.length === 0 ? null : cells;
888
+ if (cells.length === 0) {
889
+ return null;
890
+ }
891
+ return cells.map((cell) => {
892
+ let cellStart = cell.start;
893
+ let cellEnd = cell.end;
894
+ while (cellStart < cellEnd && (content[cellStart] === " " || content[cellStart] === "\t")) {
895
+ cellStart += 1;
896
+ }
897
+ while (cellEnd > cellStart && (content[cellEnd - 1] === " " || content[cellEnd - 1] === "\t")) {
898
+ cellEnd -= 1;
899
+ }
900
+ return {
901
+ value: decodePipeTableCell(trimAsciiWhitespace(content.slice(cell.start, cell.end))),
902
+ start: start + cellStart,
903
+ end: start + cellEnd
904
+ };
905
+ });
687
906
  }
688
907
  function parsePipeTableSeparator(line) {
689
908
  const cells = parsePipeTableCells(line);
@@ -727,16 +946,37 @@ function parseTableAlignmentCell(value) {
727
946
  }
728
947
  return null;
729
948
  }
730
- function normalizeTableCells(cells, columnCount) {
949
+ function normalizeTableCellSegments(cells, columnCount) {
731
950
  if (cells.length === columnCount) {
732
951
  return cells;
733
952
  }
734
953
  if (cells.length > columnCount) {
735
954
  return cells.slice(0, columnCount);
736
955
  }
737
- return [...cells, ...Array.from({ length: columnCount - cells.length }, () => "")];
956
+ return [
957
+ ...cells,
958
+ ...Array.from({ length: columnCount - cells.length }, () => ({
959
+ value: "",
960
+ start: cells[cells.length - 1]?.end ?? 0,
961
+ end: cells[cells.length - 1]?.end ?? 0
962
+ }))
963
+ ];
738
964
  }
739
- function stripBlockquoteMarker(line) {
965
+ function decodePipeTableCell(value) {
966
+ let decoded = "";
967
+ let index = 0;
968
+ while (index < value.length) {
969
+ if (value[index] === "\\" && value[index + 1] === "|") {
970
+ decoded += "|";
971
+ index += 2;
972
+ continue;
973
+ }
974
+ decoded += value[index] ?? "";
975
+ index += 1;
976
+ }
977
+ return decoded;
978
+ }
979
+ function parseBlockquoteLine(line) {
740
980
  const markerStart = skipLeadingBlockIndent(line);
741
981
  if (markerStart === -1 || markerStart >= line.length || line[markerStart] !== ">") {
742
982
  return null;
@@ -745,7 +985,10 @@ function stripBlockquoteMarker(line) {
745
985
  if (contentStart < line.length && (line[contentStart] === " " || line[contentStart] === "\t")) {
746
986
  contentStart += 1;
747
987
  }
748
- return line.slice(contentStart);
988
+ return {
989
+ content: line.slice(contentStart),
990
+ contentStart
991
+ };
749
992
  }
750
993
  function parseAlertMarker(content) {
751
994
  const endOfKind = content.indexOf("]");
@@ -756,9 +999,12 @@ function parseAlertMarker(content) {
756
999
  if (!isAlertKind(kind)) {
757
1000
  return null;
758
1001
  }
1002
+ const rawContent = content.slice(endOfKind + 1);
1003
+ const trimmedContent = trimAsciiWhitespaceStart(rawContent);
759
1004
  return {
760
1005
  kind,
761
- content: trimAsciiWhitespaceStart(content.slice(endOfKind + 1))
1006
+ content: trimmedContent,
1007
+ contentStart: endOfKind + 1 + (rawContent.length - trimmedContent.length)
762
1008
  };
763
1009
  }
764
1010
  function parseFootnoteDefinitionMarker(line) {
@@ -975,12 +1221,12 @@ function readLine(input, position) {
975
1221
  }
976
1222
  const text = input.slice(position, index);
977
1223
  if (index >= input.length) {
978
- return { text, nextPosition: input.length };
1224
+ return { start: position, text, end: index, nextPosition: input.length };
979
1225
  }
980
1226
  if (input[index] === "\r" && input[index + 1] === "\n") {
981
- return { text, nextPosition: index + 2 };
1227
+ return { start: position, text, end: index, nextPosition: index + 2 };
982
1228
  }
983
- return { text, nextPosition: index + 1 };
1229
+ return { start: position, text, end: index, nextPosition: index + 1 };
984
1230
  }
985
1231
  function isBlankLine(line) {
986
1232
  for (let index = 0; index < line.length; index += 1) {
@@ -992,11 +1238,12 @@ function isBlankLine(line) {
992
1238
  return true;
993
1239
  }
994
1240
  function skipLeadingBlockIndent(line) {
995
- const leadingWhitespace = readLeadingWhitespace(line);
1241
+ const bomOffset = line.startsWith("\uFEFF") ? 1 : 0;
1242
+ const leadingWhitespace = readLeadingWhitespace(line.slice(bomOffset));
996
1243
  if (leadingWhitespace.columns > 3) {
997
1244
  return -1;
998
1245
  }
999
- return leadingWhitespace.offset;
1246
+ return bomOffset + leadingWhitespace.offset;
1000
1247
  }
1001
1248
  function trimAsciiWhitespace(value) {
1002
1249
  return trimAsciiWhitespaceEnd(trimAsciiWhitespaceStart(value));
@@ -1023,6 +1270,21 @@ function trimAsciiWhitespaceEnd(value) {
1023
1270
  }
1024
1271
  return value.slice(0, end);
1025
1272
  }
1273
+ function trimAsciiWhitespaceRange(value) {
1274
+ let start = 0;
1275
+ let end = value.length;
1276
+ while (start < end && (value[start] === " " || value[start] === "\t")) {
1277
+ start += 1;
1278
+ }
1279
+ while (end > start && (value[end - 1] === " " || value[end - 1] === "\t")) {
1280
+ end -= 1;
1281
+ }
1282
+ return {
1283
+ value: value.slice(start, end),
1284
+ start,
1285
+ end
1286
+ };
1287
+ }
1026
1288
  function findWhitespaceIndex(value) {
1027
1289
  for (let index = 0; index < value.length; index += 1) {
1028
1290
  const char = value[index];
@@ -1067,29 +1329,33 @@ function isAlertKind(value) {
1067
1329
  value === "WARNING" ||
1068
1330
  value === "CAUTION");
1069
1331
  }
1070
- function stripBom(input) {
1071
- return input[0] === "\uFEFF" ? input.slice(1) : input;
1072
- }
1073
1332
  function parseListItem(state, list) {
1333
+ const rangeStart = state.position;
1074
1334
  const firstLine = readLine(state.input, state.position);
1075
1335
  const marker = parseListMarker(firstLine.text);
1076
1336
  if (marker === null || marker.ordered !== list.ordered || marker.indent !== list.indent) {
1077
1337
  return null;
1078
1338
  }
1079
1339
  state.position = firstLine.nextPosition;
1080
- let firstLineContent = firstLine.text.slice(marker.contentStart);
1340
+ let firstLineContentStart = marker.contentStart;
1341
+ let firstLineContent = firstLine.text.slice(firstLineContentStart);
1081
1342
  let checked;
1082
1343
  const taskMarker = parseTaskMarker(firstLineContent);
1083
1344
  if (taskMarker !== null) {
1084
1345
  checked = taskMarker.checked;
1085
1346
  firstLineContent = taskMarker.content;
1347
+ firstLineContentStart += taskMarker.contentStart;
1086
1348
  }
1087
1349
  const continuationLines = [];
1088
1350
  const pendingBlankLines = [];
1089
1351
  while (state.position < state.input.length) {
1090
1352
  const line = readLine(state.input, state.position);
1091
1353
  if (isBlankLine(line.text)) {
1092
- pendingBlankLines.push("");
1354
+ pendingBlankLines.push({
1355
+ text: "",
1356
+ offsets: [state.offsets[line.end] ?? 0],
1357
+ lineBreakEnd: state.offsets[line.nextPosition] ?? state.offsets[state.offsets.length - 1] ?? 0
1358
+ });
1093
1359
  state.position = line.nextPosition;
1094
1360
  continue;
1095
1361
  }
@@ -1099,7 +1365,7 @@ function parseListItem(state, list) {
1099
1365
  nextMarker.indent === list.indent) {
1100
1366
  break;
1101
1367
  }
1102
- const strippedLine = stripIndent(line.text, marker.contentIndent);
1368
+ const strippedLine = stripIndentLine(state, line, marker.contentIndent);
1103
1369
  if (strippedLine === null) {
1104
1370
  break;
1105
1371
  }
@@ -1107,20 +1373,20 @@ function parseListItem(state, list) {
1107
1373
  continuationLines.push(...pendingBlankLines, strippedLine);
1108
1374
  pendingBlankLines.length = 0;
1109
1375
  }
1110
- const children = parseListItemChildren(firstLineContent, continuationLines, list.preferListToThematicBreak);
1111
- return {
1376
+ const children = parseListItemChildren(createMappedTextFromLineSlice(state, firstLine, firstLineContentStart, firstLine.text.length), continuationLines, list.preferListToThematicBreak);
1377
+ return withRange({
1112
1378
  type: "listItem",
1113
1379
  ...(checked === undefined ? {} : { checked }),
1114
1380
  children
1115
- };
1381
+ }, createNodeRange(state, rangeStart));
1116
1382
  }
1117
1383
  function parseListItemChildren(firstLineContent, continuationLines, preferListToThematicBreak) {
1118
1384
  const blocks = [];
1119
- let paragraphLines = firstLineContent.length === 0 ? [] : [firstLineContent];
1385
+ let paragraphLines = firstLineContent.text.length === 0 ? [] : [firstLineContent];
1120
1386
  let lineIndex = 0;
1121
1387
  while (lineIndex < continuationLines.length) {
1122
1388
  const line = continuationLines[lineIndex];
1123
- if (isBlankLine(line)) {
1389
+ if (isBlankLine(line.text)) {
1124
1390
  if (paragraphLines.length > 0) {
1125
1391
  blocks.push(createParagraphNode(paragraphLines));
1126
1392
  paragraphLines = [];
@@ -1132,8 +1398,10 @@ function parseListItemChildren(firstLineContent, continuationLines, preferListTo
1132
1398
  if (paragraphLines.length > 0) {
1133
1399
  blocks.push(createParagraphNode(paragraphLines));
1134
1400
  }
1135
- blocks.push(...parseBlocksWithOptions(continuationLines.slice(lineIndex).join("\n"), {
1136
- preferListToThematicBreak
1401
+ const nestedContent = joinMappedLines(continuationLines.slice(lineIndex));
1402
+ blocks.push(...parseBlocksWithOptions(nestedContent.text, {
1403
+ preferListToThematicBreak,
1404
+ offsets: nestedContent.offsets
1137
1405
  }));
1138
1406
  return blocks;
1139
1407
  }
@@ -1146,10 +1414,17 @@ function parseListItemChildren(firstLineContent, continuationLines, preferListTo
1146
1414
  return blocks;
1147
1415
  }
1148
1416
  function createParagraphNode(lines) {
1149
- return {
1417
+ const content = joinMappedLines(lines);
1418
+ return withRange({
1150
1419
  type: "paragraph",
1151
- children: [{ type: "text", value: lines.join("\n") }]
1152
- };
1420
+ children: createTextChildren(content.text, {
1421
+ start: content.offsets[0] ?? 0,
1422
+ end: content.offsets[content.offsets.length - 1] ?? 0
1423
+ }, content.offsets)
1424
+ }, {
1425
+ start: lines[0]?.offsets[0] ?? 0,
1426
+ end: content.offsets[content.offsets.length - 1] ?? 0
1427
+ });
1153
1428
  }
1154
1429
  function parseTaskMarker(content) {
1155
1430
  if (content.length < 3 || content[0] !== "[" || content[2] !== "]") {
@@ -1164,15 +1439,30 @@ function parseTaskMarker(content) {
1164
1439
  }
1165
1440
  return {
1166
1441
  checked: marker === "x" || marker === "X",
1167
- content: trimAsciiWhitespaceStart(content.slice(3))
1442
+ content: trimAsciiWhitespaceStart(content.slice(3)),
1443
+ contentStart: 3 + (content.slice(3).length - trimAsciiWhitespaceStart(content.slice(3)).length)
1168
1444
  };
1169
1445
  }
1170
- function stripIndent(line, columns) {
1171
- const leadingWhitespace = readLeadingWhitespace(line);
1446
+ function stripIndentLine(state, line, columns) {
1447
+ const leadingWhitespace = readLeadingWhitespace(line.text);
1172
1448
  if (leadingWhitespace.columns < columns) {
1173
1449
  return null;
1174
1450
  }
1175
- return leadingWhitespace.normalized.slice(columns) + line.slice(leadingWhitespace.offset);
1451
+ const prefix = leadingWhitespace.normalized.slice(columns);
1452
+ const prefixStart = state.offsets[line.start + leadingWhitespace.offset] ?? 0;
1453
+ const parts = [];
1454
+ if (prefix.length > 0) {
1455
+ parts.push(createMappedText(prefix, new Array(prefix.length + 1).fill(prefixStart)));
1456
+ }
1457
+ parts.push({
1458
+ ...createMappedTextFromLineSlice(state, line, leadingWhitespace.offset, line.text.length),
1459
+ lineBreakEnd: state.offsets[line.nextPosition] ?? state.offsets[state.offsets.length - 1] ?? 0
1460
+ });
1461
+ const stripped = joinMappedTexts(parts);
1462
+ return {
1463
+ ...stripped,
1464
+ lineBreakEnd: state.offsets[line.nextPosition] ?? state.offsets[state.offsets.length - 1] ?? 0
1465
+ };
1176
1466
  }
1177
1467
  function readLeadingWhitespace(line) {
1178
1468
  let columns = 0;