HOWTO · Python

在 HTML 中執行 Python

瞭解如何在 HTML 中執行 Python

本頁內容

瀏覽器不會只因為某段程式碼放在靜態 HTML 中,就執行伺服器端的 Python。若要顯示由 Python 產生的內容,必須在伺服器上執行 Python,並將結果放入 HTTP 回應。若要整合小型程式,PHP 應用程式可以啟動 Python 程序;Django 應用程式通常則會將檢視函式的資料傳給範本。

使用 PHP 在 HTML 中執行 Python 指令碼

將頁面存成由 PHP 處理的副檔名,例如 .php,並透過已設定好的 PHP 伺服器提供。伺服器也必須安裝 Python 直譯器,且有權限啟動它。以下是完整範例:建立一個簡短的 Python 指令碼、安全地傳入兩個引數,並將擷取到的結果放進 HTTP 回應:

<?php
$pythonScript = <<<'PY'
import sys

name = sys.argv[1]
count = int(sys.argv[2])
print(f"Hello, {name}! Count: {count}")
PY;

$scriptPath = tempnam(sys_get_temp_dir(), 'page-python-');
file_put_contents($scriptPath, $pythonScript);
$command = 'python3 ' . escapeshellarg($scriptPath)
    . ' ' . escapeshellarg('Mina')
    . ' ' . escapeshellarg('3');
$result = shell_exec($command);
unlink($scriptPath);

?><!doctype html>
<html lang="en">
  <body>
    <p><?= htmlspecialchars($result ?? '', ENT_QUOTES | ENT_SUBSTITUTE, 'UTF-8') ?></p>
  </body>
</html>

此處 PHP 會啟動 python3;Python 程序會將 Mina 和 3 分別接收為 sys.argv[1] 和 sys.argv[2]。shell_exec() 會擷取程序輸出,htmlspecialchars() 則會先將輸出編碼,再插入頁面。這些內容會隨 HTTP 回應傳送給瀏覽器,不是列印到伺服器的主控台。

PHP 主機必須啟用 shell_exec(),而網頁伺服器帳戶也必須有權限執行 Python 直譯器。範例使用固定引數。若要傳入動態值,請先驗證,再使用 escapeshellarg() 個別跳脫每個引數;切勿將不受信任的輸入直接串接到 shell 指令中。若是較大型的應用程式,使用工作佇列或專用服務,可能比每次收到請求時都啟動程序更合適。

使用 Django 在 HTML 中執行 Python 指令碼

在 Django 應用程式中,將應用程式邏輯放在 Python 檢視函式中,再把結果傳給範本。範本會在伺服器上將該值轉成 HTML;瀏覽器收到的是已產生的頁面,不會執行 Python。例如,檢視函式可以準備 context = {"message": "Hello from Django"},並回傳 render(request, "page.html", context);範本則透過 {{ message }} 顯示該值。

若範本需要重複使用的呈現邏輯,自訂範本標籤會很有用。假設已安裝名為 core 的應用程式,請建立 core/templatetags/__init__.py 和 core/templatetags/my_custom_tags.py。在後者中,從 django 匯入 template,設定 register = template.Library(),並定義一個以 @register.simple_tag 裝飾的函式,例如 def greeting(): return "Hello from Django"。新增 templatetags 套件後,請重新啟動開發伺服器,讓 Django 偵測到它。

在範本中,使用 {% load my_custom_tags %} 載入模組,再以 {% greeting %} 呼叫標籤。標籤會回傳文字供伺服器端範本呈現使用;它不會在瀏覽器的 HTML 中執行任意 Python。若只是要顯示簡單的值,使用檢視函式和範本內容通常比自訂標籤更清楚。Django 也提供 date、linebreaks、safe 和 random 等內建篩選器;請參閱 Django 內建範本篩選器參考。

如果頁面載入後還需要取得資料,可以將 Django 檢視函式公開為端點,再用 fetch() 或其他 AJAX 用戶端向它發出請求。回傳敏感資料或執行操作前,請先檢查使用者是否已通過驗證並具有授權。對於會變更狀態的 POST 請求,請使用 Django 的 CSRF 防護並傳送 CSRF 權杖。僅限制端點使用 POST 並不足以確保安全。請參閱 Django CSRF 說明文件。

若要在 PHP 託管的網站中整合現有的小型 Python 指令碼,且主機允許啟動程序,可選擇由 PHP 呼叫 Python。若使用 Django 應用程式,通常透過檢視函式和範本計算並呈現頁面資料;需要重複使用範本呈現邏輯時可使用自訂標籤,而頁面載入後才需要的資料則適合透過端點取得。