From e01150731b245306027c98241ba2a1b136611882 Mon Sep 17 00:00:00 2001 From: Kyle Cutler Date: Fri, 7 Jan 2022 15:07:04 -0800 Subject: [PATCH 1/3] Normalize debugger temp file paths on Windows --- ipykernel/compiler.py | 10 ++++++++-- ipykernel/debugger.py | 2 +- setup.py | 1 + 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/ipykernel/compiler.py b/ipykernel/compiler.py index 0b1384021..472116beb 100644 --- a/ipykernel/compiler.py +++ b/ipykernel/compiler.py @@ -39,8 +39,14 @@ def murmur2_x86(data, seed): def get_tmp_directory(): tmp_dir = tempfile.gettempdir() + if os.name == 'nt': + try: + import win32file + tmp_dir = win32file.GetLongPathName(tmp_dir) + except: + pass pid = os.getpid() - return tmp_dir + '/ipykernel_' + str(pid) + return tmp_dir + os.sep + 'ipykernel_' + str(pid) def get_tmp_hash_seed(): @@ -52,7 +58,7 @@ def get_file_name(code): cell_name = os.environ.get("IPYKERNEL_CELL_NAME") if cell_name is None: name = murmur2_x86(code, get_tmp_hash_seed()) - cell_name = get_tmp_directory() + '/' + str(name) + '.py' + cell_name = get_tmp_directory() + os.sep + str(name) + '.py' return cell_name diff --git a/ipykernel/debugger.py b/ipykernel/debugger.py index 62c6a5407..d1ce0ff8f 100644 --- a/ipykernel/debugger.py +++ b/ipykernel/debugger.py @@ -507,7 +507,7 @@ async def debugInfo(self, message): 'isStarted': self.is_started, 'hashMethod': 'Murmur2', 'hashSeed': get_tmp_hash_seed(), - 'tmpFilePrefix': get_tmp_directory() + '/', + 'tmpFilePrefix': get_tmp_directory() + os.sep, 'tmpFileSuffix': '.py', 'breakpoints': breakpoint_list, 'stoppedThreads': self.stopped_threads, diff --git a/setup.py b/setup.py index 95dffbc66..dfff0d5dc 100644 --- a/setup.py +++ b/setup.py @@ -69,6 +69,7 @@ def run(self): 'matplotlib-inline>=0.1.0,<0.2.0', 'appnope;platform_system=="Darwin"', 'nest_asyncio', + 'pywin32;platform_system=="Windows"' ], extras_require={ "test": [ From 4d873e0ac59cc160859afab2e5de256a62aff9d3 Mon Sep 17 00:00:00 2001 From: Kyle Cutler Date: Mon, 10 Jan 2022 09:08:39 -0800 Subject: [PATCH 2/3] Use ctypes instead of pywin32 --- ipykernel/compiler.py | 33 ++++++++++++++++++++++++++------- setup.py | 1 - 2 files changed, 26 insertions(+), 8 deletions(-) diff --git a/ipykernel/compiler.py b/ipykernel/compiler.py index 472116beb..a38e45378 100644 --- a/ipykernel/compiler.py +++ b/ipykernel/compiler.py @@ -1,6 +1,7 @@ from IPython.core.compilerop import CachingCompiler import tempfile import os +import sys def murmur2_x86(data, seed): @@ -36,15 +37,33 @@ def murmur2_x86(data, seed): return h +convert_to_long_pathname = lambda filename:filename + +if sys.platform == 'win32': + try: + import ctypes + from ctypes.wintypes import MAX_PATH, LPCWSTR, LPWSTR, DWORD + + _GetLongPathName = ctypes.windll.kernel32.GetLongPathNameW + _GetLongPathName.argtypes = [LPCWSTR, LPWSTR, DWORD] + _GetLongPathName.restype = DWORD + + def _convert_to_long_pathname(filename): + buf = ctypes.create_unicode_buffer(MAX_PATH) + rv = _GetLongPathName(filename, buf, MAX_PATH) + if rv != 0 and rv <= MAX_PATH: + filename = buf.value + return filename + + # test that it works + _convert_to_long_pathname(__file__) + except: + pass + else: + convert_to_long_pathname = _convert_to_long_pathname def get_tmp_directory(): - tmp_dir = tempfile.gettempdir() - if os.name == 'nt': - try: - import win32file - tmp_dir = win32file.GetLongPathName(tmp_dir) - except: - pass + tmp_dir = convert_to_long_pathname(tempfile.gettempdir()) pid = os.getpid() return tmp_dir + os.sep + 'ipykernel_' + str(pid) diff --git a/setup.py b/setup.py index dfff0d5dc..95dffbc66 100644 --- a/setup.py +++ b/setup.py @@ -69,7 +69,6 @@ def run(self): 'matplotlib-inline>=0.1.0,<0.2.0', 'appnope;platform_system=="Darwin"', 'nest_asyncio', - 'pywin32;platform_system=="Windows"' ], extras_require={ "test": [ From 6ffb3d33f4a24d06b09edb85d53e06aa6ae6d73a Mon Sep 17 00:00:00 2001 From: Kyle Cutler Date: Mon, 10 Jan 2022 09:58:25 -0800 Subject: [PATCH 3/3] Add test, clarify reason for inline check --- ipykernel/compiler.py | 2 +- ipykernel/tests/test_debugger.py | 6 ++++++ 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/ipykernel/compiler.py b/ipykernel/compiler.py index a38e45378..95770e7be 100644 --- a/ipykernel/compiler.py +++ b/ipykernel/compiler.py @@ -55,7 +55,7 @@ def _convert_to_long_pathname(filename): filename = buf.value return filename - # test that it works + # test that it works so if there are any issues we fail just once here _convert_to_long_pathname(__file__) except: pass diff --git a/ipykernel/tests/test_debugger.py b/ipykernel/tests/test_debugger.py index ab9f13a2c..65f5711e1 100644 --- a/ipykernel/tests/test_debugger.py +++ b/ipykernel/tests/test_debugger.py @@ -271,3 +271,9 @@ def test_rich_inspect_at_breakpoint(kernel_with_debug): ) assert reply["body"]["data"] == {"text/plain": locals_[0]["value"]} + + +def test_convert_to_long_pathname(): + if sys.platform == 'win32': + from ipykernel.compiler import _convert_to_long_pathname + _convert_to_long_pathname(__file__) \ No newline at end of file