Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(#50): add --no-validate #496

Merged
merged 13 commits into from
Dec 19, 2024
21 changes: 13 additions & 8 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -93,9 +93,10 @@ If a file is not properly formatted, the exit code will be non-zero.

```console
foo@bar:~$ mdformat --help
usage: mdformat [-h] [--check] [--version] [--number] [--wrap {keep,no,INTEGER}]
[--end-of-line {lf,crlf,keep}] [--exclude PATTERN]
[--extensions EXTENSION] [--codeformatters LANGUAGE]
usage: mdformat [-h] [--check] [--no-validate] [--version] [--number]
[--wrap {keep,no,INTEGER}] [--end-of-line {lf,crlf,keep}]
[--exclude PATTERN] [--extensions EXTENSION]
[--codeformatters LANGUAGE]
[paths ...]

CommonMark compliant Markdown formatter
Expand All @@ -106,19 +107,23 @@ positional arguments:
options:
-h, --help show this help message and exit
--check do not apply changes to files
--no-validate do not validate that the rendered HTML is consistent
--version show program's version number and exit
--number apply consecutive numbering to ordered lists
--wrap {keep,no,INTEGER}
paragraph word wrap mode (default: keep)
--end-of-line {lf,crlf,keep}
output file line ending mode (default: lf)
--exclude PATTERN exclude files that match the Unix-style glob pattern (multiple allowed)
--exclude PATTERN exclude files that match the Unix-style glob pattern
(multiple allowed)
--extensions EXTENSION
require and enable an extension plugin (multiple allowed) (use
`--no-extensions` to disable) (default: all enabled)
require and enable an extension plugin (multiple
allowed) (use `--no-extensions` to disable) (default:
all enabled)
--codeformatters LANGUAGE
require and enable a code formatter plugin (multiple allowed)
(use `--no-codeformatters` to disable) (default: all enabled)
require and enable a code formatter plugin (multiple
allowed) (use `--no-codeformatters` to disable)
(default: all enabled)
```

The `--exclude` option is only available on Python 3.13+.
Expand Down
1 change: 1 addition & 0 deletions docs/users/configuration_file.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ Command line interface arguments take precedence over the configuration file.
wrap = "keep" # options: {"keep", "no", INTEGER}
number = false # options: {false, true}
end_of_line = "lf" # options: {"lf", "crlf", "keep"}
validate = true # options: {false, true}
# extensions = [ # options: a list of enabled extensions (default: all installed are enabled)
# "gfm",
# "toc",
Expand Down
23 changes: 17 additions & 6 deletions src/mdformat/_cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -142,12 +142,16 @@ def run(cli_args: Sequence[str]) -> int: # noqa: C901
getattr(plugin, "CHANGES_AST", False)
for plugin in enabled_parserplugins.values()
)
if not changes_ast and not is_md_equal(
original_str,
formatted_str,
options=opts,
extensions=enabled_parserplugins,
codeformatters=enabled_codeformatters,
if (
opts["validate"]
and not changes_ast
and not is_md_equal(
original_str,
formatted_str,
options=opts,
extensions=enabled_parserplugins,
codeformatters=enabled_codeformatters,
)
):
print_error(
f'Could not format "{path_str}".',
Expand Down Expand Up @@ -197,6 +201,13 @@ def make_arg_parser(
parser.add_argument(
"--check", action="store_true", help="do not apply changes to files"
)
parser.add_argument(
"--no-validate",
action="store_const",
const=False,
dest="validate",
help="do not validate that the rendered HTML is consistent",
)
version_str = f"mdformat {mdformat.__version__}"
plugin_version_str = get_plugin_version_str(
{**parser_extension_dists, **codeformatter_dists}
Expand Down
4 changes: 4 additions & 0 deletions src/mdformat/_conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
"wrap": "keep",
"number": False,
"end_of_line": "lf",
"validate": True,
"exclude": [],
"plugin": {},
"extensions": None,
Expand Down Expand Up @@ -59,6 +60,9 @@ def _validate_values(opts: Mapping, conf_path: Path) -> None: # noqa: C901
if "end_of_line" in opts:
if opts["end_of_line"] not in {"crlf", "lf", "keep"}:
raise InvalidConfError(f"Invalid 'end_of_line' value in {conf_path}")
if "validate" in opts:
if not isinstance(opts["validate"], bool):
raise InvalidConfError(f"Invalid 'validate' value in {conf_path}")
KyleKing marked this conversation as resolved.
Show resolved Hide resolved
if "number" in opts:
if not isinstance(opts["number"], bool):
raise InvalidConfError(f"Invalid 'number' value in {conf_path}")
Expand Down
13 changes: 13 additions & 0 deletions tests/test_cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -345,6 +345,19 @@ def test_eol__check_keep_crlf(tmp_path):
assert run((str(file_path), "--check", "--end-of-line=keep")) == 1


def test_cli_no_validate(tmp_path):
file_path = tmp_path / "test.md"
content = "1. ordered"
file_path.write_text(content)

with patch("mdformat.renderer._context.get_list_marker_type", return_value="?"):
assert run((str(file_path),)) == 1
assert file_path.read_text() == content

assert run((str(file_path), "--no-validate")) == 0
assert file_path.read_text() == "1? ordered\n"


def test_get_plugin_info_str():
info = get_plugin_info_str(
{"mdformat-tables": ("0.1.0", ["tables"])},
Expand Down
20 changes: 20 additions & 0 deletions tests/test_config_file.py
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@ def test_invalid_toml(tmp_path, capsys):
[
("wrap", "wrap = -3"),
("end_of_line", "end_of_line = 'lol'"),
("validate", "validate = 'off'"),
("number", "number = 0"),
("exclude", "exclude = '**'"),
("exclude", "exclude = ['1',3]"),
Expand Down Expand Up @@ -149,3 +150,22 @@ def test_empty_exclude(tmp_path, capsys):

assert run((str(tmp_path),)) == 0
assert file1_path.read_text() == FORMATTED_MARKDOWN


def test_conf_no_validate(tmp_path):
file_path = tmp_path / "file.md"
content = "1. ordered"
file_path.write_text(content)

with mock.patch(
"mdformat.renderer._context.get_list_marker_type",
return_value="?",
):
assert run_with_clear_cache((str(file_path),)) == 1
assert file_path.read_text() == content

config_path = tmp_path / ".mdformat.toml"
config_path.write_text("validate = false")

assert run_with_clear_cache((str(file_path),)) == 0
assert file_path.read_text() == "1? ordered\n"
Loading