From 0ae6dbdcbcc7a5c9c360b66bacd4122baf3503cb Mon Sep 17 00:00:00 2001 From: Justin Ridgewell Date: Tue, 16 Mar 2021 05:16:11 -0400 Subject: [PATCH] Truncate mappings to the last line with a valid segment Re: #116, which has an sourcemap without any segments. There's no point in keeping trailing lines without any segments, and truncating better matches the output from `source-map`. --- src/source-map-tree.ts | 5 +++++ test/unit/source-map-tree.ts | 32 ++++++++++++++++++++++++++++++-- 2 files changed, 35 insertions(+), 2 deletions(-) diff --git a/src/source-map-tree.ts b/src/source-map-tree.ts index 12213a0..d5e4091 100644 --- a/src/source-map-tree.ts +++ b/src/source-map-tree.ts @@ -54,6 +54,7 @@ export default class SourceMapTree { const sourcesContent: (string | null)[] = []; const { mappings: rootMappings, names: rootNames } = this.map; + let lastLineWithSegment = -1; for (let i = 0; i < rootMappings.length; i++) { const segments = rootMappings[i]; const tracedSegments: SourceMapSegment[] = []; @@ -105,10 +106,14 @@ export default class SourceMapTree { lastTraced = [segment[0], sourceIndex, line, column]; } tracedSegments.push(lastTraced); + lastLineWithSegment = i; } mappings.push(tracedSegments); } + if (mappings.length > lastLineWithSegment + 1) { + mappings.length = lastLineWithSegment + 1; + } // TODO: Make all sources relative to the sourceRoot. diff --git a/test/unit/source-map-tree.ts b/test/unit/source-map-tree.ts index a45c6da..534fe0f 100644 --- a/test/unit/source-map-tree.ts +++ b/test/unit/source-map-tree.ts @@ -54,7 +54,7 @@ describe('SourceMapTree', () => { const source = new SourceMapTree(map, [child]); const traced = source.traceMappings(); - expect(traced.mappings).toEqual([[]]); + expect(traced.mappings).toEqual([]); }); test('skips segment if trace returns null', () => { @@ -68,7 +68,7 @@ describe('SourceMapTree', () => { const source = new SourceMapTree(map, [child]); const traced = source.traceMappings(); - expect(traced.mappings).toEqual([[]]); + expect(traced.mappings).toEqual([]); }); test('traces name if segment is 5-length', () => { @@ -155,6 +155,34 @@ describe('SourceMapTree', () => { }); }); + test('truncates mappings to the last line with segment', () => { + const map: DecodedSourceMap = { + ...baseMap, + mappings: [[[0, 0, 0, 0]], [], []], + sourceRoot, + }; + + const source = new SourceMapTree(map, [child]); + const traced = source.traceMappings(); + expect(traced).toMatchObject({ + mappings: [[[0, 0, 0, 0]]], + }); + }); + + test('truncates empty mappings', () => { + const map: DecodedSourceMap = { + ...baseMap, + mappings: [[], [], []], + sourceRoot, + }; + + const source = new SourceMapTree(map, [child]); + const traced = source.traceMappings(); + expect(traced).toMatchObject({ + mappings: [], + }); + }); + describe('redundant segments', () => { it('skips redundant segments on the same line', () => { const map: DecodedSourceMap = {