description and source-codefunction parse(source, options) {
options = normalizeOptions(options);
var lines = fromString(source, options);
var sourceWithoutTabs = lines.toString({
tabWidth: options.tabWidth,
reuseWhitespace: false,
useTabs: false
});
var comments = [];
var program = options.parser.parse(sourceWithoutTabs, {
jsx: true,
loc: true,
locations: true,
range: options.range,
comment: true,
onComment: comments,
tolerant: options.tolerant,
ecmaVersion: 6,
sourceType: 'module'
});
// If the source was empty, some parsers give loc.{start,end}.line
// values of 0, instead of the minimum of 1.
util.fixFaultyLocations(program, lines);
program.loc = program.loc || {
start: lines.firstPos(),
end: lines.lastPos()
};
program.loc.lines = lines;
program.loc.indent = 0;
// Expand the Program node's .loc to include all comments, since
// typically its .loc.start and .loc.end will coincide with those of the
// first and last statements, respectively, excluding any comments that
// fall outside that region.
var trueProgramLoc = util.getTrueLoc(program, lines);
program.loc.start = trueProgramLoc.start;
program.loc.end = trueProgramLoc.end;
if (program.comments) {
comments = program.comments;
delete program.comments;
}
// In order to ensure we reprint leading and trailing program comments,
// wrap the original Program node with a File node.
var file = program;
if (file.type === "Program") {
var file = b.file(program, options.sourceFileName || null);
file.loc = {
lines: lines,
indent: 0,
start: lines.firstPos(),
end: lines.lastPos()
};
} else if (file.type === "File") {
program = file.program;
}
// Passing file.program here instead of just file means that initial
// comments will be attached to program.body[0] instead of program.
attachComments(
comments,
program.body.length ? file.program : file,
lines
);
// Return a copy of the original AST so that any changes made may be
// compared to the original.
return new TreeCopier(lines).copy(file);
}