diff --git a/Lib/idlelib/idle_test/test_run.py b/Lib/idlelib/idle_test/test_run.py index 83ecbffa2a197e..f95b8f01749d83 100644 --- a/Lib/idlelib/idle_test/test_run.py +++ b/Lib/idlelib/idle_test/test_run.py @@ -45,6 +45,7 @@ def __eq__(self, other): ('int.reel', AttributeError, "type object 'int' has no attribute 'reel'. " "Did you mean: 'real'?\n"), + (r'raise NameError("123\n456")', NameError, "123\n456\n"), ) @force_not_colorized @@ -52,7 +53,10 @@ def test_get_message(self): for code, exc, msg in self.data: with self.subTest(code=code): try: - eval(compile(code, '', 'eval')) + if "raise" not in code: + eval(compile(code, '', 'eval')) + else: + exec(compile(code, '', 'exec')) # code r"raise NameError("123\n456")" cannot run in "eval" mode: SyntaxError except exc: typ, val, tb = sys.exc_info() actual = run.get_message_lines(typ, val, tb)[0] @@ -64,15 +68,26 @@ def test_get_message(self): new_callable=lambda: (lambda t, e: None)) def test_get_multiple_message(self, mock): d = self.data - data2 = ((d[0], d[1]), (d[1], d[2]), (d[2], d[0])) + data2 = ((d[0], d[1]), + (d[1], d[2]), + (d[2], d[3]), + (d[3], d[0]), + (d[1], d[3]), + (d[0], d[2])) subtests = 0 for (code1, exc1, msg1), (code2, exc2, msg2) in data2: with self.subTest(codes=(code1,code2)): try: - eval(compile(code1, '', 'eval')) + if "raise" not in code1: + eval(compile(code1, '', 'eval')) + else: + exec(compile(code1, '', 'exec')) except exc1: try: - eval(compile(code2, '', 'eval')) + if "raise" not in code2: + eval(compile(code2, '', 'eval')) + else: + exec(compile(code2, '', 'exec')) except exc2: with captured_stderr() as output: run.print_exception() diff --git a/Lib/idlelib/run.py b/Lib/idlelib/run.py index a30db99a619a93..65076aac4305ad 100644 --- a/Lib/idlelib/run.py +++ b/Lib/idlelib/run.py @@ -235,7 +235,15 @@ def get_message_lines(typ, exc, tb): err = io.StringIO() with contextlib.redirect_stderr(err): sys.__excepthook__(typ, exc, tb) - return [err.getvalue().split("\n")[-2] + "\n"] + err_list = err.getvalue().split("\n")[1:] + + for i in range(len(err_list)): + if err_list[i].startswith(" "): + continue + else: + err_list = err_list[i:-1] + break + return ["\n".join(err_list) + "\n"] else: return traceback.format_exception_only(typ, exc) diff --git a/Misc/NEWS.d/next/IDLE/2025-08-08-10-50-59.gh-issue-135511.9Rw5Zg.rst b/Misc/NEWS.d/next/IDLE/2025-08-08-10-50-59.gh-issue-135511.9Rw5Zg.rst new file mode 100644 index 00000000000000..f9526b760573ed --- /dev/null +++ b/Misc/NEWS.d/next/IDLE/2025-08-08-10-50-59.gh-issue-135511.9Rw5Zg.rst @@ -0,0 +1,2 @@ +Fix the missing error message in "NameError" and "AttributeError" in IDLE +when "\n" in message