diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-15 18:05:20 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-15 18:05:20 +0000 |
commit | c86df75ab11643fa4649cfe6ed5c4692d4ee342b (patch) | |
tree | de847f47ec2669e74b9a3459319579346b7c99df /pre_commit/error_handler.py | |
parent | Initial commit. (diff) | |
download | pre-commit-c86df75ab11643fa4649cfe6ed5c4692d4ee342b.tar.xz pre-commit-c86df75ab11643fa4649cfe6ed5c4692d4ee342b.zip |
Adding upstream version 3.6.2.upstream/3.6.2
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'pre_commit/error_handler.py')
-rw-r--r-- | pre_commit/error_handler.py | 81 |
1 files changed, 81 insertions, 0 deletions
diff --git a/pre_commit/error_handler.py b/pre_commit/error_handler.py new file mode 100644 index 0000000..73e608b --- /dev/null +++ b/pre_commit/error_handler.py @@ -0,0 +1,81 @@ +from __future__ import annotations + +import contextlib +import functools +import os.path +import sys +import traceback +from collections.abc import Generator +from typing import IO + +import pre_commit.constants as C +from pre_commit import output +from pre_commit.errors import FatalError +from pre_commit.store import Store +from pre_commit.util import cmd_output_b +from pre_commit.util import force_bytes + + +def _log_and_exit( + msg: str, + ret_code: int, + exc: BaseException, + formatted: str, +) -> None: + error_msg = f'{msg}: {type(exc).__name__}: '.encode() + force_bytes(exc) + output.write_line_b(error_msg) + + _, git_version_b, _ = cmd_output_b('git', '--version', check=False) + git_version = git_version_b.decode(errors='backslashreplace').rstrip() + + storedir = Store().directory + log_path = os.path.join(storedir, 'pre-commit.log') + with contextlib.ExitStack() as ctx: + if os.access(storedir, os.W_OK): + output.write_line(f'Check the log at {log_path}') + log: IO[bytes] = ctx.enter_context(open(log_path, 'wb')) + else: # pragma: win32 no cover + output.write_line(f'Failed to write to log at {log_path}') + log = sys.stdout.buffer + + _log_line = functools.partial(output.write_line, stream=log) + _log_line_b = functools.partial(output.write_line_b, stream=log) + + _log_line('### version information') + _log_line() + _log_line('```') + _log_line(f'pre-commit version: {C.VERSION}') + _log_line(f'git --version: {git_version}') + _log_line('sys.version:') + for line in sys.version.splitlines(): + _log_line(f' {line}') + _log_line(f'sys.executable: {sys.executable}') + _log_line(f'os.name: {os.name}') + _log_line(f'sys.platform: {sys.platform}') + _log_line('```') + _log_line() + + _log_line('### error information') + _log_line() + _log_line('```') + _log_line_b(error_msg) + _log_line('```') + _log_line() + _log_line('```') + _log_line(formatted.rstrip()) + _log_line('```') + raise SystemExit(ret_code) + + +@contextlib.contextmanager +def error_handler() -> Generator[None, None, None]: + try: + yield + except (Exception, KeyboardInterrupt) as e: + if isinstance(e, FatalError): + msg, ret_code = 'An error has occurred', 1 + elif isinstance(e, KeyboardInterrupt): + msg, ret_code = 'Interrupted (^C)', 130 + else: + msg, ret_code = 'An unexpected error has occurred', 3 + _log_and_exit(msg, ret_code, e, traceback.format_exc()) |