Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Download
80552 views
1
'use strict';
2
var SourceMapGenerator = require('source-map').SourceMapGenerator;
3
4
function offsetMapping(mapping, offset) {
5
return { line: offset.line + mapping.line, column: offset.column + mapping.column };
6
}
7
8
function newlinesIn(src) {
9
if (!src) return 0;
10
var newlines = src.match(/\n/g);
11
12
return newlines ? newlines.length : 0;
13
}
14
15
function Generator(opts) {
16
opts = opts || {};
17
this.generator = new SourceMapGenerator({ file: opts.file || '', sourceRoot: opts.sourceRoot || '' });
18
this.sourcesContent = undefined;
19
this.opts = opts;
20
}
21
22
/**
23
* Adds the given mappings to the generator and offsets them if offset is given
24
*
25
* @name addMappings
26
* @function
27
* @param sourceFile {String} name of the source file
28
* @param mappings {Array{{Object}} each object has the form { original: { line: _, column: _ }, generated: { line: _, column: _ } }
29
* @param offset {Object} offset to apply to each mapping. Has the form { line: _, column: _ }
30
* @return {Object} the generator to allow chaining
31
*/
32
Generator.prototype.addMappings = function (sourceFile, mappings, offset) {
33
var generator = this.generator;
34
35
offset = offset || {};
36
offset.line = offset.hasOwnProperty('line') ? offset.line : 0;
37
offset.column = offset.hasOwnProperty('column') ? offset.column : 0;
38
39
mappings.forEach(function (m) {
40
// only set source if we have original position to handle edgecase (see inline-source-map tests)
41
generator.addMapping({
42
source : m.original ? sourceFile : undefined
43
, original : m.original
44
, generated : offsetMapping(m.generated, offset)
45
});
46
});
47
return this;
48
};
49
50
/**
51
* Generates mappings for the given source, assuming that no translation from original to generated is necessary.
52
*
53
* @name addGeneratedMappings
54
* @function
55
* @param sourceFile {String} name of the source file
56
* @param source {String} source of the file
57
* @param offset {Object} offset to apply to each mapping. Has the form { line: _, column: _ }
58
* @return {Object} the generator to allow chaining
59
*/
60
Generator.prototype.addGeneratedMappings = function (sourceFile, source, offset) {
61
var mappings = []
62
, linesToGenerate = newlinesIn(source) + 1;
63
64
for (var line = 1; line <= linesToGenerate; line++) {
65
var location = { line: line, column: 0 };
66
mappings.push({ original: location, generated: location });
67
}
68
69
return this.addMappings(sourceFile, mappings, offset);
70
};
71
72
/**
73
* Adds source content for the given source file.
74
*
75
* @name addSourceContent
76
* @function
77
* @param sourceFile {String} The source file for which a mapping is included
78
* @param sourcesContent {String} The content of the source file
79
* @return {Object} The generator to allow chaining
80
*/
81
Generator.prototype.addSourceContent = function (sourceFile, sourcesContent) {
82
this.sourcesContent = this.sourcesContent || {};
83
this.sourcesContent[sourceFile] = sourcesContent;
84
return this;
85
};
86
87
/**
88
* @name base64Encode
89
* @function
90
* @return {String} bas64 encoded representation of the added mappings
91
*/
92
Generator.prototype.base64Encode = function () {
93
var map = this.toString();
94
return new Buffer(map).toString('base64');
95
};
96
97
/**
98
* @name inlineMappingUrl
99
* @function
100
* @return {String} comment with base64 encoded representation of the added mappings. Can be inlined at the end of the generated file.
101
*/
102
Generator.prototype.inlineMappingUrl = function () {
103
var charset = this.opts.charset || 'utf-8';
104
return '//# sourceMappingURL=data:application/json;charset:' + charset + ';base64,' + this.base64Encode();
105
};
106
107
Generator.prototype.toJSON = function () {
108
var map = this.generator.toJSON();
109
if (!this.sourcesContent) return map;
110
111
var toSourcesContent = (function (s) { return this.sourcesContent[s] || null; }).bind(this);
112
map.sourcesContent = map.sources.map(toSourcesContent);
113
return map;
114
};
115
116
Generator.prototype.toString = function () {
117
return JSON.stringify(this);
118
};
119
120
Generator.prototype._mappings = function () {
121
return this.generator._mappings._array;
122
};
123
124
Generator.prototype.gen = function () {
125
return this.generator;
126
};
127
128
module.exports = function (opts) { return new Generator(opts); };
129
module.exports.Generator = Generator;
130
131