diff --git a/src/Validator.js b/src/Validator.js index 5988561..b885c28 100644 --- a/src/Validator.js +++ b/src/Validator.js @@ -6,7 +6,7 @@ const editorconfig = require('editorconfig'); const DEFAULTS = extend({}, require('./constants/defaults')); const MESSAGES = require('./constants/messages'); const PATTERNS = require('./constants/ignorePatterns'); -const MAPPINGS = require('./constants/editorconfig-mappings'); +const MAPPINGS = require('./constants/editorconfigMappings'); const ValidationError = require('./ValidationError'); @@ -255,15 +255,31 @@ class Validator { if (typeof config === 'object') { // Merge editorconfig values into the correct settings names: for (key in config) { - if (typeof MAPPINGS[key] === 'string') { + if (typeof MAPPINGS[key] === 'object') { + // Handle "unset" special value given by editorconfig file + // and consider not to parse invalid types and value. + // See: Issue #47 + if ( + config[key] === 'unset' || + !MAPPINGS[key].types.includes(typeof config[key]) || + ( + typeof config[key] === 'string' && + MAPPINGS[key].regexp instanceof RegExp && + !MAPPINGS[key].regexp.test(config[key]) + ) + ) { + this._settings[MAPPINGS[key].name] = false; + continue; + } + switch (key) { case 'indent_style': // The 'indent_style' property value isn't // equal to the expected setting value: - this._settings[MAPPINGS[key]] = config[key] + 's'; + this._settings[MAPPINGS[key].name] = config[key] + 's'; break; default: - this._settings[MAPPINGS[key]] = config[key]; + this._settings[MAPPINGS[key].name] = config[key]; break; } } diff --git a/src/Validator.test.js b/src/Validator.test.js index 3d22314..631a54b 100644 --- a/src/Validator.test.js +++ b/src/Validator.test.js @@ -159,7 +159,7 @@ describe('The validator', () => { expect(validator._settings.trailingspaces).toBeFalsy(); expect(validator._settings.newline).toBeFalsy(); expect(validator._settings.indentation).toBe('tabs'); - expect(validator._settings.spaces).toBe('tab'); + expect(validator._settings.spaces).toBe(false); expect(validator._settings.endOfLine).toBe('lf'); // Unchanged: @@ -210,11 +210,61 @@ describe('The validator', () => { // test for expected properties by editorconfig: expect(validator._settings.indentation).toBe('tabs'); - expect(validator._settings.spaces).toBe('tab'); + expect(validator._settings.spaces).toBe(false); expect(validator._settings.trailingspaces).toBeTruthy(); expect(validator._settings.newline).toBeTruthy(); }); + it('should parse "unset" value as false', () => { + // fake loading: + const validator = new Validator({ + editorconfig: __fromFixtures('.editorconfig.unset'), + + trailingspaces: true, + newline: true, + + indentation: 'spaces', + spaces: 2, + endOfLine: true, + }); + + // Load editorconfig with extension where options are disabled: + validator._path = __fromFixtures('core.fixture'); + validator._loadSettings(); + expect(validator._settings).toEqual(expect.objectContaining({ + trailingspaces: false, + newline: false, + indentation: false, + spaces: false, + endOfLine: false, + })) + }); + + it('should parse invalid value as false', () => { + // fake loading: + const validator = new Validator({ + editorconfig: __fromFixtures('.editorconfig.invalid'), + + trailingspaces: true, + newline: true, + + indentation: 'spaces', + spaces: 2, + endOfLine: true, + }); + + // Load editorconfig with extension where options are disabled: + validator._path = __fromFixtures('core.fixture'); + validator._loadSettings(); + expect(validator._settings).toEqual(expect.objectContaining({ + trailingspaces: false, + newline: false, + indentation: false, + spaces: false, + endOfLine: false, + })) + }); + it('should throw if is not a file', () => { const file = __fromFixtures('core.fixture'); [ diff --git a/src/__fixtures__/.editorconfig.invalid b/src/__fixtures__/.editorconfig.invalid new file mode 100644 index 0000000..dce9bcd --- /dev/null +++ b/src/__fixtures__/.editorconfig.invalid @@ -0,0 +1,15 @@ +root = true + +[*] +indent_style = space +indent_size = 2 +end_of_line = cf +insert_final_newline = true +trim_trailing_whitespace = true + +[*.fixture] +indent_style = foo +indent_size = bar +end_of_line = baz +insert_final_newline = qux +trim_trailing_whitespace = quux diff --git a/src/__fixtures__/.editorconfig.unset b/src/__fixtures__/.editorconfig.unset new file mode 100644 index 0000000..3cca934 --- /dev/null +++ b/src/__fixtures__/.editorconfig.unset @@ -0,0 +1,15 @@ +root = true + +[*] +indent_style = space +indent_size = 2 +end_of_line = cf +insert_final_newline = true +trim_trailing_whitespace = true + +[*.fixture] +indent_style = unset +indent_size = unset +end_of_line = unset +insert_final_newline = unset +trim_trailing_whitespace = unset diff --git a/src/constants/defaults.js b/src/constants/defaults.js index 55a1e8b..25361f7 100644 --- a/src/constants/defaults.js +++ b/src/constants/defaults.js @@ -12,5 +12,5 @@ module.exports = { editorconfig: false, // path to editor-config file rcconfig: false, // path to rc-config file allowsBOM: false, - end_of_line: false, // 'LF' or 'CRLF' or 'CR' or false to disable checking + endOfLine: false, // 'LF' or 'CRLF' or 'CR' or false to disable checking }; diff --git a/src/constants/editorconfig-mappings.js b/src/constants/editorconfig-mappings.js deleted file mode 100644 index e6858de..0000000 --- a/src/constants/editorconfig-mappings.js +++ /dev/null @@ -1,8 +0,0 @@ -module.exports = { - charset: 'encoding', - insert_final_newline: 'newline', - indent_style: 'indentation', - indent_size: 'spaces', - trim_trailing_whitespace: 'trailingspaces', - end_of_line: 'endOfLine', -}; diff --git a/src/constants/editorconfigMappings.js b/src/constants/editorconfigMappings.js new file mode 100644 index 0000000..54803a9 --- /dev/null +++ b/src/constants/editorconfigMappings.js @@ -0,0 +1,32 @@ +module.exports = { + charset: { + name: 'encoding', + types: ['string'], + regexp: /^.*$/, + }, + insert_final_newline: { + name: 'newline', + types: ['boolean'], + regexp: false, + }, + indent_style: { + name: 'indentation', + types: ['string'], + regexp: /^tab|space$/i, + }, + indent_size: { + name: 'spaces', + types: ['number'], + regexp: false, + }, + trim_trailing_whitespace: { + name: 'trailingspaces', + types: ['boolean'], + regexp: false, + }, + end_of_line: { + name: 'endOfLine', + types: ['string'], + regexp: /^lf|crlf|cr$/i, + }, +};