本頁面說明如何從第一代遷移至 Python 的第二代執行階段。如要升級第二代應用程式,以便使用最新支援的 Python 版本,請參閱「升級現有應用程式」。
Python 2.7 已於 2024 年 1 月 31 日停止支援。現有的 Python 2.7 應用程式將繼續執行並接收流量。不過,如果應用程式使用已停用支援的日期後的執行階段,App Engine 可能會阻止重新部署該應用程式。建議您按照本頁面中的規範,改用最新的支援版本 Python。
遷移至 Python 3 執行階段後,您就能使用最新的語言功能,並透過慣用程式碼建構更易於移植的應用程式。Python 3 執行階段會使用 Python Software Foundation 提供的最新版開放原始碼 Python 解譯器。內建 Python 3 執行階段的應用程式可以在 requirements.txt
檔案中宣告依附元件,以便在應用程式中使用 Python 豐富的套件與架構生態系統,包括使用 C 程式碼的套件與架構。
執行階段遷移程序總覽
我們建議您採用下列漸進式方法進行執行階段遷移作業,在整個過程中維持可運作且可測試的應用程式:
升級應用程式,使其與 Python 3 相容。
您可以使用多種解決方案來進行升級。例如,使用 Six、Python-Future 或 Python-Modernize。
如要進一步瞭解執行階段遷移程序的這個步驟,請前往 Python Software Foundation 說明文件網站,參閱「將 Python 2 程式碼移植到 Python 3」。
針對應用程式使用的任何 App Engine 套裝服務,請選擇下列其中一種實作策略:
將 Python 2 應用程式中的舊版套裝組合服務遷移至未套裝組合的 Google Cloud 服務、第三方服務或其他建議的替代方案。
繼續在 Python 3 應用程式中使用舊版套裝服務。這種做法可讓您在遷移週期後半階段靈活地改用非捆綁服務。
請務必在遷移每項服務後測試應用程式。
為 Python 3 執行階段準備 App Engine 設定檔案。以下幾項重要變更會影響
app.yaml
中的設定,包括但不限於:- 系統現在會假設應用程式具備「執行緒安全」特性。如果應用程式不安全,您應將
app.yaml
中的max_concurrent_requests
設為 1。這項設定可能會導致建立的執行個體數量超過執行緒安全應用程式所需的數量,進而產生不必要的費用。 app.yaml
檔案不再將要求轉送至指令碼。您必須改用內建應用程式內轉送功能的網路架構,並更新或移除app.yaml
中的所有script
處理常式。如需使用 Flask 架構執行此操作的範例,請參閱 GitHub 中的 App Engine 遷移指南程式碼範例。如要進一步瞭解如何變更這個設定檔和其他設定檔,請參閱「設定檔」一節。
- 系統現在會假設應用程式具備「執行緒安全」特性。如果應用程式不安全,您應將
在第二代執行階段中,應用程式記錄不再巢狀於要求記錄中。您必須採取額外步驟,才能在記錄檔探索工具中顯示要求和應用程式記錄的巢狀檢視畫面。詳情請參閱「遷移至 Cloud Logging」。
在 Python 3 環境中測試及部署已升級的應用程式。
所有測試都通過後,請將升級版應用程式部署至 App Engine,但請勿讓流量自動轉送至新版本。使用流量分割功能,將流量從 Python 2 執行階段的應用程式,緩慢遷移至 Python 3 執行階段的應用程式。如果遇到問題,您可以將所有流量轉送至穩定版本,直到問題修正為止。
如需將 Python 2 應用程式轉換為 Python 3 的範例,請參閱這些額外資源。
Python 2 和 Python 3 執行階段的主要差異
您在執行階段遷移期間需要進行的大部分變更,都來自 Python 2 和 Python 3 執行階段之間的以下差異:
- 記憶體用量差異
- CPU 用量差異
- 要求標頭差異
- Gunicorn worker 的差異
- Python 2 和 Python 3 之間的相容性問題
- Python 3 執行階段中的 App Engine 套裝組合服務
- 設定檔差異
- 需要網路架構才能將動態內容要求重新導向
- 僅含靜態內容的應用程式
- 測試差異
- 部署作業差異
記憶體用量差異
與第一代執行階段相比,第二代執行階段的記憶體使用量基準較高。這可能是由多種因素造成,例如不同的基礎映像檔版本,以及兩個世代計算記憶體用量的方式不同。
第二代執行階段會將執行個體記憶體用量計算為應用程式程序使用的用量總和,以及記憶體中動態快取的應用程式檔案數量。為避免記憶體密集型應用程式因超出記憶體限制而導致執行個體關閉,請升級至記憶體較多的執行個體類別。
CPU 用量差異
在執行個體冷啟動時,第二代執行階段可看到較高的 CPU 使用率基準。視應用程式的縮放設定而定,這可能會產生非預期的副作用,例如,如果應用程式已設為根據 CPU 使用率進行縮放,則執行個體數量可能會高於預期。為避免發生這個問題,請查看並測試應用程式縮放設定,確保可用的執行個體數量。
要求標頭差異
第一代執行階段允許將含有底線的請求標頭 (例如 X-Test-Foo_bar
) 轉送至應用程式。第二代執行階段會將 Nginx 導入主機架構。因此,第二代執行階段會自動移除含有底線 (_
) 的標頭。為避免應用程式發生問題,請避免在應用程式要求標頭中使用底線。
Gunicorn 工作者差異
對於 Python 3 以上版本的執行階段,Gunicorn 工作站數會直接影響記憶體用量。記憶體用量增加的幅度與工作站數量增加的幅度成正比。如要減少記憶體耗用量,請考慮減少 Gunicorn 工作站的數量。如需設定 Gunicorn 工作者人數的操作說明,請參閱進入點最佳做法
Python 2 和 Python 3 之間的相容性問題
Python 3 於 2008 年首次發布時,該語言導入了幾項與前版不相容的變更。其中有些變更只需要對程式碼進行小幅更新,例如將 print
陳述式變更為 print()
函式。其他變更可能需要大幅更新程式碼,例如更新處理二進位資料、文字和字串的方式。
許多熱門開放原始碼程式庫 (包括 Python 標準程式庫) 在從 Python 2 移至 Python 3 時也有所變更。
Python 3 執行階段中的 App Engine 套裝組合服務
為減少遷移作業的複雜度和難度,App Engine 標準環境可讓您在 Python 3 執行階段存取許多舊版套裝服務和 API,例如 Memcache。Python 3 應用程式可以透過語言慣用程式庫呼叫套裝組合服務 API,並存取與 Python 2 執行階段相同的功能。
您也可以選擇使用 Google Cloud 與舊版套裝組合服務類似的產品。建議您考慮遷移至未綁定的 Google Cloud 產品,這樣一來,您就能享有持續改善和新功能帶來的優勢。
如果是Google Cloud中沒有提供的獨立產品,例如圖片處理、搜尋和訊息服務,您可以使用建議的第三方供應商或其他解決方法。
設定檔
您可能需要變更 App Engine 使用的部分設定檔,才能在 App Engine 標準環境的 Python 3 執行階段中執行應用程式:
app.yaml
:app.yaml
設定檔中部分欄位的行為已受到修改。移除所有已淘汰的欄位,並按照遷移指南所述更新其他欄位。requirements.txt
。建立這個檔案即可安裝第三方依附元件,包括需要原生 C 擴充功能的 Python 套件。在 Python 3 執行階段中,App Engine 會在應用程式部署期間自動安裝這些依附元件。先前,如要在 Python 2 執行階段安裝依附元件,您必須在這個檔案中列出複製或自行封裝的程式庫,然後執行pip install -t lib -r requirements.txt
指令,或是在 app.yaml 檔案中列出應用程式所需的「內建」第三方程式庫。appengine_config.py
。這個檔案不會用於 Python 3 執行階段,如果部署,系統會忽略這個檔案。在 Python 2 執行階段中,這個檔案用於設定 Python 模組,並將應用程式指向複製或自行封裝的第三方程式庫。
用於將動態內容要求轉送至適當位置的網路架構
在 Python 2 執行階段中,您可以在 app.yaml
檔案中建立網址處理常式,以便在要求特定網址或網址模式時指定要執行的應用程式。
在 Python 3 執行階段中,應用程式必須使用 Flask 或 Django 等網路架構,將動態內容要求轉送至 app.yaml
,而非使用 URL 處理常式。針對靜態內容,您可以繼續在應用程式的 app.yaml
檔案中建立網址處理常式。
僅含靜態內容的應用程式
在 App Engine 上託管靜態網頁應用程式時,您可以在 app.yaml
檔案中指定處理常式,將網址對應至靜態檔案。
在 Python 2 中,如果要求不符合 app.yaml
檔案中指定的任何處理常式,App Engine 會傳回 404
錯誤代碼。
在 Python 3 中,如果要求不符合任何處理常式,App Engine 會尋找 main.py
檔案,如果找不到 main.py
檔案,就會傳回 5xx
錯誤。由於僅含靜態內容的 App Engine 應用程式不需要 main.py
檔案,因此除了在應用程式記錄中看到執行個體啟動錯誤之外,大多數使用者也會看到這項錯誤。
如要維持相同的行為,在沒有任何靜態處理常式相符時傳回 404
錯誤,並避免記錄中出現錯誤,您可以:
- 在
app.yaml
檔案中新增指向空白目錄的全部接收靜態處理常式 - 在
main.py
檔案中新增簡單的動態應用程式,以便傳回404
錯誤
使用這兩種選項的範例:
app.yaml
在根應用程式目錄中建立空白目錄,例如 empty/
。在 app.yaml
檔案的處理常式區段中,在最末端建立新的處理常式,以便擷取所有其他網址模式,並在 static_files
和 upload
元素中指定 empty
目錄:
handlers:
- url:
.
.
.
- url: /(.*)$
static_files: empty/\1
upload: empty/.*$
main.py
建立 main.py
檔案,並加入下列程式碼,以便傳回 404
錯誤:
def app(env, start_response):
start_response('404 Not Found', [('Content-Type','text/html')])
return [b"Not Found"]
測試
建議您使用 Python 慣用的測試方法,而非依附於 dev_appserver
的測試方法。舉例來說,您可以使用 venv
建立獨立的本機 Python 3 環境,並且使用任何標準 Python 測試架構來編寫自己的單元、整合功能和系統測試。您也可以考慮設定開發版本的服務,或是使用適用於許多 Google Cloud 產品的本機模擬器。
您也可以選擇使用支援 Python 3 的 dev_appserver
預覽版。如要進一步瞭解這項測試功能,請參閱「使用本機開發伺服器」。
部署中
Python 3 不支援透過 appcfg.py
進行部署。請改用 gcloud
指令列工具部署應用程式。
記錄
Python 3 執行階段的記錄功能會遵循 Cloud Logging 的記錄標準。在 Python 3 執行階段中,應用程式記錄不再與要求記錄綁在一起,而是分開記錄。如要進一步瞭解如何在 Python 3 執行階段中讀取及寫入記錄,請參閱記錄指南。
其他遷移資源
如要進一步瞭解如何將 App Engine 應用程式遷移至獨立 Cloud 服務或 Python 3 執行階段,請參閱下列 App Engine 資源: