diff --git a/Lib/_pyrepl/main.py b/Lib/_pyrepl/main.py index 447eb1e551e774..5742a213323a01 100644 --- a/Lib/_pyrepl/main.py +++ b/Lib/_pyrepl/main.py @@ -11,6 +11,8 @@ raise RuntimeError("Windows 10 TH2 or later required") if not os.isatty(sys.stdin.fileno()): raise OSError(errno.ENOTTY, "tty required", "stdin") + if sys.platform == "win32" and not os.isatty(sys.stdout.fileno()): + raise OSError(errno.ENOTTY, "tty required", "stdout") from .simple_interact import check if err := check(): raise RuntimeError(err) diff --git a/Lib/test/test_pyrepl/test_windows_console.py b/Lib/test/test_pyrepl/test_windows_console.py index f9607e02c604ff..d4b890dbda2875 100644 --- a/Lib/test/test_pyrepl/test_windows_console.py +++ b/Lib/test/test_pyrepl/test_windows_console.py @@ -5,6 +5,9 @@ raise unittest.SkipTest("test only relevant on win32") +import subprocess +from tempfile import TemporaryDirectory +import os import itertools from functools import partial from test.support import force_not_colorized_test_class @@ -577,5 +580,29 @@ def test_up_vt(self): self.assertEqual(self.mock.call_count, 3) +class WindowsCommandLineTests(unittest.TestCase): + def test_for_crash_traceback_with_redirected_stdout(self): + """python.bat -i -c "print('hlwd')" > file.txt""" + script_command = "print('script has run')" + with TemporaryDirectory() as tmp_dir: + stdout_path = os.path.join(tmp_dir, "WinCMDLineTests.txt") + with open(stdout_path, "w+") as stdout_file, \ + subprocess.Popen( + [sys.executable, '-i', '-u', '-c', script_command], + stdin=None, + stdout=stdout_file, + stderr=subprocess.PIPE, + text=True, errors='replace' + ) as process: + try: + process.wait(timeout=5) + except subprocess.TimeoutExpired: + process.kill() + stdout_file.seek(0) + stdout_from_file = stdout_file.read() + stdout_file.close() + self.assertIn("script has run", stdout_from_file) + + if __name__ == "__main__": unittest.main() diff --git a/Misc/NEWS.d/next/Windows/2025-06-13-19-18-00.gh-issue-132962.qOquLB.rst b/Misc/NEWS.d/next/Windows/2025-06-13-19-18-00.gh-issue-132962.qOquLB.rst new file mode 100644 index 00000000000000..68a6b1da2c6e43 --- /dev/null +++ b/Misc/NEWS.d/next/Windows/2025-06-13-19-18-00.gh-issue-132962.qOquLB.rst @@ -0,0 +1,3 @@ +The interactive interpreter (-i) on Windows no longer crashes when standard +output is redirected. It now correctly falls back to the basic REPL in this +situation.