Track sourcemap location on a stack - fixes T7255

This commit is contained in:
Logan Smyth 2016-04-10 21:16:11 -07:00
parent 7d6d4c204b
commit 76bb1dffaa
15 changed files with 118 additions and 77 deletions

View File

@ -5,4 +5,4 @@ function _classCallCheck(instance, Constructor) { if (!(instance instanceof Cons
var Test = function Test() { var Test = function Test() {
_classCallCheck(this, Test); _classCallCheck(this, Test);
}; };
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uL3NyYy9iYXIvYmFyLmpzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7SUFBTSIsImZpbGUiOiJiYXIuanMiLCJzb3VyY2VzQ29udGVudCI6WyJjbGFzcyBUZXN0IHtcblxufSJdfQ== //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uL3NyYy9iYXIvYmFyLmpzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7SUFBTSxJIiwiZmlsZSI6ImJhci5qcyIsInNvdXJjZXNDb250ZW50IjpbImNsYXNzIFRlc3Qge1xuXG59Il19

View File

@ -3,4 +3,4 @@
arr.map(function (x) { arr.map(function (x) {
return x * MULTIPLIER; return x * MULTIPLIER;
}); });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uL3NyYy9mb28uanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7QUFBQSxJQUFJLEdBQUosQ0FBUTtTQUFLLElBQUksVUFBSjtDQUFMLENBQVIiLCJmaWxlIjoiZm9vLmpzIiwic291cmNlc0NvbnRlbnQiOlsiYXJyLm1hcCh4ID0+IHggKiBNVUxUSVBMSUVSKTsiXX0= //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uL3NyYy9mb28uanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7QUFBQSxJQUFJLEdBQUosQ0FBUTtBQUFBLFNBQUssSUFBSSxVQUFUO0FBQUEsQ0FBUiIsImZpbGUiOiJmb28uanMiLCJzb3VyY2VzQ29udGVudCI6WyJhcnIubWFwKHggPT4geCAqIE1VTFRJUExJRVIpOyJdfQ==

View File

@ -1 +1 @@
{"version":3,"sources":["../../src/bar/bar.js"],"names":[],"mappings":";;;;IAAM","file":"bar.js","sourcesContent":["class Test {\n\n}"]} {"version":3,"sources":["../../src/bar/bar.js"],"names":[],"mappings":";;;;IAAM,I","file":"bar.js","sourcesContent":["class Test {\n\n}"]}

View File

@ -1 +1 @@
{"version":3,"sources":["../src/foo.js"],"names":[],"mappings":";;AAAA,IAAI,GAAJ,CAAQ;SAAK,IAAI,UAAJ;CAAL,CAAR","file":"foo.js","sourcesContent":["arr.map(x => x * MULTIPLIER);"]} {"version":3,"sources":["../src/foo.js"],"names":[],"mappings":";;AAAA,IAAI,GAAJ,CAAQ;AAAA,SAAK,IAAI,UAAT;AAAA,CAAR","file":"foo.js","sourcesContent":["arr.map(x => x * MULTIPLIER);"]}

View File

@ -4,4 +4,4 @@ arr.map(function (x) {
return x * MULTIPLIER; return x * MULTIPLIER;
}); });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNjcmlwdC5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOztBQUFBLElBQUksR0FBSixDQUFRO1NBQUssSUFBSSxVQUFKO0NBQUwsQ0FBUiIsImZpbGUiOiJzY3JpcHQyLmpzIiwic291cmNlc0NvbnRlbnQiOlsiYXJyLm1hcCh4ID0+IHggKiBNVUxUSVBMSUVSKTsiXX0= //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNjcmlwdC5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOztBQUFBLElBQUksR0FBSixDQUFRO0FBQUEsU0FBSyxJQUFJLFVBQVQ7QUFBQSxDQUFSIiwiZmlsZSI6InNjcmlwdDIuanMiLCJzb3VyY2VzQ29udGVudCI6WyJhcnIubWFwKHggPT4geCAqIE1VTFRJUExJRVIpOyJdfQ==

View File

@ -4,4 +4,4 @@ var foo = function foo() {
return 4; return 4;
}; };
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNjcmlwdC5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOztBQUFBO1MsQUFBZ0IsQUFBQyxFO0NBQVAiLCJmaWxlIjoic2NyaXB0Mi5qcyIsInNvdXJjZXNDb250ZW50IjpbInZhciBmb28gPSBmdW5jdGlvbiAoKSB7XG4gIHJldHVybiA0O1xufTtcblxuLy8jIHNvdXJjZU1hcHBpbmdVUkw9ZGF0YTphcHBsaWNhdGlvbi9qc29uO2Jhc2U2NCxleUoyWlhKemFXOXVJam96TENKemIzVnlZMlZ6SWpwYkltOXlhV2RwYm1Gc0xtcHpJbDBzSW01aGJXVnpJanBiWFN3aWJXRndjR2x1WjNNaU9pSkJRVUZCTEZWQlFWVXNXVHRUUVVGTkxFTTdRMEZCUXlJc0luTnZkWEpqWlhORGIyNTBaVzUwSWpwYkluWmhjaUJtYjI4Z1BTQW9LU0E5UGlBME95SmRmUT09Il19 //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNjcmlwdC5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOztBQUFBLFVBQVU7UyxBQUFNLEFBQUM7QSIsImZpbGUiOiJzY3JpcHQyLmpzIiwic291cmNlc0NvbnRlbnQiOlsidmFyIGZvbyA9IGZ1bmN0aW9uICgpIHtcbiAgcmV0dXJuIDQ7XG59O1xuXG4vLyMgc291cmNlTWFwcGluZ1VSTD1kYXRhOmFwcGxpY2F0aW9uL2pzb247YmFzZTY0LGV5SjJaWEp6YVc5dUlqb3pMQ0p6YjNWeVkyVnpJanBiSW05eWFXZHBibUZzTG1weklsMHNJbTVoYldWeklqcGJYU3dpYldGd2NHbHVaM01pT2lKQlFVRkJMRlZCUVZVc1dUdFRRVUZOTEVNN1EwRkJReUlzSW5OdmRYSmpaWE5EYjI1MFpXNTBJanBiSW5aaGNpQm1iMjhnUFNBb0tTQTlQaUEwT3lKZGZRPT0iXX0=

View File

@ -11,4 +11,4 @@ arr.map(function (x) {
return x * MULTIPLIER; return x * MULTIPLIER;
}); });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNjcmlwdC5qcyIsInNjcmlwdDIuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7OztJQUFNOzs7Ozs7QUNBTixJQUFJLEdBQUosQ0FBUTtTQUFLLElBQUksVUFBSjtDQUFMLENBQVIiLCJmaWxlIjoic2NyaXB0My5qcyIsInNvdXJjZXNDb250ZW50IjpbImNsYXNzIFRlc3Qge1xuXG59IiwiYXJyLm1hcCh4ID0+IHggKiBNVUxUSVBMSUVSKTsiXX0= //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNjcmlwdC5qcyIsInNjcmlwdDIuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7OztJQUFNLEk7Ozs7OztBQ0FOLElBQUksR0FBSixDQUFRO0FBQUEsU0FBSyxJQUFJLFVBQVQ7QUFBQSxDQUFSIiwiZmlsZSI6InNjcmlwdDMuanMiLCJzb3VyY2VzQ29udGVudCI6WyJjbGFzcyBUZXN0IHtcblxufSIsImFyci5tYXAoeCA9PiB4ICogTVVMVElQTElFUik7Il19

View File

@ -1 +1 @@
{"version":3,"sources":["script.js","script2.js"],"names":[],"mappings":";;;;IAAM;;;;;;ACAN,IAAI,GAAJ,CAAQ;SAAK,IAAI,UAAJ;CAAL,CAAR","file":"script3.js","sourcesContent":["class Test {\n\n}","arr.map(x => x * MULTIPLIER);"]} {"version":3,"sources":["script.js","script2.js"],"names":[],"mappings":";;;;IAAM,I;;;;;;ACAN,IAAI,GAAJ,CAAQ;AAAA,SAAK,IAAI,UAAT;AAAA,CAAR","file":"script3.js","sourcesContent":["class Test {\n\n}","arr.map(x => x * MULTIPLIER);"]}

View File

@ -3,6 +3,6 @@
"file": "source-maps/full/expected.js", "file": "source-maps/full/expected.js",
"sources": ["source-maps/full/actual.js"], "sources": ["source-maps/full/actual.js"],
"names": [], "names": [],
"mappings": "AAAA,IAAI,GAAJ,CAAQ;SAAK,IAAI,CAAJ;CAAL,CAAR", "mappings": "AAAA,IAAI,GAAJ,CAAQ;AAAA,SAAK,IAAI,CAAT;AAAA,CAAR",
"sourcesContent": ["arr.map(x => x * x);"] "sourcesContent": ["arr.map(x => x * x);"]
} }

View File

@ -1,4 +1,4 @@
arr.map(function (x) { arr.map(function (x) {
return x * x; return x * x;
}); });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNvdXJjZS1tYXBzL2lubGluZS9hY3R1YWwuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsSUFBSSxHQUFKLENBQVE7U0FBSyxJQUFJLENBQUo7Q0FBTCxDQUFSIiwiZmlsZSI6InNvdXJjZS1tYXBzL2lubGluZS9leHBlY3RlZC5qcyIsInNvdXJjZXNDb250ZW50IjpbImFyci5tYXAoeCA9PiB4ICogeCk7Il19 //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbInNvdXJjZS1tYXBzL2lubGluZS9hY3R1YWwuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsSUFBSSxHQUFKLENBQVE7QUFBQSxTQUFLLElBQUksQ0FBVDtBQUFBLENBQVIiLCJmaWxlIjoic291cmNlLW1hcHMvaW5saW5lL2V4cGVjdGVkLmpzIiwic291cmNlc0NvbnRlbnQiOlsiYXJyLm1hcCh4ID0+IHggKiB4KTsiXX0=

View File

@ -1,6 +1,6 @@
{ {
"version": 3, "version": 3,
"mappings": "AAAA;SAAgB,A,AAAC,E;CAAP", "mappings": "AAAA,UAAU;SAAM,A,AAAC;A",
"names": [], "names": [],
"sources": [ "sources": [
"original.js" "original.js"

View File

@ -19,6 +19,13 @@ export default class Buffer {
// to make sure that v8 doesn't "flatten" the string more often than needed // to make sure that v8 doesn't "flatten" the string more often than needed
// see https://github.com/babel/babel/pull/3283 for details. // see https://github.com/babel/babel/pull/3283 for details.
this.last = ""; this.last = "";
this.map = null;
this._sourcePosition = {
line: null,
column: null,
filename: null,
};
} }
printedCommentStarts: Object; printedCommentStarts: Object;
@ -230,6 +237,40 @@ export default class Buffer {
} }
} }
/**
* Sets a given position as the current source location so generated code after this call
* will be given this position in the sourcemap.
*/
source(prop: string, loc: Location) {
if (prop && !loc) return;
let pos = loc ? loc[prop] : null;
this._sourcePosition.line = pos ? pos.line : null;
this._sourcePosition.column = pos ? pos.column : null;
this._sourcePosition.filename = loc && loc.filename || null;
}
/**
* Call a callback with a specific source location and restore on completion.
*/
withSource(prop: string, loc: Location, cb: () => void) {
// Use the call stack to manage a stack of "source location" data.
let originalLine = this._sourcePosition.line;
let originalColumn = this._sourcePosition.column;
let originalFilename = this._sourcePosition.filename;
this.source(prop, loc);
cb();
this._sourcePosition.line = originalLine;
this._sourcePosition.column = originalColumn;
this._sourcePosition.filename = originalFilename;
}
/** /**
* Push a string to the buffer, maintaining indentation and newlines. * Push a string to the buffer, maintaining indentation and newlines.
*/ */
@ -276,6 +317,9 @@ export default class Buffer {
} }
} }
// If there the line is ending, adding a new mapping marker is redundant
if (str[0] !== "\n") this.map.mark(this._sourcePosition);
// //
this.position.push(str); this.position.push(str);
this.buf += str; this.buf += str;

View File

@ -51,9 +51,10 @@ export default class Printer extends Buffer {
if (opts.before) opts.before(); if (opts.before) opts.before();
this.map.mark(node); let loc = (t.isProgram(node) || t.isFile(node)) ? null : node.loc;
this.withSource("start", loc, () => {
this._print(node, parent); this._print(node, parent);
});
// Check again if any of our children may have left an aux comment on the stack // Check again if any of our children may have left an aux comment on the stack
if (node.loc) this.printAuxAfterComment(); if (node.loc) this.printAuxAfterComment();
@ -64,7 +65,6 @@ export default class Printer extends Buffer {
// end // end
this._printStack.pop(); this._printStack.pop();
if (parent) this.map.mark(parent);
if (opts.after) opts.after(); if (opts.after) opts.after();
this.format.concise = oldConcise; this.format.concise = oldConcise;
@ -268,46 +268,50 @@ export default class Printer extends Buffer {
this.printedCommentStarts[comment.start] = true; this.printedCommentStarts[comment.start] = true;
} }
this.catchUp(comment); // Exclude comments from source mappings since they will only clutter things.
this.withSource(null, null, () => {
this.catchUp(comment);
// whitespace before // whitespace before
this.newline(this.whitespace.getNewlinesBefore(comment)); this.newline(this.whitespace.getNewlinesBefore(comment));
let column = this.position.column; let column = this.position.column;
let val = this.generateComment(comment); let val = this.generateComment(comment);
if (column && !this.isLast(["\n", " ", "[", "{"])) { if (column && !this.isLast(["\n", " ", "[", "{"])) {
this._push(" "); this._push(" ");
column++; column++;
}
//
if (comment.type === "CommentBlock" && this.format.indent.adjustMultilineComment) {
let offset = comment.loc && comment.loc.start.column;
if (offset) {
let newlineRegex = new RegExp("\\n\\s{1," + offset + "}", "g");
val = val.replace(newlineRegex, "\n");
} }
let indent = Math.max(this.indentSize(), column); //
val = val.replace(/\n/g, `\n${repeating(" ", indent)}`); if (comment.type === "CommentBlock" && this.format.indent.adjustMultilineComment) {
} let offset = comment.loc && comment.loc.start.column;
if (offset) {
let newlineRegex = new RegExp("\\n\\s{1," + offset + "}", "g");
val = val.replace(newlineRegex, "\n");
}
if (column === 0) { let indent = Math.max(this.indentSize(), column);
val = this.getIndent() + val; val = val.replace(/\n/g, `\n${repeating(" ", indent)}`);
} }
// force a newline for line comments when retainLines is set in case the next printed node if (column === 0) {
// doesn't catch up val = this.getIndent() + val;
if ((this.format.compact || this.format.concise || this.format.retainLines) && comment.type === "CommentLine") { }
val += "\n";
}
// // force a newline for line comments when retainLines is set in case the next printed node
this._push(val); // doesn't catch up
if ((this.format.compact || this.format.concise || this.format.retainLines) &&
comment.type === "CommentLine") {
val += "\n";
}
// whitespace after //
this.newline(this.whitespace.getNewlinesAfter(comment)); this._push(val);
// whitespace after
this.newline(this.whitespace.getNewlinesAfter(comment));
});
} }
printComments(comments?: Array<Object>) { printComments(comments?: Array<Object>) {

View File

@ -1,5 +1,4 @@
import sourceMap from "source-map"; import sourceMap from "source-map";
import * as t from "babel-types";
/** /**
* Build a sourcemap. * Build a sourcemap.
@ -43,46 +42,40 @@ export default class SourceMap {
} }
/** /**
* Mark a node's generated position, and add it to the sourcemap. * Mark the current generated position with a source position. May also be passed null line/column
* values to insert a mapping to nothing.
*/ */
mark(node) { mark(sourcePos: Object) {
let loc = node.loc;
if (!loc) return; // no location info
let map = this.map; let map = this.map;
if (!map) return; // no source map if (!map) return; // no source map
if (t.isProgram(node) || t.isFile(node)) return; // illegal mapping nodes
let position = this.position; let position = this.position;
let generated = { // Adding an empty mapping at the start of a generated line just clutters the map.
line: position.line, if (this._lastGenLine !== position.line && sourcePos.line === null) return;
column: position.column
};
let original = loc.start; // If this mapping points to the same source location as the last one, we can ignore it since
// the previous one covers it.
// Avoid emitting duplicates on either side. Duplicated if (this._lastGenLine === position.line && this._lastSourceLine === sourcePos.line &&
// original values creates unnecesssarily large source maps this._lastSourceColumn === sourcePos.column) {
// and increases compile time. Duplicates on the generated
// side can lead to incorrect mappings.
if (comparePosition(original, this.last.original)
|| comparePosition(generated, this.last.generated)) {
return; return;
} }
this.last = { this._lastGenLine = position.line;
source: loc.filename || this.opts.sourceFileName, this._lastSourceLine = sourcePos.line;
generated: generated, this._lastSourceColumn = sourcePos.column;
original: original
};
map.addMapping(this.last); map.addMapping({
generated: {
line: position.line,
column: position.column
},
source: sourcePos.line == null ? null : sourcePos.filename || this.opts.sourceFileName,
original: sourcePos.line == null ? null : {
line: sourcePos.line,
column: sourcePos.column,
},
});
} }
} }
function comparePosition(a, b) {
return a.line === b.line && a.column === b.column;
}

View File

@ -43,7 +43,7 @@ suite("generation", function () {
version: 3, version: 3,
sources: [ 'a.js', 'b.js' ], sources: [ 'a.js', 'b.js' ],
names: [], names: [],
mappings: 'AAAA,SAAS,EAAT,CAAa,GAAb,EAAkB;AAAE,UAAQ,GAAR,CAAY,GAAZ,EAAF;CAAlB;;GCAG,OAAH', mappings: 'AAAA,SAAS,EAAT,CAAa,GAAb,EAAkB;AAAE,UAAQ,GAAR,CAAY,GAAZ;AAAF;;ACAlB,GAAG,OAAH',
sourcesContent: [ sourcesContent: [
'function hi (msg) { console.log(msg); }\n', 'function hi (msg) { console.log(msg); }\n',
'hi(\'hello\');\n' 'hi(\'hello\');\n'