From edbdeec90d55b530c97c842cad63b2b76e5c9949 Mon Sep 17 00:00:00 2001 From: lanyuanxiaoyao Date: Sun, 15 Mar 2026 12:06:44 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E6=94=AF=E6=8C=81=E4=BB=8E=E4=BB=BB?= =?UTF-8?q?=E6=84=8F=E8=B7=AF=E5=BE=84=E8=B0=83=E7=94=A8=20lyxy=5Fdocument?= =?UTF-8?q?=5Freader.py?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 从 __file__ 动态计算项目根目录 - 使用绝对路径引用 bootstrap.py - 设置正确的 PYTHONPATH 和 cwd - 添加路径解析测试 Co-Authored-By: Claude Opus 4.6 --- scripts/lyxy_document_reader.py | 13 +++++-- tests/test_cli/test_path_resolution.py | 53 ++++++++++++++++++++++++++ 2 files changed, 62 insertions(+), 4 deletions(-) create mode 100644 tests/test_cli/test_path_resolution.py diff --git a/scripts/lyxy_document_reader.py b/scripts/lyxy_document_reader.py index ba07b4e..15dc8a3 100644 --- a/scripts/lyxy_document_reader.py +++ b/scripts/lyxy_document_reader.py @@ -8,8 +8,13 @@ import subprocess import sys from pathlib import Path +# 确定项目根目录和脚本路径 +script_file = Path(__file__).resolve() +scripts_dir = script_file.parent +project_root = scripts_dir.parent +bootstrap_path = str(scripts_dir / "bootstrap.py") + # 将 scripts/ 目录添加到 sys.path -scripts_dir = Path(__file__).resolve().parent if str(scripts_dir) not in sys.path: sys.path.append(str(scripts_dir)) @@ -96,7 +101,7 @@ def main(): # 生成 uv 命令参数列表 uv_args = generate_uv_args( dependencies=dependencies, - script_path="scripts/bootstrap.py", + script_path=bootstrap_path, python_version=python_version, include_pyarmor=True ) @@ -106,10 +111,10 @@ def main(): # 设置环境变量 env = os.environ.copy() - env["PYTHONPATH"] = "." + env["PYTHONPATH"] = str(project_root) # 自启动:使用 subprocess 替代 execvpe(Windows 兼容) - result = subprocess.run(uv_args, env=env) + result = subprocess.run(uv_args, env=env, cwd=str(project_root)) sys.exit(result.returncode) diff --git a/tests/test_cli/test_path_resolution.py b/tests/test_cli/test_path_resolution.py new file mode 100644 index 0000000..2bec251 --- /dev/null +++ b/tests/test_cli/test_path_resolution.py @@ -0,0 +1,53 @@ +"""测试路径解析功能 - 验证从任意路径调用脚本。""" + +import sys +from pathlib import Path + + +class TestPathResolution: + """测试路径解析逻辑。""" + + def test_project_root_detection(self): + """测试项目根目录检测逻辑。""" + # 模拟 lyxy_document_reader.py 中的路径计算逻辑 + # 获取当前测试文件的路径,然后向上找到项目根 + test_file = Path(__file__).resolve() + tests_dir = test_file.parent.parent # tests/ + project_root = tests_dir.parent # 项目根 + + # 验证我们能正确找到项目根 + assert (project_root / "scripts").exists() + assert (project_root / "scripts" / "lyxy_document_reader.py").exists() + assert (project_root / "scripts" / "bootstrap.py").exists() + + def test_bootstrap_path_absolute(self): + """测试 bootstrap.py 路径是绝对路径。""" + # 模拟 lyxy_document_reader.py 中的路径计算 + test_file = Path(__file__).resolve() + project_root = test_file.parent.parent.parent # 从 tests/test_cli/ 向上两级 + scripts_dir = project_root / "scripts" + bootstrap_path = scripts_dir / "bootstrap.py" + + # 验证路径是绝对路径 + assert bootstrap_path.is_absolute() + assert bootstrap_path.exists() + + def test_path_independent_from_cwd(self, monkeypatch, tmp_path): + """测试路径计算不依赖当前工作目录。""" + # 保存原始路径 + test_file = Path(__file__).resolve() + project_root = test_file.parent.parent.parent + scripts_dir = project_root / "scripts" + + # 切换到临时目录 + monkeypatch.chdir(tmp_path) + + # 即使在临时目录,我们仍然能通过 __file__ 找到正确的路径 + # 这里我们模拟 lyxy_document_reader.py 中的逻辑 + # 注意:实际中 __file__ 是脚本本身的路径,不是测试文件的路径 + # 这里我们验证原理:__file__ 给出的是脚本位置,与 cwd 无关 + + # 验证 scripts_dir 和 bootstrap_path 的计算只依赖 __file__ + # 这个测试验证的是概念,不是实际的脚本导入 + assert scripts_dir.is_absolute() + assert (scripts_dir / "bootstrap.py").exists()