1. 実際に解決したかった問題
静的サイトとPHPフォームAPIを組み合わせた構成において、ローカルからFTPクライアント(FileZilla等)を用いた手動ファイル転送は、転送漏れ、不要な開発用ファイルの混入、およびサーバー側設定ファイルの誤上書きリスクがありました。また、問い合わせ宛先メールアドレスやSMTP認証情報をGitリポジトリにコミットせずに本番サーバーへ安全に同期する仕組みが必要でした。
2. 初期構成
SLEEP LATE LABのリポジトリ(sleeplatelab-static)では、Lolipopレンタルサーバー(ライトプラン/ハイスピードプラン)を本番ホスティングとして採用しています。初期はGitHub Actionsの汎用FTP Actionを検証しましたが、TLS暗号化の強制(Explicit FTPS)とパーミッション制御において安定性に課題がありました。
3. GitHub Actions workflow
リポジトリの .github/workflows/deploy-lolipop.yml にて、ubuntu-latest ランナー上で同期用一時ディレクトリ _site/ を組み立てる構成を導入しました。以下は実際に運用している rsync フィルタリング処理です。
- name: Prepare public files
run: |
mkdir -p _site
rsync -av --delete \
--exclude='.git*' \
--exclude='.github*' \
--exclude='_site*' \
--exclude='scripts*' \
--exclude='reports*' \
--exclude='migration*' \
--exclude='*.md' \
--exclude='.DS_Store' \
./ _site/4. FTPS同期(lftp)
Linuxパッケージの lftp を使用し、明示的FTPS (FTP over TLS) を強制する設定を適用しました。--reverse モードにより、ローカルの _site/ の内容を本番ディレクトリへ正確に反映します。
lftp -u "$LOLIPOP_FTP_USERNAME,$LOLIPOP_FTP_PASSWORD" "ftp://$LOLIPOP_FTP_HOST" <<LFTP
set ftp:ssl-auth TLS
set ftp:ssl-force true
set ftp:ssl-protect-data true
set ftp:passive-mode true
set ssl:verify-certificate true
set net:max-retries 2
set net:timeout 20
mirror --reverse --parallel=2 --verbose=1 --no-perms _site/ "$LOLIPOP_SERVER_DIR"
bye
LFTP5. Secret管理とPHP設定の分離
問い合わせ受信先メールアドレスおよびSMTPログイン情報は、GitHub Repository Secrets(KOSHI_CONTACT_RECIPIENT, LOLIPOP_SMTP_PASS 等)へ格納。デプロイステップ内で runner の一時領域 $RUNNER_TEMP/contact-config.php に chmod 600 で動的生成し、単独で contact/contact-config.php へ転送する分離構成を採用しました。
6. 失敗した点
初期デプロイ時、checkout アクションのバージョン非互換(actions/checkout@v6 の誤記述)により構文エラーが発生したほか、rsync のインクルード指定が不完全で .htaccess が転送対象から漏れる失敗が発生しました(コミット a9a7bb1 で修正)。
7. 修正
actions/checkout@v4 への固定、rsync のワイルドカード排他ルールの単純化、および lftp の並列転送数 --parallel=2 への最適化により、転送エラーを解消しました。
8. Production検証
実際にGitHub Actions Run ID 31930268839 および 32229610860 でデプロイを実行した結果、合計所要時間 38秒(Job実行時間 48秒)で全静的ファイルおよび contact-config.php の同期完了を実測検証しました。
9. 現在の運用
main ブランチへの push により自動起動し、サイト構造検証スクリプト python3 scripts/check_site.py と PHP 構文検査 php -l contact/send.php が成功した場合のみ Lolipop へ安全に転送されます。
10. 学び
レンタルサーバー環境であっても、明示的FTPSとCLIツール(lftp)を組み合わせることで、SaaS型ホスティングと同等の安全かつ高速な CI/CD パイプラインをゼロコストで構築できることが実証されました。
Evidence
- リポジトリ構成ファイル:
.github/workflows/deploy-lolipop.yml - 主要修正コミット:
eb4c0ab,a9a7bb1,9ea05b2 - 本番デプロイ実測値: Run ID
32229610860(転送時間 38秒) - 検証コマンド:
gh run view 32229610860 --log