[Pkg-javascript-commits] [node-source-map] 01/05: Imported Upstream version 0.1.40
Leo Iannacone
l3on-guest at moszumanska.debian.org
Sun Oct 12 12:18:42 UTC 2014
This is an automated email from the git hooks/post-receive script.
l3on-guest pushed a commit to branch master
in repository node-source-map.
commit a2b492d735fd20574aabb613688e74bef7050ab8
Author: Leo Iannacone <l3on at ubuntu.com>
Date: Sun Oct 12 12:27:52 2014 +0200
Imported Upstream version 0.1.40
---
CHANGELOG.md | 36 ++++++++
README.md | 7 +-
lib/source-map/base64-vlq.js | 10 +--
lib/source-map/source-map-consumer.js | 39 ++++----
lib/source-map/source-map-generator.js | 67 +++++++-------
lib/source-map/source-node.js | 24 +++--
lib/source-map/util.js | 45 +++++++---
package.json | 8 +-
test/source-map/test-base64-vlq.js | 5 +-
test/source-map/test-source-map-consumer.js | 70 +++++++++++++--
test/source-map/test-source-map-generator.js | 127 +++++++++++++++++++++++++--
test/source-map/test-source-node.js | 125 ++++++++++++++++++++++++++
test/source-map/test-util.js | 89 +++++++++++++++++++
test/source-map/util.js | 15 ++++
14 files changed, 566 insertions(+), 101 deletions(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 240d54a..518bed4 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,41 @@
# Change Log
+## 0.1.40
+
+* Performance improvements for parsing source maps in SourceMapConsumer.
+
+## 0.1.39
+
+* Fix a bug where setting a source's contents to null before any source content
+ had been set before threw a TypeError. See issue #131.
+
+## 0.1.38
+
+* Fix a bug where finding relative paths from an empty path were creating
+ absolute paths. See issue #129.
+
+## 0.1.37
+
+* Fix a bug where if the source root was an empty string, relative source paths
+ would turn into absolute source paths. Issue #124.
+
+## 0.1.36
+
+* Allow the `names` mapping property to be an empty string. Issue #121.
+
+## 0.1.35
+
+* A third optional parameter was added to `SourceNode.fromStringWithSourceMap`
+ to specify a path that relative sources in the second parameter should be
+ relative to. Issue #105.
+
+* If no file property is given to a `SourceMapGenerator`, then the resulting
+ source map will no longer have a `null` file property. The property will
+ simply not exist. Issue #104.
+
+* Fixed a bug where consecutive newlines were ignored in `SourceNode`s.
+ Issue #116.
+
## 0.1.34
* Make `SourceNode` work with windows style ("\r\n") newlines. Issue #103.
diff --git a/README.md b/README.md
index b00e970..1a1c7d8 100644
--- a/README.md
+++ b/README.md
@@ -332,7 +332,7 @@ use before outputting the generated JS and source map.
* `name`: Optional. The original identifier.
-#### SourceNode.fromStringWithSourceMap(code, sourceMapConsumer)
+#### SourceNode.fromStringWithSourceMap(code, sourceMapConsumer[, relativePath])
Creates a SourceNode from generated code and a SourceMapConsumer.
@@ -340,6 +340,9 @@ Creates a SourceNode from generated code and a SourceMapConsumer.
* `sourceMapConsumer` The SourceMap for the generated code
+* `relativePath` The optional path that relative sources in `sourceMapConsumer`
+ should be relative to.
+
#### SourceNode.prototype.add(chunk)
Add a chunk of generated JS to this source node.
@@ -399,7 +402,7 @@ for trimming whitespace from the end of a source node, etc.
Return the string representation of this source node. Walks over the tree and
concatenates all the various snippets together to one string.
-### SourceNode.prototype.toStringWithSourceMap([startOfSourceMap])
+#### SourceNode.prototype.toStringWithSourceMap([startOfSourceMap])
Returns the string representation of this tree of source nodes, plus a
SourceMapGenerator which contains all the mappings between the generated and
diff --git a/lib/source-map/base64-vlq.js b/lib/source-map/base64-vlq.js
index 1b67bb3..b4ff136 100644
--- a/lib/source-map/base64-vlq.js
+++ b/lib/source-map/base64-vlq.js
@@ -115,9 +115,9 @@ define(function (require, exports, module) {
/**
* Decodes the next base 64 VLQ value from the given string and returns the
- * value and the rest of the string.
+ * value and the rest of the string via the out parameter.
*/
- exports.decode = function base64VLQ_decode(aStr) {
+ exports.decode = function base64VLQ_decode(aStr, aOutParam) {
var i = 0;
var strLen = aStr.length;
var result = 0;
@@ -135,10 +135,8 @@ define(function (require, exports, module) {
shift += VLQ_BASE_SHIFT;
} while (continuation);
- return {
- value: fromVLQSigned(result),
- rest: aStr.slice(i)
- };
+ aOutParam.value = fromVLQSigned(result);
+ aOutParam.rest = aStr.slice(i);
};
});
diff --git a/lib/source-map/source-map-consumer.js b/lib/source-map/source-map-consumer.js
index 5214d5e..ea643bf 100644
--- a/lib/source-map/source-map-consumer.js
+++ b/lib/source-map/source-map-consumer.js
@@ -116,7 +116,7 @@ define(function (require, exports, module) {
Object.defineProperty(SourceMapConsumer.prototype, 'sources', {
get: function () {
return this._sources.toArray().map(function (s) {
- return this.sourceRoot ? util.join(this.sourceRoot, s) : s;
+ return this.sourceRoot != null ? util.join(this.sourceRoot, s) : s;
}, this);
}
});
@@ -177,6 +177,12 @@ define(function (require, exports, module) {
}
});
+ SourceMapConsumer.prototype._nextCharIsMappingSeparator =
+ function SourceMapConsumer_nextCharIsMappingSeparator(aStr) {
+ var c = aStr.charAt(0);
+ return c === ";" || c === ",";
+ };
+
/**
* Parse the mappings in a string in to a data structure which we can easily
* query (the ordered arrays in the `this.__generatedMappings` and
@@ -190,10 +196,9 @@ define(function (require, exports, module) {
var previousOriginalColumn = 0;
var previousSource = 0;
var previousName = 0;
- var mappingSeparator = /^[,;]/;
var str = aStr;
+ var temp = {};
var mapping;
- var temp;
while (str.length > 0) {
if (str.charAt(0) === ';') {
@@ -209,41 +214,41 @@ define(function (require, exports, module) {
mapping.generatedLine = generatedLine;
// Generated column.
- temp = base64VLQ.decode(str);
+ base64VLQ.decode(str, temp);
mapping.generatedColumn = previousGeneratedColumn + temp.value;
previousGeneratedColumn = mapping.generatedColumn;
str = temp.rest;
- if (str.length > 0 && !mappingSeparator.test(str.charAt(0))) {
+ if (str.length > 0 && !this._nextCharIsMappingSeparator(str)) {
// Original source.
- temp = base64VLQ.decode(str);
+ base64VLQ.decode(str, temp);
mapping.source = this._sources.at(previousSource + temp.value);
previousSource += temp.value;
str = temp.rest;
- if (str.length === 0 || mappingSeparator.test(str.charAt(0))) {
+ if (str.length === 0 || this._nextCharIsMappingSeparator(str)) {
throw new Error('Found a source, but no line and column');
}
// Original line.
- temp = base64VLQ.decode(str);
+ base64VLQ.decode(str, temp);
mapping.originalLine = previousOriginalLine + temp.value;
previousOriginalLine = mapping.originalLine;
// Lines are stored 0-based
mapping.originalLine += 1;
str = temp.rest;
- if (str.length === 0 || mappingSeparator.test(str.charAt(0))) {
+ if (str.length === 0 || this._nextCharIsMappingSeparator(str)) {
throw new Error('Found a source and line, but no column');
}
// Original column.
- temp = base64VLQ.decode(str);
+ base64VLQ.decode(str, temp);
mapping.originalColumn = previousOriginalColumn + temp.value;
previousOriginalColumn = mapping.originalColumn;
str = temp.rest;
- if (str.length > 0 && !mappingSeparator.test(str.charAt(0))) {
+ if (str.length > 0 && !this._nextCharIsMappingSeparator(str)) {
// Original name.
- temp = base64VLQ.decode(str);
+ base64VLQ.decode(str, temp);
mapping.name = this._names.at(previousName + temp.value);
previousName += temp.value;
str = temp.rest;
@@ -315,7 +320,7 @@ define(function (require, exports, module) {
if (mapping && mapping.generatedLine === needle.generatedLine) {
var source = util.getArg(mapping, 'source', null);
- if (source && this.sourceRoot) {
+ if (source != null && this.sourceRoot != null) {
source = util.join(this.sourceRoot, source);
}
return {
@@ -345,7 +350,7 @@ define(function (require, exports, module) {
return null;
}
- if (this.sourceRoot) {
+ if (this.sourceRoot != null) {
aSource = util.relative(this.sourceRoot, aSource);
}
@@ -354,7 +359,7 @@ define(function (require, exports, module) {
}
var url;
- if (this.sourceRoot
+ if (this.sourceRoot != null
&& (url = util.urlParse(this.sourceRoot))) {
// XXX: file:// URIs and absolute paths lead to unexpected behavior for
// many users. We can help them out when they expect file:// URIs to
@@ -397,7 +402,7 @@ define(function (require, exports, module) {
originalColumn: util.getArg(aArgs, 'column')
};
- if (this.sourceRoot) {
+ if (this.sourceRoot != null) {
needle.source = util.relative(this.sourceRoot, needle.source);
}
@@ -459,7 +464,7 @@ define(function (require, exports, module) {
var sourceRoot = this.sourceRoot;
mappings.map(function (mapping) {
var source = mapping.source;
- if (source && sourceRoot) {
+ if (source != null && sourceRoot != null) {
source = util.join(sourceRoot, source);
}
return {
diff --git a/lib/source-map/source-map-generator.js b/lib/source-map/source-map-generator.js
index fb6d6c3..5387fa1 100644
--- a/lib/source-map/source-map-generator.js
+++ b/lib/source-map/source-map-generator.js
@@ -55,9 +55,9 @@ define(function (require, exports, module) {
}
};
- if (mapping.source) {
+ if (mapping.source != null) {
newMapping.source = mapping.source;
- if (sourceRoot) {
+ if (sourceRoot != null) {
newMapping.source = util.relative(sourceRoot, newMapping.source);
}
@@ -66,7 +66,7 @@ define(function (require, exports, module) {
column: mapping.originalColumn
};
- if (mapping.name) {
+ if (mapping.name != null) {
newMapping.name = mapping.name;
}
}
@@ -75,7 +75,7 @@ define(function (require, exports, module) {
});
aSourceMapConsumer.sources.forEach(function (sourceFile) {
var content = aSourceMapConsumer.sourceContentFor(sourceFile);
- if (content) {
+ if (content != null) {
generator.setSourceContent(sourceFile, content);
}
});
@@ -101,11 +101,11 @@ define(function (require, exports, module) {
this._validateMapping(generated, original, source, name);
- if (source && !this._sources.has(source)) {
+ if (source != null && !this._sources.has(source)) {
this._sources.add(source);
}
- if (name && !this._names.has(name)) {
+ if (name != null && !this._names.has(name)) {
this._names.add(name);
}
@@ -125,18 +125,18 @@ define(function (require, exports, module) {
SourceMapGenerator.prototype.setSourceContent =
function SourceMapGenerator_setSourceContent(aSourceFile, aSourceContent) {
var source = aSourceFile;
- if (this._sourceRoot) {
+ if (this._sourceRoot != null) {
source = util.relative(this._sourceRoot, source);
}
- if (aSourceContent !== null) {
+ if (aSourceContent != null) {
// Add the source content to the _sourcesContents map.
// Create a new _sourcesContents map if the property is null.
if (!this._sourcesContents) {
this._sourcesContents = {};
}
this._sourcesContents[util.toSetString(source)] = aSourceContent;
- } else {
+ } else if (this._sourcesContents) {
// Remove the source file from the _sourcesContents map.
// If the _sourcesContents map is empty, set the property to null.
delete this._sourcesContents[util.toSetString(source)];
@@ -164,60 +164,59 @@ define(function (require, exports, module) {
*/
SourceMapGenerator.prototype.applySourceMap =
function SourceMapGenerator_applySourceMap(aSourceMapConsumer, aSourceFile, aSourceMapPath) {
+ var sourceFile = aSourceFile;
// If aSourceFile is omitted, we will use the file property of the SourceMap
- if (!aSourceFile) {
- if (!aSourceMapConsumer.file) {
+ if (aSourceFile == null) {
+ if (aSourceMapConsumer.file == null) {
throw new Error(
'SourceMapGenerator.prototype.applySourceMap requires either an explicit source file, ' +
'or the source map\'s "file" property. Both were omitted.'
);
}
- aSourceFile = aSourceMapConsumer.file;
+ sourceFile = aSourceMapConsumer.file;
}
var sourceRoot = this._sourceRoot;
- // Make "aSourceFile" relative if an absolute Url is passed.
- if (sourceRoot) {
- aSourceFile = util.relative(sourceRoot, aSourceFile);
+ // Make "sourceFile" relative if an absolute Url is passed.
+ if (sourceRoot != null) {
+ sourceFile = util.relative(sourceRoot, sourceFile);
}
// Applying the SourceMap can add and remove items from the sources and
// the names array.
var newSources = new ArraySet();
var newNames = new ArraySet();
- // Find mappings for the "aSourceFile"
+ // Find mappings for the "sourceFile"
this._mappings.forEach(function (mapping) {
- if (mapping.source === aSourceFile && mapping.originalLine) {
+ if (mapping.source === sourceFile && mapping.originalLine != null) {
// Check if it can be mapped by the source map, then update the mapping.
var original = aSourceMapConsumer.originalPositionFor({
line: mapping.originalLine,
column: mapping.originalColumn
});
- if (original.source !== null) {
+ if (original.source != null) {
// Copy mapping
mapping.source = original.source;
- if (aSourceMapPath) {
+ if (aSourceMapPath != null) {
mapping.source = util.join(aSourceMapPath, mapping.source)
}
- if (sourceRoot) {
+ if (sourceRoot != null) {
mapping.source = util.relative(sourceRoot, mapping.source);
}
mapping.originalLine = original.line;
mapping.originalColumn = original.column;
- if (original.name !== null && mapping.name !== null) {
- // Only use the identifier name if it's an identifier
- // in both SourceMaps
+ if (original.name != null) {
mapping.name = original.name;
}
}
}
var source = mapping.source;
- if (source && !newSources.has(source)) {
+ if (source != null && !newSources.has(source)) {
newSources.add(source);
}
var name = mapping.name;
- if (name && !newNames.has(name)) {
+ if (name != null && !newNames.has(name)) {
newNames.add(name);
}
@@ -228,11 +227,11 @@ define(function (require, exports, module) {
// Copy sourcesContents of applied map.
aSourceMapConsumer.sources.forEach(function (sourceFile) {
var content = aSourceMapConsumer.sourceContentFor(sourceFile);
- if (content) {
- if (aSourceMapPath) {
+ if (content != null) {
+ if (aSourceMapPath != null) {
sourceFile = util.join(aSourceMapPath, sourceFile);
}
- if (sourceRoot) {
+ if (sourceRoot != null) {
sourceFile = util.relative(sourceRoot, sourceFile);
}
this.setSourceContent(sourceFile, content);
@@ -323,7 +322,7 @@ define(function (require, exports, module) {
- previousGeneratedColumn);
previousGeneratedColumn = mapping.generatedColumn;
- if (mapping.source) {
+ if (mapping.source != null) {
result += base64VLQ.encode(this._sources.indexOf(mapping.source)
- previousSource);
previousSource = this._sources.indexOf(mapping.source);
@@ -337,7 +336,7 @@ define(function (require, exports, module) {
- previousOriginalColumn);
previousOriginalColumn = mapping.originalColumn;
- if (mapping.name) {
+ if (mapping.name != null) {
result += base64VLQ.encode(this._names.indexOf(mapping.name)
- previousName);
previousName = this._names.indexOf(mapping.name);
@@ -354,7 +353,7 @@ define(function (require, exports, module) {
if (!this._sourcesContents) {
return null;
}
- if (aSourceRoot) {
+ if (aSourceRoot != null) {
source = util.relative(aSourceRoot, source);
}
var key = util.toSetString(source);
@@ -372,12 +371,14 @@ define(function (require, exports, module) {
function SourceMapGenerator_toJSON() {
var map = {
version: this._version,
- file: this._file,
sources: this._sources.toArray(),
names: this._names.toArray(),
mappings: this._serializeMappings()
};
- if (this._sourceRoot) {
+ if (this._file != null) {
+ map.file = this._file;
+ }
+ if (this._sourceRoot != null) {
map.sourceRoot = this._sourceRoot;
}
if (this._sourcesContents) {
diff --git a/lib/source-map/source-node.js b/lib/source-map/source-node.js
index 66a2ebc..baa5f40 100644
--- a/lib/source-map/source-node.js
+++ b/lib/source-map/source-node.js
@@ -14,7 +14,7 @@ define(function (require, exports, module) {
// Matches a Windows-style `\r\n` newline or a `\n` newline used by all other
// operating systems these days (capturing the result).
- var REGEX_NEWLINE = /(\r?\n)/g;
+ var REGEX_NEWLINE = /(\r?\n)/;
// Matches a Windows-style newline, or any character.
var REGEX_CHARACTER = /\r\n|[\s\S]/g;
@@ -34,10 +34,10 @@ define(function (require, exports, module) {
function SourceNode(aLine, aColumn, aSource, aChunks, aName) {
this.children = [];
this.sourceContents = {};
- this.line = aLine === undefined ? null : aLine;
- this.column = aColumn === undefined ? null : aColumn;
- this.source = aSource === undefined ? null : aSource;
- this.name = aName === undefined ? null : aName;
+ this.line = aLine == null ? null : aLine;
+ this.column = aColumn == null ? null : aColumn;
+ this.source = aSource == null ? null : aSource;
+ this.name = aName == null ? null : aName;
if (aChunks != null) this.add(aChunks);
}
@@ -46,9 +46,11 @@ define(function (require, exports, module) {
*
* @param aGeneratedCode The generated code
* @param aSourceMapConsumer The SourceMap for the generated code
+ * @param aRelativePath Optional. The path that relative sources in the
+ * SourceMapConsumer should be relative to.
*/
SourceNode.fromStringWithSourceMap =
- function SourceNode_fromStringWithSourceMap(aGeneratedCode, aSourceMapConsumer) {
+ function SourceNode_fromStringWithSourceMap(aGeneratedCode, aSourceMapConsumer, aRelativePath) {
// The SourceNode we want to fill with the generated code
// and the SourceMap
var node = new SourceNode();
@@ -128,7 +130,10 @@ define(function (require, exports, module) {
// Copy sourcesContent into SourceNode
aSourceMapConsumer.sources.forEach(function (sourceFile) {
var content = aSourceMapConsumer.sourceContentFor(sourceFile);
- if (content) {
+ if (content != null) {
+ if (aRelativePath != null) {
+ sourceFile = util.join(aRelativePath, sourceFile);
+ }
node.setSourceContent(sourceFile, content);
}
});
@@ -139,9 +144,12 @@ define(function (require, exports, module) {
if (mapping === null || mapping.source === undefined) {
node.add(code);
} else {
+ var source = aRelativePath
+ ? util.join(aRelativePath, mapping.source)
+ : mapping.source;
node.add(new SourceNode(mapping.originalLine,
mapping.originalColumn,
- mapping.source,
+ source,
code,
mapping.name));
}
diff --git a/lib/source-map/util.js b/lib/source-map/util.js
index 4316445..976f6ca 100644
--- a/lib/source-map/util.js
+++ b/lib/source-map/util.js
@@ -143,6 +143,12 @@ define(function (require, exports, module) {
* - Joining for example 'http://' and 'www.example.com' is also supported.
*/
function join(aRoot, aPath) {
+ if (aRoot === "") {
+ aRoot = ".";
+ }
+ if (aPath === "") {
+ aPath = ".";
+ }
var aPathUrl = urlParse(aPath);
var aRootUrl = urlParse(aRoot);
if (aRootUrl) {
@@ -180,6 +186,31 @@ define(function (require, exports, module) {
exports.join = join;
/**
+ * Make a path relative to a URL or another path.
+ *
+ * @param aRoot The root path or URL.
+ * @param aPath The path or URL to be made relative to aRoot.
+ */
+ function relative(aRoot, aPath) {
+ if (aRoot === "") {
+ aRoot = ".";
+ }
+
+ aRoot = aRoot.replace(/\/$/, '');
+
+ // XXX: It is possible to remove this block, and the tests still pass!
+ var url = urlParse(aRoot);
+ if (aPath.charAt(0) == "/" && url && url.path == "/") {
+ return aPath.slice(1);
+ }
+
+ return aPath.indexOf(aRoot + '/') === 0
+ ? aPath.substr(aRoot.length + 1)
+ : aPath;
+ }
+ exports.relative = relative;
+
+ /**
* Because behavior goes wacky when you set `__proto__` on objects, we
* have to prefix all the strings in our set with an arbitrary character.
*
@@ -198,20 +229,6 @@ define(function (require, exports, module) {
}
exports.fromSetString = fromSetString;
- function relative(aRoot, aPath) {
- aRoot = aRoot.replace(/\/$/, '');
-
- var url = urlParse(aRoot);
- if (aPath.charAt(0) == "/" && url && url.path == "/") {
- return aPath.slice(1);
- }
-
- return aPath.indexOf(aRoot + '/') === 0
- ? aPath.substr(aRoot.length + 1)
- : aPath;
- }
- exports.relative = relative;
-
function strcmp(aStr1, aStr2) {
var s1 = aStr1 || "";
var s2 = aStr2 || "";
diff --git a/package.json b/package.json
index 423a4e2..f337b45 100644
--- a/package.json
+++ b/package.json
@@ -1,7 +1,7 @@
{
"name": "source-map",
"description": "Generates and consumes source maps",
- "version": "0.1.34",
+ "version": "0.1.40",
"homepage": "https://github.com/mozilla/source-map",
"author": "Nick Fitzgerald <nfitzgerald at mozilla.com>",
"contributors": [
@@ -25,7 +25,11 @@
"David Glasser <glasser at davidglasser.net>",
"Simon Lydell <simon.lydell at gmail.com>",
"Jmeas Smith <jellyes2 at gmail.com>",
- "Michael Z Goddard <mzgoddard at gmail.com>"
+ "Michael Z Goddard <mzgoddard at gmail.com>",
+ "azu <azu at users.noreply.github.com>",
+ "John Gozde <john at gozde.ca>",
+ "Adam Kirkton <akirkton at truefitinnovation.com>",
+ "Chris Montgomery <christopher.montgomery at dowjones.com>"
],
"repository": {
"type": "git",
diff --git a/test/source-map/test-base64-vlq.js b/test/source-map/test-base64-vlq.js
index 653a874..6fd0d99 100644
--- a/test/source-map/test-base64-vlq.js
+++ b/test/source-map/test-base64-vlq.js
@@ -12,10 +12,9 @@ define(function (require, exports, module) {
var base64VLQ = require('../../lib/source-map/base64-vlq');
exports['test normal encoding and decoding'] = function (assert, util) {
- var result;
+ var result = {};
for (var i = -255; i < 256; i++) {
- result = base64VLQ.decode(base64VLQ.encode(i));
- assert.ok(result);
+ base64VLQ.decode(base64VLQ.encode(i), result);
assert.equal(result.value, i);
assert.equal(result.rest, "");
}
diff --git a/test/source-map/test-source-map-consumer.js b/test/source-map/test-source-map-consumer.js
index acd24d5..a4c6659 100644
--- a/test/source-map/test-source-map-consumer.js
+++ b/test/source-map/test-source-map-consumer.js
@@ -22,18 +22,34 @@ define(function (require, exports, module) {
};
exports['test that the `sources` field has the original sources'] = function (assert, util) {
- var map = new SourceMapConsumer(util.testMap);
- var sources = map.sources;
+ var map;
+ var sources;
+ map = new SourceMapConsumer(util.testMap);
+ sources = map.sources;
assert.equal(sources[0], '/the/root/one.js');
assert.equal(sources[1], '/the/root/two.js');
assert.equal(sources.length, 2);
+
+ map = new SourceMapConsumer(util.testMapNoSourceRoot);
+ sources = map.sources;
+ assert.equal(sources[0], 'one.js');
+ assert.equal(sources[1], 'two.js');
+ assert.equal(sources.length, 2);
+
+ map = new SourceMapConsumer(util.testMapEmptySourceRoot);
+ sources = map.sources;
+ assert.equal(sources[0], 'one.js');
+ assert.equal(sources[1], 'two.js');
+ assert.equal(sources.length, 2);
};
exports['test that the source root is reflected in a mapping\'s source field'] = function (assert, util) {
- var map = new SourceMapConsumer(util.testMap);
+ var map;
var mapping;
+ map = new SourceMapConsumer(util.testMap);
+
mapping = map.originalPositionFor({
line: 2,
column: 1
@@ -45,6 +61,36 @@ define(function (require, exports, module) {
column: 1
});
assert.equal(mapping.source, '/the/root/one.js');
+
+
+ map = new SourceMapConsumer(util.testMapNoSourceRoot);
+
+ mapping = map.originalPositionFor({
+ line: 2,
+ column: 1
+ });
+ assert.equal(mapping.source, 'two.js');
+
+ mapping = map.originalPositionFor({
+ line: 1,
+ column: 1
+ });
+ assert.equal(mapping.source, 'one.js');
+
+
+ map = new SourceMapConsumer(util.testMapEmptySourceRoot);
+
+ mapping = map.originalPositionFor({
+ line: 2,
+ column: 1
+ });
+ assert.equal(mapping.source, 'two.js');
+
+ mapping = map.originalPositionFor({
+ line: 1,
+ column: 1
+ });
+ assert.equal(mapping.source, 'one.js');
};
exports['test mapping tokens back exactly'] = function (assert, util) {
@@ -111,15 +157,15 @@ define(function (require, exports, module) {
};
exports['test eachMapping'] = function (assert, util) {
- var map = new SourceMapConsumer(util.testMap);
+ var map;
+
+ map = new SourceMapConsumer(util.testMap);
var previousLine = -Infinity;
var previousColumn = -Infinity;
map.eachMapping(function (mapping) {
assert.ok(mapping.generatedLine >= previousLine);
- if (mapping.source) {
- assert.equal(mapping.source.indexOf(util.testMap.sourceRoot), 0);
- }
+ assert.ok(mapping.source === '/the/root/one.js' || mapping.source === '/the/root/two.js');
if (mapping.generatedLine === previousLine) {
assert.ok(mapping.generatedColumn >= previousColumn);
@@ -130,6 +176,16 @@ define(function (require, exports, module) {
previousColumn = -Infinity;
}
});
+
+ map = new SourceMapConsumer(util.testMapNoSourceRoot);
+ map.eachMapping(function (mapping) {
+ assert.ok(mapping.source === 'one.js' || mapping.source === 'two.js');
+ });
+
+ map = new SourceMapConsumer(util.testMapEmptySourceRoot);
+ map.eachMapping(function (mapping) {
+ assert.ok(mapping.source === 'one.js' || mapping.source === 'two.js');
+ });
};
exports['test iterating over mappings in a different order'] = function (assert, util) {
diff --git a/test/source-map/test-source-map-generator.js b/test/source-map/test-source-map-generator.js
index 227140f..a0d9d00 100644
--- a/test/source-map/test-source-map-generator.js
+++ b/test/source-map/test-source-map-generator.js
@@ -21,8 +21,9 @@ define(function (require, exports, module) {
});
assert.ok(true);
- var map = new SourceMapGenerator();
- assert.ok(true);
+ var map = new SourceMapGenerator().toJSON();
+ assert.ok(!('file' in map));
+ assert.ok(!('sourceRoot' in map));
};
exports['test JSON serialization'] = function (assert, util) {
@@ -180,6 +181,24 @@ define(function (require, exports, module) {
util.assertEqualMaps(assert, map, util.testMap);
};
+ exports['test that adding a mapping with an empty string name does not break generation'] = function (assert, util) {
+ var map = new SourceMapGenerator({
+ file: 'generated-foo.js',
+ sourceRoot: '.'
+ });
+
+ map.addMapping({
+ generated: { line: 1, column: 1 },
+ source: 'bar.js',
+ original: { line: 1, column: 1 },
+ name: ''
+ });
+
+ assert.doesNotThrow(function () {
+ JSON.parse(map.toString());
+ });
+ };
+
exports['test that source content can be set'] = function (assert, util) {
var map = new SourceMapGenerator({
file: 'min.js',
@@ -292,8 +311,8 @@ define(function (require, exports, module) {
// foo.coffee
// temp/
// bundle.js
- // temp_maps/
- // bundle.js.map
+ // temp_maps/
+ // bundle.js.map
// public/
// bundle.min.js
// bundle.min.js.map
@@ -307,9 +326,9 @@ define(function (require, exports, module) {
bundleMap.addMapping({
generated: { line: 3, column: 3 },
original: { line: 2, column: 2 },
- source: '../coffee/foo.coffee'
+ source: '../../coffee/foo.coffee'
});
- bundleMap.setSourceContent('../coffee/foo.coffee', 'foo coffee');
+ bundleMap.setSourceContent('../../coffee/foo.coffee', 'foo coffee');
bundleMap.addMapping({
generated: { line: 13, column: 13 },
original: { line: 12, column: 12 },
@@ -382,23 +401,106 @@ define(function (require, exports, module) {
return map.toJSON();
}
- util.assertEqualMaps(assert, actualMap('../temp_maps'), expectedMap([
+ util.assertEqualMaps(assert, actualMap('../temp/temp_maps'), expectedMap([
'coffee/foo.coffee',
'/bar.coffee',
'http://www.example.com/baz.coffee'
]));
- util.assertEqualMaps(assert, actualMap('/app/temp_maps'), expectedMap([
+ util.assertEqualMaps(assert, actualMap('/app/temp/temp_maps'), expectedMap([
'/app/coffee/foo.coffee',
'/bar.coffee',
'http://www.example.com/baz.coffee'
]));
- util.assertEqualMaps(assert, actualMap('http://foo.org/app/temp_maps'), expectedMap([
+ util.assertEqualMaps(assert, actualMap('http://foo.org/app/temp/temp_maps'), expectedMap([
'http://foo.org/app/coffee/foo.coffee',
'http://foo.org/bar.coffee',
'http://www.example.com/baz.coffee'
]));
+
+ // If the third parameter is omitted or set to the current working
+ // directory we get incorrect source paths:
+
+ util.assertEqualMaps(assert, actualMap(), expectedMap([
+ '../coffee/foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee'
+ ]));
+
+ util.assertEqualMaps(assert, actualMap(''), expectedMap([
+ '../coffee/foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee'
+ ]));
+
+ util.assertEqualMaps(assert, actualMap('.'), expectedMap([
+ '../coffee/foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee'
+ ]));
+
+ util.assertEqualMaps(assert, actualMap('./'), expectedMap([
+ '../coffee/foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee'
+ ]));
+ };
+
+ exports['test applySourceMap name handling'] = function (assert, util) {
+ // Imagine some CoffeeScript code being compiled into JavaScript and then
+ // minified.
+
+ var assertName = function(coffeeName, jsName, expectedName) {
+ var minifiedMap = new SourceMapGenerator({
+ file: 'test.js.min'
+ });
+ minifiedMap.addMapping({
+ generated: { line: 1, column: 4 },
+ original: { line: 1, column: 4 },
+ source: 'test.js',
+ name: jsName
+ });
+
+ var coffeeMap = new SourceMapGenerator({
+ file: 'test.js'
+ });
+ coffeeMap.addMapping({
+ generated: { line: 1, column: 4 },
+ original: { line: 1, column: 0 },
+ source: 'test.coffee',
+ name: coffeeName
+ });
+
+ minifiedMap.applySourceMap(new SourceMapConsumer(coffeeMap.toJSON()));
+
+ new SourceMapConsumer(minifiedMap.toJSON()).eachMapping(function(mapping) {
+ assert.equal(mapping.name, expectedName);
+ });
+ };
+
+ // `foo = 1` -> `var foo = 1;` -> `var a=1`
+ // CoffeeScript doesn’t rename variables, so there’s no need for it to
+ // provide names in its source maps. Minifiers do rename variables and
+ // therefore do provide names in their source maps. So that name should be
+ // retained if the original map lacks names.
+ assertName(null, 'foo', 'foo');
+
+ // `foo = 1` -> `var coffee$foo = 1;` -> `var a=1`
+ // Imagine that CoffeeScript prefixed all variables with `coffee$`. Even
+ // though the minifier then also provides a name, the original name is
+ // what corresponds to the source.
+ assertName('foo', 'coffee$foo', 'foo');
+
+ // `foo = 1` -> `var coffee$foo = 1;` -> `var coffee$foo=1`
+ // Minifiers can turn off variable mangling. Then there’s no need to
+ // provide names in the source map, but the names from the original map are
+ // still needed.
+ assertName('foo', null, 'foo');
+
+ // `foo = 1` -> `var foo = 1;` -> `var foo=1`
+ // No renaming at all.
+ assertName(null, null, null);
};
exports['test sorting with duplicate generated mappings'] = function (assert, util) {
@@ -546,4 +648,11 @@ define(function (require, exports, module) {
});
};
+ exports['test setting sourcesContent to null when already null'] = function (assert, util) {
+ var smg = new SourceMapGenerator({ file: "foo.js" });
+ assert.doesNotThrow(function() {
+ smg.setSourceContent("bar.js", null);
+ });
+ };
+
});
diff --git a/test/source-map/test-source-node.js b/test/source-map/test-source-node.js
index d186521..139af4e 100644
--- a/test/source-map/test-source-node.js
+++ b/test/source-map/test-source-node.js
@@ -159,6 +159,7 @@ define(function (require, exports, module) {
assert.ok(map instanceof SourceMapGenerator, 'map instanceof SourceMapGenerator');
assert.ok(mapWithoutOptions instanceof SourceMapGenerator, 'mapWithoutOptions instanceof SourceMapGenerator');
+ assert.ok(!('file' in mapWithoutOptions));
mapWithoutOptions._file = 'foo.js';
util.assertEqualMaps(assert, map.toJSON(), mapWithoutOptions.toJSON());
@@ -276,6 +277,94 @@ define(function (require, exports, module) {
util.assertEqualMaps(assert, map, inputMap);
});
+ exports['test .fromStringWithSourceMap() third argument'] = function (assert, util) {
+ // Assume the following directory structure:
+ //
+ // http://foo.org/
+ // bar.coffee
+ // app/
+ // coffee/
+ // foo.coffee
+ // coffeeBundle.js # Made from {foo,bar,baz}.coffee
+ // maps/
+ // coffeeBundle.js.map
+ // js/
+ // foo.js
+ // public/
+ // app.js # Made from {foo,coffeeBundle}.js
+ // app.js.map
+ //
+ // http://www.example.com/
+ // baz.coffee
+
+ var coffeeBundle = new SourceNode(1, 0, 'foo.coffee', 'foo(coffee);\n');
+ coffeeBundle.setSourceContent('foo.coffee', 'foo coffee');
+ coffeeBundle.add(new SourceNode(2, 0, '/bar.coffee', 'bar(coffee);\n'));
+ coffeeBundle.add(new SourceNode(3, 0, 'http://www.example.com/baz.coffee', 'baz(coffee);'));
+ coffeeBundle = coffeeBundle.toStringWithSourceMap({
+ file: 'foo.js',
+ sourceRoot: '..'
+ });
+
+ var foo = new SourceNode(1, 0, 'foo.js', 'foo(js);');
+
+ var test = function(relativePath, expectedSources) {
+ var app = new SourceNode();
+ app.add(SourceNode.fromStringWithSourceMap(
+ coffeeBundle.code,
+ new SourceMapConsumer(coffeeBundle.map.toString()),
+ relativePath));
+ app.add(foo);
+ var i = 0;
+ app.walk(function (chunk, loc) {
+ assert.equal(loc.source, expectedSources[i]);
+ i++;
+ });
+ app.walkSourceContents(function (sourceFile, sourceContent) {
+ assert.equal(sourceFile, expectedSources[0]);
+ assert.equal(sourceContent, 'foo coffee');
+ })
+ };
+
+ test('../coffee/maps', [
+ '../coffee/foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee',
+ 'foo.js'
+ ]);
+
+ // If the third parameter is omitted or set to the current working
+ // directory we get incorrect source paths:
+
+ test(undefined, [
+ '../foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee',
+ 'foo.js'
+ ]);
+
+ test('', [
+ '../foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee',
+ 'foo.js'
+ ]);
+
+ test('.', [
+ '../foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee',
+ 'foo.js'
+ ]);
+
+ test('./', [
+ '../foo.coffee',
+ '/bar.coffee',
+ 'http://www.example.com/baz.coffee',
+ 'foo.js'
+ ]);
+ };
+
exports['test .toStringWithSourceMap() merging duplicate mappings'] = forEachNewline(function (assert, util, nl) {
var input = new SourceNode(null, null, null, [
new SourceNode(1, 0, "a.js", "(function"),
@@ -441,6 +530,42 @@ define(function (require, exports, module) {
assert.equal(result.code, '');
};
+ exports['test .toStringWithSourceMap() with consecutive newlines'] = forEachNewline(function (assert, util, nl) {
+ var input = new SourceNode(null, null, null, [
+ "/***/" + nl + nl,
+ new SourceNode(1, 0, "a.js", "'use strict';" + nl),
+ new SourceNode(2, 0, "a.js", "a();"),
+ ]);
+ input = input.toStringWithSourceMap({
+ file: 'foo.js'
+ });
+
+ assert.equal(input.code, [
+ "/***/",
+ "",
+ "'use strict';",
+ "a();",
+ ].join(nl));
+
+ var correctMap = new SourceMapGenerator({
+ file: 'foo.js'
+ });
+ correctMap.addMapping({
+ generated: { line: 3, column: 0 },
+ source: 'a.js',
+ original: { line: 1, column: 0 }
+ });
+ correctMap.addMapping({
+ generated: { line: 4, column: 0 },
+ source: 'a.js',
+ original: { line: 2, column: 0 }
+ });
+
+ var inputMap = input.map.toJSON();
+ correctMap = correctMap.toJSON();
+ util.assertEqualMaps(assert, inputMap, correctMap);
+ });
+
exports['test setSourceContent with toStringWithSourceMap'] = function (assert, util) {
var aNode = new SourceNode(1, 1, 'a.js', 'a');
aNode.setSourceContent('a.js', 'someContent');
diff --git a/test/source-map/test-util.js b/test/source-map/test-util.js
index 22e9a9e..997d1a2 100644
--- a/test/source-map/test-util.js
+++ b/test/source-map/test-util.js
@@ -28,7 +28,14 @@ define(function (require, exports, module) {
assertUrl('//www.example.com');
assertUrl('file:///www.example.com');
+ assert.equal(libUtil.urlParse(''), null);
+ assert.equal(libUtil.urlParse('.'), null);
+ assert.equal(libUtil.urlParse('..'), null);
+ assert.equal(libUtil.urlParse('a'), null);
+ assert.equal(libUtil.urlParse('a/b'), null);
assert.equal(libUtil.urlParse('a//b'), null);
+ assert.equal(libUtil.urlParse('/a'), null);
+ assert.equal(libUtil.urlParse('data:foo,bar'), null);
};
exports['test normalize()'] = function (assert, util) {
@@ -50,6 +57,7 @@ define(function (require, exports, module) {
assert.equal(libUtil.normalize('/././././a/b/c'), '/a/b/c');
assert.equal(libUtil.normalize('/a/b/c/./././d/././e'), '/a/b/c/d/e');
+ assert.equal(libUtil.normalize(''), '.');
assert.equal(libUtil.normalize('.'), '.');
assert.equal(libUtil.normalize('./'), '.');
assert.equal(libUtil.normalize('././a'), 'a');
@@ -88,6 +96,73 @@ define(function (require, exports, module) {
assert.equal(libUtil.join('a', 'data:foo,bar'), 'data:foo,bar');
+ assert.equal(libUtil.join('', 'b'), 'b');
+ assert.equal(libUtil.join('.', 'b'), 'b');
+ assert.equal(libUtil.join('', 'b/'), 'b/');
+ assert.equal(libUtil.join('.', 'b/'), 'b/');
+ assert.equal(libUtil.join('', 'b//'), 'b/');
+ assert.equal(libUtil.join('.', 'b//'), 'b/');
+
+ assert.equal(libUtil.join('', '..'), '..');
+ assert.equal(libUtil.join('.', '..'), '..');
+ assert.equal(libUtil.join('', '../b'), '../b');
+ assert.equal(libUtil.join('.', '../b'), '../b');
+
+ assert.equal(libUtil.join('', '.'), '.');
+ assert.equal(libUtil.join('.', '.'), '.');
+ assert.equal(libUtil.join('', './b'), 'b');
+ assert.equal(libUtil.join('.', './b'), 'b');
+
+ assert.equal(libUtil.join('', 'http://www.example.com'), 'http://www.example.com');
+ assert.equal(libUtil.join('.', 'http://www.example.com'), 'http://www.example.com');
+ assert.equal(libUtil.join('', 'data:foo,bar'), 'data:foo,bar');
+ assert.equal(libUtil.join('.', 'data:foo,bar'), 'data:foo,bar');
+
+
+ assert.equal(libUtil.join('..', 'b'), '../b');
+ assert.equal(libUtil.join('..', 'b/'), '../b/');
+ assert.equal(libUtil.join('..', 'b//'), '../b/');
+
+ assert.equal(libUtil.join('..', '..'), '../..');
+ assert.equal(libUtil.join('..', '../b'), '../../b');
+
+ assert.equal(libUtil.join('..', '.'), '..');
+ assert.equal(libUtil.join('..', './b'), '../b');
+
+ assert.equal(libUtil.join('..', 'http://www.example.com'), 'http://www.example.com');
+ assert.equal(libUtil.join('..', 'data:foo,bar'), 'data:foo,bar');
+
+
+ assert.equal(libUtil.join('a', ''), 'a');
+ assert.equal(libUtil.join('a', '.'), 'a');
+ assert.equal(libUtil.join('a/', ''), 'a');
+ assert.equal(libUtil.join('a/', '.'), 'a');
+ assert.equal(libUtil.join('a//', ''), 'a');
+ assert.equal(libUtil.join('a//', '.'), 'a');
+ assert.equal(libUtil.join('/a', ''), '/a');
+ assert.equal(libUtil.join('/a', '.'), '/a');
+ assert.equal(libUtil.join('', ''), '.');
+ assert.equal(libUtil.join('.', ''), '.');
+ assert.equal(libUtil.join('.', ''), '.');
+ assert.equal(libUtil.join('.', '.'), '.');
+ assert.equal(libUtil.join('..', ''), '..');
+ assert.equal(libUtil.join('..', '.'), '..');
+ assert.equal(libUtil.join('http://foo.org/a', ''), 'http://foo.org/a');
+ assert.equal(libUtil.join('http://foo.org/a', '.'), 'http://foo.org/a');
+ assert.equal(libUtil.join('http://foo.org/a/', ''), 'http://foo.org/a');
+ assert.equal(libUtil.join('http://foo.org/a/', '.'), 'http://foo.org/a');
+ assert.equal(libUtil.join('http://foo.org/a//', ''), 'http://foo.org/a');
+ assert.equal(libUtil.join('http://foo.org/a//', '.'), 'http://foo.org/a');
+ assert.equal(libUtil.join('http://foo.org', ''), 'http://foo.org/');
+ assert.equal(libUtil.join('http://foo.org', '.'), 'http://foo.org/');
+ assert.equal(libUtil.join('http://foo.org/', ''), 'http://foo.org/');
+ assert.equal(libUtil.join('http://foo.org/', '.'), 'http://foo.org/');
+ assert.equal(libUtil.join('http://foo.org//', ''), 'http://foo.org/');
+ assert.equal(libUtil.join('http://foo.org//', '.'), 'http://foo.org/');
+ assert.equal(libUtil.join('//www.example.com', ''), '//www.example.com/');
+ assert.equal(libUtil.join('//www.example.com', '.'), '//www.example.com/');
+
+
assert.equal(libUtil.join('http://foo.org/a', 'b'), 'http://foo.org/a/b');
assert.equal(libUtil.join('http://foo.org/a/', 'b'), 'http://foo.org/a/b');
assert.equal(libUtil.join('http://foo.org/a//', 'b'), 'http://foo.org/a/b');
@@ -124,4 +199,18 @@ define(function (require, exports, module) {
assert.equal(libUtil.join('//www.example.com', '//foo.org/bar'), '//foo.org/bar');
};
+ // TODO Issue #128: Define and test this function properly.
+ exports['test relative()'] = function (assert, util) {
+ assert.equal(libUtil.relative('/the/root', '/the/root/one.js'), 'one.js');
+ assert.equal(libUtil.relative('/the/root', '/the/rootone.js'), '/the/rootone.js');
+
+ assert.equal(libUtil.relative('', '/the/root/one.js'), '/the/root/one.js');
+ assert.equal(libUtil.relative('.', '/the/root/one.js'), '/the/root/one.js');
+ assert.equal(libUtil.relative('', 'the/root/one.js'), 'the/root/one.js');
+ assert.equal(libUtil.relative('.', 'the/root/one.js'), 'the/root/one.js');
+
+ assert.equal(libUtil.relative('/', '/the/root/one.js'), 'the/root/one.js');
+ assert.equal(libUtil.relative('/', 'the/root/one.js'), 'the/root/one.js');
+ };
+
});
diff --git a/test/source-map/util.js b/test/source-map/util.js
index 288046b..fa213ce 100644
--- a/test/source-map/util.js
+++ b/test/source-map/util.js
@@ -40,6 +40,21 @@ define(function (require, exports, module) {
sourceRoot: '/the/root',
mappings: 'CAAC,IAAI,IAAM,SAAUA,GAClB,OAAOC,IAAID;CCDb,IAAI,IAAM,SAAUE,GAClB,OAAOA'
};
+ exports.testMapNoSourceRoot = {
+ version: 3,
+ file: 'min.js',
+ names: ['bar', 'baz', 'n'],
+ sources: ['one.js', 'two.js'],
+ mappings: 'CAAC,IAAI,IAAM,SAAUA,GAClB,OAAOC,IAAID;CCDb,IAAI,IAAM,SAAUE,GAClB,OAAOA'
+ };
+ exports.testMapEmptySourceRoot = {
+ version: 3,
+ file: 'min.js',
+ names: ['bar', 'baz', 'n'],
+ sources: ['one.js', 'two.js'],
+ sourceRoot: '',
+ mappings: 'CAAC,IAAI,IAAM,SAAUA,GAClB,OAAOC,IAAID;CCDb,IAAI,IAAM,SAAUE,GAClB,OAAOA'
+ };
exports.testMapWithSourcesContent = {
version: 3,
file: 'min.js',
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-javascript/node-source-map.git
More information about the Pkg-javascript-commits
mailing list