Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
DavidAnson committed Apr 29, 2024
1 parent 062b447 commit 56ed229
Show file tree
Hide file tree
Showing 5 changed files with 64 additions and 6 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -99,8 +99,8 @@ JS configuration files contain JavaScript code, must have the `.js` or `.cjs` fi
If your workspace _(project)_ is [ESM-only] _(`"type": "module"` set in the root `package.json` file)_, then the configuration file **should end with `.cjs` file extension**.
A JS configuration file may internally `require` one or more npm packages as a way of reusing configuration across projects.

The `--configPointer` argument allows the use of [JSON Pointer][json-pointer] syntax to identify a sub-object within the configuration file specified via `--config`.
This works for any configuration file format and makes it possible to nest a configuration object within a more expansive file that (ex: `package.json` or `pyproject.toml`).
The `--configPointer` argument allows the use of [JSON Pointer][json-pointer] syntax to identify a sub-object within the configuration object (per above).
This argument can be used with any configuration file format and makes it possible to nest a configuration object within another file like `package.json` or `pyproject.toml` (e.g., via `/key` or `/key/subkey`).

`--enable` and `--disable` override configuration files; if a configuration file disables `MD123` and you pass `--enable MD123`, it will be enabled.
If a rule is passed to both `--enable` and `--disable`, it will be disabled.
Expand Down
7 changes: 3 additions & 4 deletions markdownlint.js
Original file line number Diff line number Diff line change
Expand Up @@ -56,8 +56,6 @@ const fsOptions = {encoding: 'utf8'};
const processCwd = process.cwd();

function readConfiguration(userConfigFile) {
const jsConfigFile = /\.c?js$/i.test(userConfigFile);

// Load from well-known config files
let config = rc('markdownlint', {});
for (const projectConfigFile of projectConfigFiles) {
Expand All @@ -72,9 +70,10 @@ function readConfiguration(userConfigFile) {
}

// Normally parsing this file is not needed, because it is already parsed by rc package.
// However I have to do it to overwrite configuration from .markdownlint.{json,yaml,yml}.
// However I have to do it to overwrite configuration from .markdownlint.{jsonc,json,yaml,yml}.
if (userConfigFile) {
try {
const jsConfigFile = /\.c?js$/i.test(userConfigFile);
const userConfig = jsConfigFile ? require(path.resolve(processCwd, userConfigFile)) : markdownlint.readConfigSync(userConfigFile, configParsers);
config = require('deep-extend')(config, userConfig);
} catch (error) {
Expand Down Expand Up @@ -279,7 +278,7 @@ const diff = files.filter(file => !ignores.some(ignore => ignore.absolute === fi
function lintAndPrint(stdin, files) {
files ||= [];
const configuration = readConfiguration(options.config);
const config = jsonpointer.get(configuration, options.configPointer);
const config = jsonpointer.get(configuration, options.configPointer) || {};

for (const rule of options.enable || []) {
// Leave default values in place if rule is an object
Expand Down
8 changes: 8 additions & 0 deletions test/nested-config.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"name": "unused",

"key": {
"blanks-around-headings": false,
"commands-show-output": false
}
}
7 changes: 7 additions & 0 deletions test/nested-config.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
name = "unused"

[key]
other-name = "unused"

[key.subkey]
commands-show-output = false
44 changes: 44 additions & 0 deletions test/test.js
Original file line number Diff line number Diff line change
Expand Up @@ -489,6 +489,50 @@ test('.markdownlint.yaml in cwd is used instead of .markdownlint.yml', getCwdCon

test('.markdownlint.json with JavaScript-style comments is handled', getCwdConfigFileTest('json-c'));

test('invalid JSON Pointer', async t => {
try {
await execa('../markdownlint.js', ['--config', 'nested-config.json', '--configPointer', 'INVALID', '**/*.md'], {stripFinalNewline: false});
t.fail();
} catch (error) {
t.is(error.stdout, '');
t.regex(error.stderr, /Invalid JSON pointer\./);
t.is(error.exitCode, 4);
}
});

test('empty JSON Pointer', async t => {
try {
await execa('../markdownlint.js', ['--config', 'nested-config.json', '--configPointer', '/EMPTY', 'incorrect.md'], {stripFinalNewline: false});
t.fail();
} catch (error) {
t.is(error.stdout, '');
t.is(error.stderr.match(errorPattern).length, 7);
t.is(error.exitCode, 1);
}
});

test('valid JSON Pointer with JSON configuration', async t => {
try {
await execa('../markdownlint.js', ['--config', 'nested-config.json', '--configPointer', '/key', 'incorrect.md'], {stripFinalNewline: false});
t.fail();
} catch (error) {
t.is(error.stdout, '');
t.is(error.stderr.match(errorPattern).length, 1);
t.is(error.exitCode, 1);
}
});

test('valid JSON Pointer with TOML configuration', async t => {
try {
await execa('../markdownlint.js', ['--config', 'nested-config.toml', '--configPointer', '/key/subkey', 'incorrect.md'], {stripFinalNewline: false});
t.fail();
} catch (error) {
t.is(error.stdout, '');
t.is(error.stderr.match(errorPattern).length, 3);
t.is(error.exitCode, 1);
}
});

test('Custom rule from single file loaded', async t => {
try {
const input = '# Input\n';
Expand Down

0 comments on commit 56ed229

Please sign in to comment.