diff --git a/README.md b/README.md index 1287d30..f433edb 100644 --- a/README.md +++ b/README.md @@ -101,3 +101,8 @@ Options: a function, the function will be called with the invalid characters and it's return value will be used as the replacement. See [`String.prototype.replace`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/replace) for more info. + * `options.sanitizeWindows`: *optional, boolean, default: `true`*. If falsy, + Windows-reserved filenames and trailing periods or spaces will not be + sanitized. + * `options.truncate`: *optional, boolean, default: `true`*. If falsy, + resulting filenames will not be truncated to 255 bytes. \ No newline at end of file diff --git a/index.js b/index.js index b32e77c..c22718a 100644 --- a/index.js +++ b/index.js @@ -36,21 +36,34 @@ var reservedRe = /^\.+$/; var windowsReservedRe = /^(con|prn|aux|nul|com[0-9]|lpt[0-9])(\..*)?$/i; var windowsTrailingRe = /[\. ]+$/; -function sanitize(input, replacement) { +var defaultOptions = { + replacement: '', + sanitizeWindows: true, + truncate: true +} + +function sanitize(input, replacement, options) { + options = Object.assign({}, defaultOptions, options) var sanitized = input .replace(illegalRe, replacement) .replace(controlRe, replacement) - .replace(reservedRe, replacement) - .replace(windowsReservedRe, replacement) - .replace(windowsTrailingRe, replacement); - return truncate(sanitized, 255); + .replace(reservedRe, replacement); + if (options.sanitizeWindows) { + sanitized = sanitized + .replace(windowsReservedRe, replacement) + .replace(windowsTrailingRe, replacement); + } + if (options.truncate) { + return truncate(sanitized, 255); + } + return sanitized } module.exports = function (input, options) { - var replacement = (options && options.replacement) || ''; - var output = sanitize(input, replacement); + var replacement = (options && options.replacement) || defaultOptions.replacement; + var output = sanitize(input, replacement, options); if (replacement === '') { return output; } - return sanitize(output, ''); + return sanitize(output, '', options); }; diff --git a/package.json b/package.json index 13ca38d..7d17138 100644 --- a/package.json +++ b/package.json @@ -19,6 +19,7 @@ }, "scripts": { "test": "tape test.js", + "test-unit": "tape test.js --unit-only", "test-browser": "zuul --local --open -- test.js", "test-browser-sauce": "zuul -- test.js" }, diff --git a/test.js b/test.js index 3995653..ccce5d6 100644 --- a/test.js +++ b/test.js @@ -11,6 +11,14 @@ var REPLACEMENT_OPTS = { replacement: "_", }; +var NO_WINDOWS_OPTS = { + sanitizeWindows: false +} + +var NO_TRUNCATE_OPTS = { + truncate: false +} + test("valid names", function(t) { ["the quick brown fox jumped over the lazy dog.mp3", "résumé"].forEach(function(name) { @@ -100,6 +108,16 @@ test("reserved filename in Windows with replacement", function(t) { t.end(); }); +test("reserved filename in Windows with sanitizeWindows false", function(t) { + t.equal(sanitize("con", NO_WINDOWS_OPTS), "con"); + t.equal(sanitize("COM1", NO_WINDOWS_OPTS), "COM1"); + t.equal(sanitize("PRN.", NO_WINDOWS_OPTS), "PRN."); + t.equal(sanitize("aux.txt", NO_WINDOWS_OPTS), "aux.txt"); + t.equal(sanitize("LPT9.asdfasdf", NO_WINDOWS_OPTS), "LPT9.asdfasdf"); + t.equal(sanitize("LPT10.txt", NO_WINDOWS_OPTS), "LPT10.txt"); + t.end(); +}); + test("invalid replacement", function (t) { t.equal(sanitize(".", { replacement: "."}), ""); t.equal(sanitize("foo?.txt", { replacement: ">"}), "foo.txt"); @@ -115,6 +133,13 @@ test("255 characters max", function(t) { t.end(); }); +test("no character maximum with truncate false", function(t) { + var string = repeat("a", 300); + t.ok(string.length > 255); + t.ok(sanitize(string, NO_TRUNCATE_OPTS).length === 300); + t.end(); +}); + // Test the handling of non-BMP chars in UTF-8 // @@ -168,7 +193,7 @@ function testStringUsingFS(str, t) { } // Don't run these tests in browser environments -if ( ! process.browser) { +if (!process.browser && !process.argv.find(arg => arg === '--unit-only')) { // ## Browserify Build // // Make sure Buffer is not used when building using browserify.