From ad4e35f3b8d5580da0baba86835503a24b464c0c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Stefan=20B=C3=BChler?= Date: Mon, 15 Aug 2022 09:56:23 +0200 Subject: [PATCH] Allow to enable/disable plugin error codes Fixes #12987 * Ignore unknown error codes in process_options * Reload enabled / disabled error codes after loading plugins * Unknown errors codes no longer a hard failure, they only get logged to stderr --- mypy/build.py | 27 +++++++++++++++++++++++++++ mypy/main.py | 15 +++++++-------- 2 files changed, 34 insertions(+), 8 deletions(-) diff --git a/mypy/build.py b/mypy/build.py index 605368a6dc51..92e7e2f00469 100644 --- a/mypy/build.py +++ b/mypy/build.py @@ -43,6 +43,7 @@ import mypy.semanal_main from mypy.checker import TypeChecker +from mypy.errorcodes import error_codes from mypy.errors import CompileError, ErrorInfo, Errors, report_internal_error from mypy.graph_utils import prepare_sccs, strongly_connected_components, topsort from mypy.indirection import TypeIndirectionVisitor @@ -233,6 +234,32 @@ def _build( errors = Errors(options, read_source=lambda path: read_py_file(path, cached_read)) plugin, snapshot = load_plugins(options, errors, stdout, extra_plugins) + # Plugins might define own error codes, take a look again now + + # Process `--enable-error-code` and `--disable-error-code` flags + disabled_codes = set(options.disable_error_code) + enabled_codes = set(options.enable_error_code) + + valid_error_codes = set(error_codes.keys()) + invalid_codes = (enabled_codes | disabled_codes) - valid_error_codes + if invalid_codes: + print(f"Invalid error code(s): {', '.join(sorted(invalid_codes))}", file=stderr) + + options.disabled_error_codes |= { + error_codes[code] for code in disabled_codes if code in error_codes + } + options.enabled_error_codes |= { + error_codes[code] for code in enabled_codes if code in error_codes + } + + # Enabling an error code always overrides disabling + options.disabled_error_codes -= options.enabled_error_codes + + # Update error codes in Errors object (might use a different + # set instance if original was empty) + errors.disabled_error_codes = options.disabled_error_codes + errors.enabled_error_codes = options.enabled_error_codes + # Add catch-all .gitignore to cache dir if we created it cache_dir_existed = os.path.isdir(options.cache_dir) diff --git a/mypy/main.py b/mypy/main.py index 1aede530c33e..f1ad54a654a3 100644 --- a/mypy/main.py +++ b/mypy/main.py @@ -1317,14 +1317,13 @@ def set_strict_flags() -> None: disabled_codes = set(options.disable_error_code) enabled_codes = set(options.enable_error_code) - valid_error_codes = set(error_codes.keys()) - - invalid_codes = (enabled_codes | disabled_codes) - valid_error_codes - if invalid_codes: - parser.error(f"Invalid error code(s): {', '.join(sorted(invalid_codes))}") - - options.disabled_error_codes |= {error_codes[code] for code in disabled_codes} - options.enabled_error_codes |= {error_codes[code] for code in enabled_codes} + # Plugins might define own error codes later, only load those we already know about here + options.disabled_error_codes |= { + error_codes[code] for code in disabled_codes if code in error_codes + } + options.enabled_error_codes |= { + error_codes[code] for code in enabled_codes if code in error_codes + } # Enabling an error code always overrides disabling options.disabled_error_codes -= options.enabled_error_codes