187 lines
5.2 KiB
JavaScript
187 lines
5.2 KiB
JavaScript
|
/*!
|
||
|
* strip-comments <https://github.com/jonschlinkert/strip-comments>
|
||
|
*
|
||
|
* Copyright (c) 2014-2016, 2018, Jon Schlinkert.
|
||
|
* Released under the MIT License.
|
||
|
*/
|
||
|
|
||
|
'use strict';
|
||
|
|
||
|
const assign = Object.assign;
|
||
|
const extract = require('babel-extract-comments');
|
||
|
|
||
|
/**
|
||
|
* Strip all code comments from the given `input`, including protected
|
||
|
* comments that start with `!`, unless disabled by setting `options.keepProtected`
|
||
|
* to true.
|
||
|
*
|
||
|
* ```js
|
||
|
* const str = strip('const foo = "bar";// this is a comment\n /* me too *\/');
|
||
|
* console.log(str);
|
||
|
* // => 'const foo = "bar";'
|
||
|
* ```
|
||
|
* @name strip
|
||
|
* @param {String} `input` string from which to strip comments
|
||
|
* @param {Object} `options` optional options, passed to [extract-comments][extract-comments]
|
||
|
* @option {Boolean} [options] `line` if `false` strip only block comments, default `true`
|
||
|
* @option {Boolean} [options] `block` if `false` strip only line comments, default `true`
|
||
|
* @option {Boolean} [options] `keepProtected` Keep ignored comments (e.g. `/*!` and `//!`)
|
||
|
* @option {Boolean} [options] `preserveNewlines` Preserve newlines after comments are stripped
|
||
|
* @return {String} modified input
|
||
|
* @api public
|
||
|
*/
|
||
|
|
||
|
function strip(input, options) {
|
||
|
return stripComments(input, assign({ block: true, line: true }, options));
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* Strip only block comments.
|
||
|
*
|
||
|
* ```js
|
||
|
* const strip = require('..');
|
||
|
* const str = strip.block('const foo = "bar";// this is a comment\n /* me too *\/');
|
||
|
* console.log(str);
|
||
|
* // => 'const foo = "bar";// this is a comment'
|
||
|
* ```
|
||
|
* @name .block
|
||
|
* @param {String} `input` string from which to strip comments
|
||
|
* @param {Object} `options` pass `opts.keepProtected: true` to keep ignored comments (e.g. `/*!`)
|
||
|
* @return {String} modified string
|
||
|
* @api public
|
||
|
*/
|
||
|
|
||
|
strip.block = function(input, options) {
|
||
|
return stripComments(input, assign({ block: true }, options));
|
||
|
};
|
||
|
|
||
|
/**
|
||
|
* Strip only line comments.
|
||
|
*
|
||
|
* ```js
|
||
|
* const str = strip.line('const foo = "bar";// this is a comment\n /* me too *\/');
|
||
|
* console.log(str);
|
||
|
* // => 'const foo = "bar";\n/* me too *\/'
|
||
|
* ```
|
||
|
* @name .line
|
||
|
* @param {String} `input` string from which to strip comments
|
||
|
* @param {Object} `options` pass `opts.keepProtected: true` to keep ignored comments (e.g. `//!`)
|
||
|
* @return {String} modified string
|
||
|
* @api public
|
||
|
*/
|
||
|
|
||
|
strip.line = function(input, options) {
|
||
|
return stripComments(input, assign({ line: true }, options));
|
||
|
};
|
||
|
|
||
|
/**
|
||
|
* Strip the first comment from the given `input`. Or, if `opts.keepProtected` is true,
|
||
|
* the first non-protected comment will be stripped.
|
||
|
*
|
||
|
* ```js
|
||
|
* const output = strip.first(input, { keepProtected: true });
|
||
|
* console.log(output);
|
||
|
* // => '//! first comment\nfoo; '
|
||
|
* ```
|
||
|
* @name .first
|
||
|
* @param {String} `input`
|
||
|
* @param {Object} `options` pass `opts.keepProtected: true` to keep comments with `!`
|
||
|
* @return {String}
|
||
|
* @api public
|
||
|
*/
|
||
|
|
||
|
strip.first = function(input, options) {
|
||
|
const opts = assign({ block: true, line: true, first: true }, options);
|
||
|
return stripComments(input, opts);
|
||
|
};
|
||
|
|
||
|
/**
|
||
|
* Strip comments
|
||
|
*/
|
||
|
|
||
|
function stripComments(input, options) {
|
||
|
if (typeof input !== 'string') {
|
||
|
throw new TypeError('expected a string');
|
||
|
}
|
||
|
|
||
|
// strip all by default, including `ingored` comments.
|
||
|
const defaults = {
|
||
|
// we shouldn't care about this here since our goal is to strip comments,
|
||
|
// not transpiling, and this has been a common cause of parsing issues
|
||
|
allowReturnOutsideFunction: true,
|
||
|
block: false,
|
||
|
line: false,
|
||
|
safe: false,
|
||
|
first: false,
|
||
|
plugins: []
|
||
|
};
|
||
|
|
||
|
const opts = assign({}, defaults, options);
|
||
|
opts.plugins.push('objectRestSpread');
|
||
|
|
||
|
if (typeof opts.keepProtected !== 'boolean') {
|
||
|
opts.keepProtected = opts.safe;
|
||
|
}
|
||
|
|
||
|
try {
|
||
|
const comments = extract(input, opts);
|
||
|
let pos = { start: 0, end: 0, removed: 0 };
|
||
|
if (!comments) return input;
|
||
|
|
||
|
for (const comment of comments) {
|
||
|
if (typeof opts.filter === 'function' && opts.filter(comment, opts) === false) {
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
input = remove(input, comment, opts, pos);
|
||
|
|
||
|
if (opts.first === true && !isProtected(comment, opts)) {
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
} catch (err) {
|
||
|
if (options.silent !== true) {
|
||
|
throw err;
|
||
|
}
|
||
|
}
|
||
|
return input;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* Remove a single comment from the given string.
|
||
|
*/
|
||
|
|
||
|
function remove(str, comment, options, pos) {
|
||
|
let nl = '';
|
||
|
|
||
|
if (isProtected(comment, options)) {
|
||
|
return str;
|
||
|
}
|
||
|
|
||
|
if (options && options.preserveNewlines) {
|
||
|
nl = comment.value.replace(/[^\r\n]/g, '');
|
||
|
}
|
||
|
|
||
|
if (comment.type === 'CommentLine' && options.line === true) {
|
||
|
const before = str.slice(0, comment.start - pos.removed);
|
||
|
const after = str.slice(comment.end - pos.removed);
|
||
|
pos.removed += comment.end - comment.start - nl.length;
|
||
|
return before + nl + after;
|
||
|
}
|
||
|
|
||
|
if (comment.type === 'CommentBlock' && options.block === true) {
|
||
|
const before = str.slice(0, comment.start - pos.removed);
|
||
|
const after = str.slice(comment.end - pos.removed);
|
||
|
pos.removed += comment.end - comment.start - nl.length;
|
||
|
return before + nl + after;
|
||
|
}
|
||
|
|
||
|
return str;
|
||
|
}
|
||
|
|
||
|
function isProtected(comment, options) {
|
||
|
return options && options.keepProtected === true && /^\*?!/.test(comment.value);
|
||
|
}
|
||
|
|
||
|
module.exports = strip;
|