2025-04-02 06:50:39 -04:00

99 lines
2.3 KiB
JavaScript

'use strict';
const sourceMapGenerator_js = require('source-map-js/lib/source-map-generator.js');
const trackNodes = new Set(['Atrule', 'Selector', 'Declaration']);
function generateSourceMap(handlers) {
const map = new sourceMapGenerator_js.SourceMapGenerator();
const generated = {
line: 1,
column: 0,
};
const original = {
line: 0, // should be zero to add first mapping
column: 0,
};
const activatedGenerated = {
line: 1,
column: 0,
};
const activatedMapping = {
generated: activatedGenerated,
};
let line = 1;
let column = 0;
let sourceMappingActive = false;
const origHandlersNode = handlers.node;
handlers.node = function (node) {
if (node.loc && node.loc.start && trackNodes.has(node.type)) {
const nodeLine = node.loc.start.line;
const nodeColumn = node.loc.start.column - 1;
if (original.line !== nodeLine || original.column !== nodeColumn) {
original.line = nodeLine;
original.column = nodeColumn;
generated.line = line;
generated.column = column;
if (sourceMappingActive) {
sourceMappingActive = false;
if (
generated.line !== activatedGenerated.line ||
generated.column !== activatedGenerated.column
) {
map.addMapping(activatedMapping);
}
}
sourceMappingActive = true;
map.addMapping({
source: node.loc.source,
original,
generated,
});
}
}
origHandlersNode.call(this, node);
if (sourceMappingActive && trackNodes.has(node.type)) {
activatedGenerated.line = line;
activatedGenerated.column = column;
}
};
const origHandlersEmit = handlers.emit;
handlers.emit = function (value, type, auto) {
for (let i = 0; i < value.length; i++) {
if (value.charCodeAt(i) === 10) {
// \n
line++;
column = 0;
} else {
column++;
}
}
origHandlersEmit(value, type, auto);
};
const origHandlersResult = handlers.result;
handlers.result = function () {
if (sourceMappingActive) {
map.addMapping(activatedMapping);
}
return {
css: origHandlersResult(),
map,
};
};
return handlers;
}
exports.generateSourceMap = generateSourceMap;