You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python中如何获取被主脚本调用的子脚本所在目录?

解决子脚本调用自定义包函数时获取自身目录的问题

这个问题的核心在于你需要获取的是调用该包函数的脚本路径,而非包本身或主脚本的路径。之前的尝试要么依赖进程的工作目录(os.getcwd()),要么只获取了包的帧信息,我们可以通过调整inspect的栈帧层级来解决。

核心解决方案:获取调用者的脚本路径

修改你自定义包中的函数,让它获取调用该函数的代码所在的栈帧,而不是函数自身的帧。这样不管是主脚本、exec执行的子脚本还是subprocess启动的子脚本调用它,都能拿到正确的调用者目录。

# 自定义包中的函数
import os
import inspect

def get_caller_script_dir():
    # 获取当前函数的上一层栈帧(即调用该函数的代码所在的帧)
    caller_frame = inspect.currentframe().f_back
    if not caller_frame:
        # 极端情况:没有调用帧, fallback到当前工作目录
        return os.getcwd()
    # 获取调用者的脚本文件名
    caller_filename = inspect.getframeinfo(caller_frame).filename
    # 返回该脚本的目录
    return os.path.dirname(os.path.abspath(caller_filename))

针对不同调用场景的细节处理

1. 使用exec执行子脚本的情况

exec默认会在主脚本的上下文执行,子脚本的__file__不会被自动设置。你需要在exec时手动注入__file__变量,确保子脚本的代码能正确暴露自己的路径:

# 主脚本中exec子脚本的代码
import os

sub_script_path = "./path/to/your/sub_script.py"

with open(sub_script_path, 'r') as f:
    # 编译子脚本代码,指定文件名(用于inspect识别)
    code = compile(f.read(), sub_script_path, 'exec')
    # 注入__file__变量到执行上下文
    exec(code, {"__file__": sub_script_path})

此时子脚本调用get_caller_script_dir()时,就能拿到子脚本自身的目录。

2. 使用subprocess调用子脚本的情况

如果之前用subprocess遇到问题,大概率是因为子脚本没有正确导入你的自定义包,或者你没有以独立进程的方式启动它。确保:

  • 子脚本能正确找到自定义包(比如把包所在目录加入sys.path,或者安装为可导入的包)
  • 使用完整的Python命令启动子脚本,让它作为独立进程运行:
# 主脚本中subprocess调用的代码
import subprocess

sub_script_path = "./path/to/your/sub_script.py"
# 启动独立进程执行子脚本
subprocess.run(["python", sub_script_path], check=True)

此时子脚本中的__file__会自动指向自身路径,调用get_caller_script_dir()就能拿到正确的目录。

为什么之前的尝试没成功?

  • os.getcwd():返回的是进程的工作目录,exec和默认的subprocess都会继承主脚本的工作目录,所以拿到的是主脚本目录。
  • 直接用inspect.currentframe():拿到的是包函数自身的栈帧,所以返回的是包的路径;而我们需要往上找一层,获取调用者的帧。

内容的提问来源于stack exchange,提问作者AJT

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 07:59:20