0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Laravel + Docker(PHP-FPM)で「migrateしたのにAPIの挙動が変わらない」を切り分ける手順

0
Posted at

背景

写真投稿機能に新しいカラム(place_id)を追加する実装をした(下記は実際に紐付けられた場所名が表示されている画面)。

実際に紐付けられた場所名が表示されている画面

マイグレーション・モデル・コントローラーのバリデーションを修正した。

テスト(php artisan testRefreshDatabaseで毎回マイグレーションし直す別DB)はすべてGreenだった。

しかし、実際にブラウザから操作すると「保存できない」という報告を受けた。テストが通っているのに実環境だけ動かない、という状況の切り分け手順をまとめる。

環境

  • PHP 8.4 / Laravel
  • Docker(php-fpmベースのコンテナでopcache.enable=On, opcache.validate_timestamps=Off, opcache.enable_cli=Off

原因1: 新しいmigrationが実DBに未適用だった

テストはRefreshDatabaseトレイトを使っており、テスト実行のたびにテスト専用DBに全マイグレーションを流し直す。

そのため、新しいマイグレーションファイルを作成しただけで満足してしまいがちになる。開発用の実DBに対するphp artisan migrateを忘れていても、テストではまったく気づけない。

docker exec <app_container> php artisan migrate:status

出力の該当行がPendingになっていれば未適用。php artisan migrateを実行して反映する。

原因2: opcacheでコード変更(コントローラー等)が反映されていなかった

migrationを適用してもまだ直らない場合に疑うべきなのがopcacheだ。

opcache.validate_timestamps=0(Off)にしていると、PHPはファイルの更新日時をチェックしなくなる。そのためopcache_reset()の呼び出しか、Webサーバー(php-fpmプロセス)の再起動をしない限り、修正後のコードが反映されない(公式ドキュメント)。

docker restart <app_container>

見分け方

opcache.enable_cli=Offにしている場合、CLIコマンド(php artisan route:list等)はopcacheの影響を受けないため常に最新のコードで動く。

「CLIで確認すると正しいのに、実際のHTTPリクエストだけ古い挙動のまま」という食い違いが出たら、opcacheが原因である典型的なサインになる。

まとめ

  • テストがGreenでも実DB・実環境側の反映漏れは検知できない。バックエンド変更後の動作確認では、症状を問わずまずmigrate:statusを確認する
  • opcache.validate_timestamps=Offな環境では、コード修正後にコンテナ(php-fpmプロセス)を再起動する習慣をセットにする
  • 「migrate」→「restart」の2点セットをチェックリスト化しておくと切り分けが早い

参考

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?