WindowsのPythonでHTTPS通信を行ったとき、ブラウザでは正常に開けるサイトなのに、Pythonでは証明書エラーになることがあります。そんなときに試したいのが truststore です。
どんなエラー?
例えば requests や urllib3 で通信したときに、次のような例外が出るケースです。
ssl.SSLCertVerificationError:
[SSL: CERTIFICATE_VERIFY_FAILED]
certificate verify failed:
unable to get local issuer certificate
原因は、信頼できる認証局(CA)までの証明書チェーンを検証できないこと。certifi のCA証明書セットとWindowsの証明書ストアの違い、中間証明書の不足、プロキシ・セキュリティソフトによるHTTPS検査などが関係する場合があります。
truststoreとは?
truststore は、PythonからOS標準の証明書検証機構を使えるようにするライブラリです。WindowsではCryptoAPIを利用します。Windows側で管理されている認証局を利用でき、中間証明書の取得などもOSの仕組みを活用できます。
ここで注意したいのは、標準のPythonがWindowsの証明書ストアを全く使わないわけではないということ。Pythonの標準sslもWindowsのCA/ROOTストアを読み込めます。ただし、証明書チェーンの検証処理などがWindowsネイティブの仕組みと異なるため、truststoreで改善するケースがあります。
導入手順はたった2ステップ
1. インストール
Python 3.10以降で利用できます。PowerShellまたはコマンドプロンプトで実行します。
py -m pip install truststore
2. プログラムの先頭で有効化
import truststore
# HTTPS関連ライブラリを読み込む前に実行
truststore.inject_into_ssl()
import requests
response = requests.get("https://www.python.org/", timeout=10)
response.raise_for_status()
print(response.status_code)
これだけです。inject_into_ssl() は、なるべくアプリケーション起動直後、requests などをインポートする前に呼び出します。すでに読み込まれたライブラリには反映されない場合があります。
なお、inject_into_ssl() はアプリケーションや単独スクリプト向けです。配布するライブラリ内部では勝手にグローバル設定を変更せず、必要に応じて truststore.SSLContext を明示的に渡す設計が推奨されています。
それでも直らない場合
- Windowsの日付と時刻が正しいか確認する。
- サーバー側の証明書の期限・ホスト名・中間証明書チェーンに問題がないか確認する。
- プロキシやウイルス対策ソフトがHTTPS通信を検査している場合、使用するCA証明書が適切に信頼されているか確認する。
- 仮想環境やEXE化環境では、実際に動いているPython・依存ライブラリ・インポート順序を確認する。
やってはいけない対処:requests.get(..., verify=False) や ssl._create_unverified_context() で証明書検証を無効化すること。エラーは消えても、中間者攻撃を検出できなくなる危険があります。
pipの証明書エラーとは別の話
pip 24.2以降は、Python 3.10以上でシステム証明書とcertifiを併用して検証する仕組みが標準で利用されています。一方、pipがそうなっていても、自作PythonアプリのHTTPS通信が自動的に全部truststoreになるわけではありません。
Windowsでブラウザだけ正常、Pythonだけ証明書検証に失敗する場合は、原因を確認したうえで truststore を試す価値があります。
