runpy — 定位並執行Python模組

原始碼: Lib/runpy.py


runpy 模組用於定位並執行 Python 模組,而無需先匯入它們。它的主要用途是實現命令列開關 -m,該開關允許使用 Python 模組名稱空間而不是檔案系統來定位指令碼。

請注意,這不是一個沙盒模組——所有程式碼都在當前程序中執行,並且任何副作用(例如其他模組的快取匯入)在函式返回後仍將保留。

此外,在 runpy 函式返回後,執行程式碼定義的任何函式和類不保證能正常工作。如果此限制對於給定用例不可接受,那麼 importlib 可能比此模組更適合。

runpy 模組提供了兩個函式

runpy.run_module(mod_name, init_globals=None, run_name=None, alter_sys=False)

執行指定模組的程式碼,並返回生成的模組的全域性字典。模組的程式碼首先使用標準匯入機制定位(詳情請參閱 PEP 302),然後在新的模組名稱空間中執行。

mod_name 引數應該是一個絕對模組名稱。如果模組名稱指的是包而不是普通模組,那麼將匯入該包,然後執行該包中的 __main__ 子模組,並返回生成的模組全域性字典。

可選的字典引數 init_globals 可用於在程式碼執行之前預填充模組的全域性字典。init_globals 不會被修改。如果以下任何特殊全域性變數在 init_globals 中定義,則這些定義將被 run_module() 覆蓋。

特殊全域性變數 __name____spec____file____cached____loader____package__ 在模組程式碼執行前在全域性字典中設定。(請注意,這是一組最小的變數——其他變數可能作為直譯器實現細節隱式設定。)

如果可選引數 run_name 不為 None,則 __name__ 將設定為 run_name;如果指定模組是包,則設定為 mod_name + '.__main__';否則設定為 mod_name 引數。

__spec__ 將根據 實際 匯入的模組進行適當設定(也就是說,__spec__.name 將始終為 mod_namemod_name + '.__main__',而不是 run_name)。

__file____cached____loader____package__ 根據模組規範正常設定

如果提供了引數 alter_sys 且其值為 True,則 sys.argv[0] 將更新為 __file__ 的值,並且 sys.modules[__name__] 將更新為正在執行模組的臨時模組物件。在函式返回之前,sys.argv[0]sys.modules[__name__] 都將恢復到其原始值。

請注意,對 sys 的這種操作不是執行緒安全的。其他執行緒可能會看到部分初始化的模組以及已更改的引數列表。建議在從多執行緒程式碼呼叫此函式時,不要動 sys 模組。

參見

-m 選項在命令列提供等效功能。

3.1 新版功能: 增加了透過查詢 __main__ 子模組來執行包的能力。

3.2 新版功能: 添加了 __cached__ 全域性變數(參見 PEP 3147)。

3.4 新版功能: 更新以利用 PEP 451 新增的模組規範特性。這允許正確設定透過此方式執行的模組的 __cached__,並確保真實的模組名稱始終可作為 __spec__.name 訪問。

3.12 版中已變更: __cached__, __loader____package__ 的設定已棄用。請參閱 ModuleSpec 以獲取替代方案。

runpy.run_path(path_name, init_globals=None, run_name=None)

執行指定檔案系統位置的程式碼,並返回生成的模組的全域性字典。與提供給 CPython 命令列的指令碼名稱一樣,file_path 可以指向 Python 原始檔、編譯後的位元組碼檔案或包含 __main__ 模組的有效 sys.path 條目(例如,包含頂級 __main__.py 檔案的 zip 檔案)。

對於簡單指令碼,指定的程式碼只在新的模組名稱空間中執行。對於有效的 sys.path 條目(通常是 zip 檔案或目錄),該條目首先新增到 sys.path 的開頭。然後函式使用更新的路徑查詢並執行 __main__ 模組。請注意,如果在指定位置沒有此類模組,則沒有特殊的保護措施可以防止呼叫位於 sys.path 其他位置的現有 __main__ 條目。

可選的字典引數 init_globals 可用於在程式碼執行之前預填充模組的全域性字典。init_globals 不會被修改。如果以下任何特殊全域性變數在 init_globals 中定義,則這些定義將被 run_path() 覆蓋。

特殊全域性變數 __name____spec____file____cached____loader____package__ 在模組程式碼執行前在全域性字典中設定。(請注意,這是一組最小的變數——其他變數可能作為直譯器實現細節隱式設定。)

如果可選引數 run_name 不為 None,則 __name__ 將設定為 run_name;否則設定為 '<run_path>'

如果 file_path 直接引用指令碼檔案(無論是原始檔還是預編譯位元組碼),則 __file__ 將設定為 file_path,並且 __spec____cached____loader____package__ 都將設定為 None

如果 file_path 是對有效 sys.path 條目的引用,則 __spec__ 將為匯入的 __main__ 模組進行適當設定(也就是說,__spec__.name 將始終為 __main__)。__file____cached____loader____package__ 將根據模組規範正常設定

sys 模組也進行了一些更改。首先,sys.path 可能會如上所述進行更改。sys.argv[0] 將更新為 file_path 的值,並且 sys.modules[__name__] 將更新為正在執行模組的臨時模組物件。在函式返回之前,對 sys 中專案的所有修改都將還原

請注意,與 run_module() 不同,在此函式中對 sys 的更改不是可選的,因為這些調整對於允許執行 sys.path 條目至關重要。由於執行緒安全限制仍然適用,因此在多執行緒程式碼中使用此函式應透過匯入鎖進行序列化,或委託給單獨的程序。

參見

命令列上等效功能的介面選項 (python path/to/script)。

在 3.2 版本加入。

3.4 新版功能: 更新以利用 PEP 451 新增的模組規範特性。這允許在從有效的 sys.path 條目匯入 __main__ 而不是直接執行的情況下,正確設定 __cached__

3.12 版中已變更: __cached__, __loader____package__ 的設定已棄用。

參見

PEP 338 – 將模組作為指令碼執行

由 Nick Coghlan 撰寫和實現。

PEP 366 – 主模組顯式相對匯入

由 Nick Coghlan 撰寫和實現。

PEP 451 – 匯入系統的 ModuleSpec 型別

由 Eric Snow 撰寫和實現

命令列和環境 - CPython 命令列詳情

importlib.import_module() 函式