Helm Chart Release / release-chart (push) Successful in 5s
PHPからPythonスクリプトを呼び出す用途向けに、values.yamlの設定
だけでPython仮想環境(venv)を導入できるようにした。既存のComposer
サポートと同じ設計方針(デフォルト導入先はWebルート外・PVC非マウ
ントの使い捨て領域、packages/useRequirementsTxtの二択、
additionalApkPackagesでネイティブ拡張ビルド対応)を踏襲。
- values.yaml: python セクション新設
- templates/deployment.yaml: python3/py3-pipのAPKインストール、
venv構築、pip install処理を追加(requirements.txtの展開は
trim | nindent 14 でYAML破壊を回避、v8.5.6-dと同じ手法)
- README.md: パラメータ表・使用例(例12)・注意事項を追加
PHPからは exec('/venv/bin/python3 script.py') で呼び出す。
自動更新ワークフローによりPHP 8.5.8へのフルリリース(v8.5.8)が
先行して行われたため、本機能はそのタグの上に手動リリース 8.5.8-a
として適用する。
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
343 lines
15 KiB
YAML
343 lines
15 KiB
YAML
apiVersion: apps/v1
|
||
kind: Deployment
|
||
metadata:
|
||
name: {{ include "phpfpm.fullname" . }}
|
||
labels:
|
||
{{- include "phpfpm.labels" . | nindent 4 }}
|
||
spec:
|
||
replicas: {{ .Values.replicaCount }}
|
||
selector:
|
||
matchLabels:
|
||
{{- include "phpfpm.selectorLabels" . | nindent 6 }}
|
||
template:
|
||
metadata:
|
||
labels:
|
||
{{- include "phpfpm.selectorLabels" . | nindent 8 }}
|
||
spec:
|
||
containers:
|
||
- name: nginx
|
||
image: "{{ .Values.image.nginx.registry }}/{{ .Values.image.nginx.repository }}:{{ .Values.image.nginx.tag }}"
|
||
imagePullPolicy: {{ .Values.image.nginx.pullPolicy }}
|
||
ports:
|
||
- containerPort: 80
|
||
volumeMounts:
|
||
- name: app-storage
|
||
mountPath: /var/www/html
|
||
subPath: html
|
||
- name: nginx-config
|
||
mountPath: /etc/nginx/nginx.conf
|
||
subPath: nginx.conf
|
||
- name: php-fpm
|
||
image: "{{ .Values.image.php.registry }}/{{ .Values.image.php.repository }}:{{ .Values.image.php.tag }}"
|
||
imagePullPolicy: {{ .Values.image.php.pullPolicy }}
|
||
command:
|
||
- sh
|
||
- -c
|
||
- |
|
||
echo "Starting PHP-FPM setup process..."
|
||
|
||
{{- if or .Values.composer.enabled .Values.selenium.enabled .Values.externalDatabase.enabled .Values.python.enabled }}
|
||
# ========================================
|
||
# APKパッケージのインストール
|
||
# ========================================
|
||
APK_PACKAGES=""
|
||
|
||
{{- if or .Values.composer.enabled .Values.selenium.enabled }}
|
||
# Composer本体に必要なパッケージ
|
||
APK_PACKAGES="$APK_PACKAGES curl zip libzip-dev"
|
||
{{- end }}
|
||
|
||
{{- if .Values.externalDatabase.enabled }}
|
||
# MySQL/MariaDB接続に必要なパッケージ
|
||
APK_PACKAGES="$APK_PACKAGES mysql-client mysql-dev"
|
||
{{- end }}
|
||
|
||
{{- if .Values.smtp.enabled }}
|
||
# SMTP送信に必要なパッケージ
|
||
APK_PACKAGES="$APK_PACKAGES msmtp ca-certificates"
|
||
{{- end }}
|
||
|
||
{{- if .Values.python.enabled }}
|
||
# Python本体に必要なパッケージ
|
||
APK_PACKAGES="$APK_PACKAGES python3 py3-pip"
|
||
{{- end }}
|
||
|
||
{{- if .Values.composer.additionalApkPackages }}
|
||
# ユーザー指定の追加APKパッケージ(Composer用)
|
||
{{- range .Values.composer.additionalApkPackages }}
|
||
APK_PACKAGES="$APK_PACKAGES {{ . }}"
|
||
{{- end }}
|
||
{{- end }}
|
||
|
||
{{- if .Values.python.additionalApkPackages }}
|
||
# ユーザー指定の追加APKパッケージ(Python用)
|
||
{{- range .Values.python.additionalApkPackages }}
|
||
APK_PACKAGES="$APK_PACKAGES {{ . }}"
|
||
{{- end }}
|
||
{{- end }}
|
||
|
||
# PHP拡張(gd / mbstring)の依存パッケージを自動的に追加
|
||
{{- if .Values.composer.additionalPhpExtensions }}
|
||
for ext in {{ join " " .Values.composer.additionalPhpExtensions }}; do
|
||
if [ "$ext" = "gd" ]; then
|
||
echo "GD extension detected, adding required dependencies..."
|
||
APK_PACKAGES="$APK_PACKAGES libpng-dev libjpeg-turbo-dev freetype-dev"
|
||
fi
|
||
if [ "$ext" = "mbstring" ]; then
|
||
echo "mbstring extension detected, adding required dependencies..."
|
||
APK_PACKAGES="$APK_PACKAGES oniguruma-dev"
|
||
fi
|
||
done
|
||
{{- end }}
|
||
|
||
if [ -n "$APK_PACKAGES" ]; then
|
||
echo "Installing APK packages: $APK_PACKAGES"
|
||
apk add --no-cache $APK_PACKAGES
|
||
fi
|
||
|
||
# ========================================
|
||
# PHP拡張のインストール
|
||
# ========================================
|
||
{{- if or .Values.composer.enabled .Values.selenium.enabled }}
|
||
echo "Installing PHP zip extension..."
|
||
docker-php-ext-install zip
|
||
{{- end }}
|
||
|
||
{{- if .Values.externalDatabase.enabled }}
|
||
echo "Installing pdo_mysql extension..."
|
||
docker-php-ext-install pdo_mysql
|
||
{{- end }}
|
||
|
||
{{- if .Values.composer.additionalPhpExtensions }}
|
||
echo "Installing additional PHP extensions..."
|
||
{{- range .Values.composer.additionalPhpExtensions }}
|
||
docker-php-ext-install {{ . }}
|
||
{{- end }}
|
||
{{- end }}
|
||
|
||
# ========================================
|
||
# Composerのインストールと実行
|
||
# ========================================
|
||
{{- if or .Values.composer.enabled .Values.selenium.enabled }}
|
||
echo "Installing Composer..."
|
||
curl -sS https://getcomposer.org/installer | php -- --install-dir=/usr/local/bin --filename=composer
|
||
|
||
# Composer導入先(デフォルトはWebルート外の /composer)
|
||
# PHPからは require_once '{{ .Values.composer.workingDir | default "/composer" }}/vendor/autoload.php'; で読み込む
|
||
mkdir -p {{ .Values.composer.workingDir | default "/composer" }}
|
||
cd {{ .Values.composer.workingDir | default "/composer" }}
|
||
|
||
{{- if .Values.composer.enabled }}
|
||
# ユーザー定義のComposer設定
|
||
{{- if .Values.composer.useComposerJson }}
|
||
# composer.jsonファイルを使用
|
||
echo "Creating composer.json from values..."
|
||
cat > composer.json << 'COMPOSER_JSON_EOF'
|
||
{{- .Values.composer.composerJson | trim | nindent 14 }}
|
||
COMPOSER_JSON_EOF
|
||
|
||
{{- if .Values.composer.composerLock }}
|
||
echo "Creating composer.lock from values..."
|
||
cat > composer.lock << 'COMPOSER_LOCK_EOF'
|
||
{{- .Values.composer.composerLock | trim | nindent 14 }}
|
||
COMPOSER_LOCK_EOF
|
||
{{- end }}
|
||
|
||
echo "Running composer install..."
|
||
composer install {{ .Values.composer.installOptions }}
|
||
|
||
{{- else if .Values.composer.packages }}
|
||
# パッケージリストから直接インストール
|
||
echo "Installing Composer packages..."
|
||
{{- range .Values.composer.packages }}
|
||
composer require {{ . }}
|
||
{{- end }}
|
||
|
||
{{- if .Values.composer.installOptions }}
|
||
# オプティマイズ実行
|
||
composer install {{ .Values.composer.installOptions }}
|
||
{{- end }}
|
||
|
||
{{- else }}
|
||
# 旧Webルート(/var/www/html)に composer.json がある場合は移行(v8.5.6-a以前からのアップグレード対応)
|
||
if [ ! -f composer.json ] && [ -f /var/www/html/composer.json ]; then
|
||
echo "Migrating legacy composer files from /var/www/html to $(pwd)..."
|
||
mv /var/www/html/composer.json ./composer.json
|
||
if [ -f /var/www/html/composer.lock ]; then mv /var/www/html/composer.lock ./composer.lock; fi
|
||
if [ -d /var/www/html/vendor ]; then mv /var/www/html/vendor ./vendor; fi
|
||
fi
|
||
# composer.jsonが既に存在する場合はそれを使用
|
||
if [ -f composer.json ]; then
|
||
echo "Found existing composer.json, running composer install..."
|
||
composer install {{ .Values.composer.installOptions }}
|
||
else
|
||
echo "No composer configuration found, skipping package installation"
|
||
fi
|
||
{{- end }}
|
||
{{- end }}
|
||
|
||
{{- if .Values.selenium.enabled }}
|
||
# Selenium用のパッケージインストール(レガシー互換性)
|
||
echo "Installing Selenium WebDriver package..."
|
||
composer require php-webdriver/webdriver
|
||
{{- end }}
|
||
{{- end }}
|
||
{{- end }}
|
||
|
||
{{- if .Values.python.enabled }}
|
||
{{- $pythonDir := .Values.python.venvDir | default "/venv" }}
|
||
# ========================================
|
||
# Python仮想環境のセットアップ
|
||
# ========================================
|
||
echo "Setting up Python virtual environment..."
|
||
|
||
# Python導入先(デフォルトはWebルート外の /venv、Composerと同様の使い捨て領域)
|
||
# PHPからの呼び出し方: exec('{{ $pythonDir }}/bin/python3 /path/to/script.py 2>&1', $output, $exitCode);
|
||
python3 -m venv {{ $pythonDir }}
|
||
|
||
{{- if .Values.python.useRequirementsTxt }}
|
||
echo "Creating requirements.txt from values..."
|
||
cat > /tmp/requirements.txt << 'REQUIREMENTS_TXT_EOF'
|
||
{{- .Values.python.requirementsTxt | trim | nindent 14 }}
|
||
REQUIREMENTS_TXT_EOF
|
||
|
||
echo "Installing Python packages from requirements.txt..."
|
||
{{ $pythonDir }}/bin/pip install {{ .Values.python.installOptions }} -r /tmp/requirements.txt
|
||
rm -f /tmp/requirements.txt
|
||
|
||
{{- else if .Values.python.packages }}
|
||
echo "Installing Python packages..."
|
||
{{- range .Values.python.packages }}
|
||
{{ $pythonDir }}/bin/pip install {{ $.Values.python.installOptions }} "{{ . }}"
|
||
{{- end }}
|
||
|
||
{{- else }}
|
||
echo "No Python package configuration found, virtual environment created without additional packages"
|
||
{{- end }}
|
||
{{- end }}
|
||
|
||
{{- if .Values.smtp.enabled }}
|
||
# ========================================
|
||
# SMTP設定(msmtp)
|
||
# ========================================
|
||
echo "Configuring SMTP for mail sending..."
|
||
|
||
# msmtprc設定ファイルをコピー
|
||
# msmtpはPHP-FPMワーカー(www-data等の非root)から実行されるため、
|
||
# rootが作成するこのファイルも読み取り可にする必要がある
|
||
# (実パスワードはpasswordeval経由で別ファイルから取得するため、
|
||
# msmtprc自体に平文パスワードは含まれない)
|
||
cp /etc/smtp-config/msmtprc /etc/msmtprc
|
||
chmod 644 /etc/msmtprc
|
||
|
||
# PHP設定をphp.ini.d/に作成
|
||
cat > /usr/local/etc/php/conf.d/99-smtp.ini << 'PHP_SMTP_EOF'
|
||
; SMTP設定 - msmtp経由でメール送信
|
||
sendmail_path = "/usr/bin/msmtp -t"
|
||
sendmail_from = "{{ .Values.smtp.from }}"
|
||
PHP_SMTP_EOF
|
||
|
||
echo "SMTP configured:"
|
||
echo " Host: {{ .Values.smtp.host }}:{{ .Values.smtp.port }}"
|
||
echo " Protocol: {{ .Values.smtp.protocol }}"
|
||
echo " From: {{ .Values.smtp.from }}"
|
||
{{- end }}
|
||
|
||
echo "Setup complete, starting PHP-FPM..."
|
||
php-fpm
|
||
ports:
|
||
- containerPort: 9000 # PHP-FPMは9000ポートでリッスン
|
||
volumeMounts:
|
||
# PVCルートを /var/www にマウント
|
||
# - /var/www/html のみ nginx が公開(nginx側は html サブパスだけをマウント)
|
||
# - それ以外(/var/www/<任意>)は非公開ファイルの格納先として利用可能
|
||
# ※ Composer導入先(デフォルト /composer)は意図的にマウントしない:
|
||
# Pod再起動のたびにクリーンな環境へ再構築される使い捨て領域とする
|
||
- name: app-storage
|
||
mountPath: /var/www
|
||
{{- if and .Values.composer.enabled .Values.composer.useComposerJson }}
|
||
- name: composer-config
|
||
mountPath: /tmp/composer-init
|
||
{{- end }}
|
||
{{- if .Values.smtp.enabled }}
|
||
- name: smtp-config
|
||
mountPath: /etc/smtp-config
|
||
readOnly: true
|
||
{{- if .Values.smtp.auth.enabled }}
|
||
- name: smtp-secrets
|
||
mountPath: /etc/smtp-secrets
|
||
readOnly: true
|
||
{{- end }}
|
||
{{- end }}
|
||
env:
|
||
{{- if .Values.externalDatabase.enabled }}
|
||
- name: DB_HOST
|
||
value: {{ .Values.externalDatabase.host | quote }}
|
||
- name: DB_PORT
|
||
value: {{ .Values.externalDatabase.port | quote }}
|
||
- name: DB_NAME
|
||
value: {{ .Values.externalDatabase.database | quote }}
|
||
- name: DB_USER
|
||
value: {{ .Values.externalDatabase.username | quote }}
|
||
- name: DB_PASS
|
||
valueFrom:
|
||
secretKeyRef:
|
||
name: {{ include "phpfpm.fullname" . }}-db-secret
|
||
key: {{ include "phpfpm.fullname" . }}-db-key
|
||
{{- end }}
|
||
{{- range $key, $value := .Values.phpEnv }}
|
||
- name: {{ $key }}
|
||
value: {{ $value | quote }}
|
||
{{- end }}
|
||
{{- if .Values.selenium.enabled }}
|
||
- name: selenium
|
||
image: "{{ .Values.image.selenium.registry }}/{{ .Values.image.selenium.repository }}:{{ .Values.image.selenium.tag }}"
|
||
imagePullPolicy: {{ .Values.image.selenium.pullPolicy }}
|
||
ports:
|
||
- containerPort: 4444 # Selenium用ポート
|
||
volumeMounts:
|
||
- name: app-storage
|
||
mountPath: /var/www/html
|
||
subPath: html
|
||
{{- end }}
|
||
dnsPolicy: ClusterFirst
|
||
dnsConfig:
|
||
options:
|
||
- name: ndots
|
||
value: "1"
|
||
volumes:
|
||
- name: app-storage
|
||
{{- if .Values.persistence.enabled }}
|
||
persistentVolumeClaim:
|
||
claimName: {{ include "phpfpm.fullname" . }}-pvc
|
||
{{- else }}
|
||
emptyDir: {}
|
||
{{- end }}
|
||
- name: nginx-config
|
||
configMap:
|
||
name: {{ include "phpfpm.fullname" . }}-nginx-config
|
||
{{- if and .Values.composer.enabled .Values.composer.useComposerJson }}
|
||
- name: composer-config
|
||
configMap:
|
||
name: {{ include "phpfpm.fullname" . }}-composer-config
|
||
{{- end }}
|
||
{{- if .Values.smtp.enabled }}
|
||
- name: smtp-config
|
||
configMap:
|
||
name: {{ include "phpfpm.fullname" . }}-smtp-config
|
||
items:
|
||
- key: msmtprc
|
||
path: msmtprc
|
||
{{- if .Values.smtp.auth.enabled }}
|
||
- name: smtp-secrets
|
||
secret:
|
||
secretName: {{ include "phpfpm.fullname" . }}-smtp
|
||
items:
|
||
- key: password
|
||
path: password
|
||
# 0600だとSecretボリュームの所有者はroot、
|
||
# msmtpはPHP-FPMワーカー(www-data等の非root)から実行されるため読めない
|
||
# → 全ユーザー読み取り可にする(ボリュームはPod内にしか存在しないため許容範囲)
|
||
mode: 0644
|
||
{{- end }}
|
||
{{- end }} |