一文詳解如何在瀏覽器前端運(yùn)行Python程序
前言
在傳統(tǒng)的 Web 開發(fā)中,Python 通常更多地被用作服務(wù)器端語言(如 Django、Flask 等),而在瀏覽器端(前端)通常使用 JavaScript 來操作 DOM、進(jìn)行事件處理等。不過,隨著 WebAssembly 技術(shù)的發(fā)展和一些 Python-to-JavaScript 轉(zhuǎn)譯方案的出現(xiàn),我們已經(jīng)可以在前端直接運(yùn)行(或間接編譯)Python 代碼。
下面將詳細(xì)介紹在前端運(yùn)行 Python 程序的多種主要方式、它們的優(yōu)點(diǎn)和局限性,并附帶一些示例或基本使用思路。
一、直接在瀏覽器運(yùn)行 Python:基于 WebAssembly 的 Pyodide
1. 什么是 Pyodide
Pyodide 是基于 WebAssembly 的一個(gè)完整 Python 解釋器項(xiàng)目,它將 CPython(Python 的官方解釋器)編譯成了可以在瀏覽器環(huán)境(或者其它 WebAssembly 運(yùn)行環(huán)境)里執(zhí)行的版本。換句話說,你不需要安裝任何插件,只要瀏覽器支持 WebAssembly,你就可以在前端環(huán)境里運(yùn)行幾乎完整的 Python。
2. Pyodide 的主要特點(diǎn)
- 兼容性好:幾乎完整移植了 CPython,包括標(biāo)準(zhǔn)庫和部分第三方庫的支持(如 NumPy、Pandas 等)。
- 易集成:官方提供了一個(gè)
pyodide.js
(或pyodide.mjs
),前端只要將其引入即可使用。 - WebAssembly 性能:相較于純 JavaScript 解釋 Python 的方案,Pyodide 的性能更好。
3. 如何使用 Pyodide
引入 pyodide.js從官方的 CDN 或者本地托管,引入 Pyodide 腳本:
<script src="https://cdn.jsdelivr.net/pyodide/v0.23.4/full/pyodide.js"></script>
提示:版本號(hào)可能會(huì)不斷更新,可以去 Pyodide Releases 查看最新版本。
初始化 Pyodide 環(huán)境
<script> async function initPyodide() { // 加載 Pyodide let pyodide = await loadPyodide(); // 在這里就可以使用 pyodide.runPython 執(zhí)行 Python 代碼了 let result = pyodide.runPython(\` import sys sys.version \`); console.log("Python version:", result); } initPyodide(); </script>
執(zhí)行 Python 代碼
pyodide.runPython(code)
可以直接執(zhí)行一段 Python 代碼字符串,并返回最后一行表達(dá)式的值(如果有)。pyodide.globals
可以獲取當(dāng)前 Python 解釋器中全局作用域的變量。- 除了執(zhí)行簡單的腳本外,還可以加載第三方庫(部分純 Python 庫已經(jīng)預(yù)編譯到 Pyodide 里)。
示例:
<script> async function initPyodide() { let pyodide = await loadPyodide(); // 安裝 / 加載一些包 await pyodide.loadPackage("micropip"); // micropip 可以安裝更多的 Python 包,但需要兼容 WASM,如 pyodide.org 中提到的包 // 運(yùn)行簡單的 Python 代碼 let code = \` import math def compute_circle_area(r): return math.pi * (r ** 2) area = compute_circle_area(5) \`; pyodide.runPython(code); let area = pyodide.globals.get("area"); console.log("Circle area:", area); } initPyodide(); </script>
4. 優(yōu)缺點(diǎn)
- 優(yōu)點(diǎn):
- 幾乎完整地支持 Python 生態(tài),能夠直接使用很多 Python 包,尤其是科學(xué)計(jì)算相關(guān)。
- 依賴 WebAssembly,高度還原 CPython 功能,運(yùn)行效率相對(duì)其他純 JS 解釋器更高。
- 缺點(diǎn):
- 體積較大,需要加載編譯好的 Python 解釋器和相關(guān)包,初次加載可能會(huì)比較耗時(shí)。
- 并非所有 Python 包都能在 Pyodide 中使用,一些依賴本地 C/C++ 擴(kuò)展的庫需要專門移植。
二、Brython:將 Python 作為瀏覽器腳本語言
1. 什么是 Brython
Brython 是一款用 JavaScript 實(shí)現(xiàn)的 Python 解釋器,它的目標(biāo)是讓 Python 可以取代前端開發(fā)中 JavaScript 的地位。它提供了一個(gè)運(yùn)行時(shí)環(huán)境,使用純 JavaScript 解釋 Python 語法,并且封裝了一系列 DOM 操作、瀏覽器接口等,使得你可以像寫 JavaScript 一樣來操作瀏覽器對(duì)象。
2. Brython 的使用
- 引入 Brython
<script src="https://cdn.jsdelivr.net/npm/brython@3.11.0/brython.min.js"></script> <script src="https://cdn.jsdelivr.net/npm/brython@3.11.0/brython_stdlib.js"></script>
- HTML 標(biāo)記與啟動(dòng)在
<body>
標(biāo)簽中添加onload="brython()"
或者用 JavaScript 的方式在 DOM 加載后初始化 Brython:<body onload="brython()"> ... </body>
- 在
<script type="text/python">
中編寫 PythonBrython 允許我們直接在 HTML 文件中使用<script type="text/python">
標(biāo)簽來書寫前端 Python 代碼,如:這里<script type="text/python"> from browser import document, alert def greet(ev): alert("Hello from Brython!") document["mybutton"].bind("click", greet) </script>
document["mybutton"]
與 JavaScript 中的document.getElementById("mybutton")
類似。
3. 優(yōu)缺點(diǎn)
- 優(yōu)點(diǎn):
- 使用非常簡單,直接
<script type="text/python">
就能寫代碼。 - 對(duì) DOM 操作進(jìn)行了一定的封裝,可以讓 Python 代碼操作瀏覽器 API。
- 代碼體積相對(duì) Pyodide 更?。ó吘箾]有完整移植 CPython)。
- 使用非常簡單,直接
- 缺點(diǎn):
- Brython 并不包含完整的 Python 標(biāo)準(zhǔn)庫實(shí)現(xiàn),某些場景下功能有限。
- 由于是純 JavaScript 解釋,需要考慮性能影響,復(fù)雜運(yùn)算性能可能遠(yuǎn)低于 WebAssembly 方案。
- 一些 Python 第三方庫可能無法直接使用,或需要依賴特定的 Polyfill。
三、Transcrypt:Python 轉(zhuǎn)譯成 JavaScript
1. 什么是 Transcrypt
Transcrypt 是一個(gè)將 Python 代碼編譯成高質(zhì)量、可讀性較高的 JavaScript 代碼的工具。可以在開發(fā)階段用 Python 編寫邏輯,然后通過 Transcrypt 將其編譯成 JavaScript,最終在瀏覽器端運(yùn)行的還是 JavaScript。
2. 工作流程
- 安裝 Transcrypt:
pip install transcrypt
- 使用 Transcrypt 編譯 Python 文件:
transcrypt -b -m myscript.py
-b
表示在瀏覽器模式下編譯(browser)。-m
表示生成映射文件(source map)。
- 編譯完成后,會(huì)生成一個(gè)
__javascript__
文件夾,里面有myscript.js
以及依賴文件。 - 在 HTML 中引入編譯后的 JS 文件:
<script src="__javascript__/myscript.js"></script>
- 這樣,就可以在瀏覽器端使用轉(zhuǎn)換后的 JS 邏輯。
3. 優(yōu)缺點(diǎn)
- 優(yōu)點(diǎn):
- 保持了 Python 語法的開發(fā)體驗(yàn)。
- 得到的 JavaScript 體積相對(duì)較小,且沒有額外的運(yùn)行時(shí)依賴。
- 編譯后的速度與 JavaScript 本身類似(畢竟最終產(chǎn)物是 JS)。
- 缺點(diǎn):
- 并不是在瀏覽器里直接執(zhí)行 Python,而是將 Python 轉(zhuǎn)譯成 JS,某種程度上要對(duì) Python 語法有一定限制。
- 對(duì)于 Python 的某些動(dòng)態(tài)特性和部分庫支持不完美。
四、Skulpt、RapydScript 等其他方案
除上述方案外,還有一些項(xiàng)目也能幫助在前端運(yùn)行(或近似運(yùn)行)Python:
Skulpt
- 純 JavaScript 實(shí)現(xiàn)的 Python 解釋器。
- 支持 Python 語法的子集,適用于教學(xué)或簡單腳本場景。
- 不支持完整標(biāo)準(zhǔn)庫。
RapydScript
- 一種 Python-like 語法,編譯成高效的 JavaScript。
- 更接近于一種獨(dú)立的語言,兼具 Python 與 JavaScript 的特性。
Trinket、Replit 等在線平臺(tái)
- 通過遠(yuǎn)程服務(wù)器或 WebAssembly 內(nèi)嵌的方式,在網(wǎng)頁里直接運(yùn)行 Python 代碼。
- 適合教學(xué)、演示或小型項(xiàng)目試驗(yàn)。
五、適合不同場景的選擇建議
如果你希望在瀏覽器端完整運(yùn)行 Python 并使用科學(xué)計(jì)算庫(如 NumPy、Pandas 等)
- Pyodide 是首選方案,但要注意加載速度、兼容性以及內(nèi)存使用。
如果你想在前端用 Python 語法來操作 DOM,替代部分 JavaScript 功能
- Brython 可以嘗試,不過要注意第三方庫的支持以及性能。
如果你的核心需求仍然是將 Python 邏輯轉(zhuǎn)成最終的 JavaScript
- Transcrypt 可以幫助你在保持 Python 開發(fā)體驗(yàn)的同時(shí),得到優(yōu)化后的純 JS 代碼。
如果你是教學(xué)或簡單的 Python 腳本交互
- Skulpt、Trinket 這類項(xiàng)目或在線平臺(tái)可以快速上手,但功能相對(duì)有限。
六、總結(jié)
在瀏覽器里運(yùn)行 Python 不再是遙不可及的想法,隨著 WebAssembly 的普及和多種 Python-to-JavaScript 解決方案的出現(xiàn),前端與 Python 生態(tài)之間的融合將越來越緊密。選擇具體方案時(shí),需要綜合考慮:
- 是否需要大量使用 Python 第三方庫?
- 對(duì)性能與包體積的要求如何?
- 是否需要調(diào)用瀏覽器的 DOM 或 Web API?
- 是否只是教學(xué)、實(shí)驗(yàn),還是要應(yīng)用到生產(chǎn)環(huán)境?
無論是直接基于 WebAssembly 的 Pyodide、JavaScript 實(shí)現(xiàn)的 Brython,還是把 Python 編譯/轉(zhuǎn)譯為 JavaScript 的 Transcrypt,都是在不同場景下可選的思路。未來,隨著 Web 技術(shù)的進(jìn)一步發(fā)展,前端與 Python 的結(jié)合也會(huì)更容易、更高效。希望以上介紹能幫助你更好地理解和選擇前端運(yùn)行 Python 的最佳方式。
到此這篇關(guān)于如何在瀏覽器前端運(yùn)行Python程序的文章就介紹到這了,更多相關(guān)瀏覽器前端運(yùn)行Python程序內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
python實(shí)現(xiàn)的陽歷轉(zhuǎn)陰歷(農(nóng)歷)算法
這篇文章主要介紹了python實(shí)現(xiàn)的陽歷轉(zhuǎn)陰歷(農(nóng)歷)算法,需要的朋友可以參考下2014-04-04使用wxPython和OpenCV實(shí)現(xiàn)手勢識(shí)別相機(jī)功能
在這篇博客中,我將分享一個(gè)有趣的?Python?項(xiàng)目:通過?wxPython?創(chuàng)建圖形界面,利用?OpenCV?的計(jì)算機(jī)視覺技術(shù)實(shí)現(xiàn)實(shí)時(shí)手勢識(shí)別,以下是項(xiàng)目的完整實(shí)現(xiàn)過程,包括代碼分析、使用說明和可能的優(yōu)化建議,需要的朋友可以參考下2025-04-04詳解python命令提示符窗口下如何運(yùn)行python腳本
這篇文章主要介紹了詳解python命令提示符窗口下如何運(yùn)行python腳本,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-09-09Python基于opencv實(shí)現(xiàn)的人臉識(shí)別(適合初學(xué)者)
OpenCV是一個(gè)基于BSD許可開源發(fā)行的跨平臺(tái)計(jì)算機(jī)視覺庫,下面這篇文章主要給大家介紹了關(guān)于Python基于opencv實(shí)現(xiàn)的人臉識(shí)別,文中通過實(shí)例代碼介紹的非常詳細(xì),本文的教程非常適合初學(xué)者,需要的朋友可以參考下2022-03-03詳解Python如何使用PyBuilder從零開始構(gòu)建項(xiàng)目
PyBuilder是一個(gè)用于構(gòu)建Python項(xiàng)目的工具,它提供了一種簡單而強(qiáng)大的方式來管理項(xiàng)目的依賴、運(yùn)行測試、生成文檔等任務(wù),下面就跟隨小編一起來學(xué)習(xí)一下如何使用PyBuilder構(gòu)建項(xiàng)目吧2024-03-03python:接口間數(shù)據(jù)傳遞與調(diào)用方法
今天小編就為大家分享一篇python:接口間數(shù)據(jù)傳遞與調(diào)用方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2018-12-12Python 使用@property對(duì)屬性進(jìn)行數(shù)據(jù)規(guī)范性校驗(yàn)的實(shí)現(xiàn)
本文主要介紹了Python 使用@property對(duì)屬性進(jìn)行數(shù)據(jù)規(guī)范性校驗(yàn)的實(shí)現(xiàn),文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2021-10-10