Symfony Component Advent Calendar 2022の 6日目の記事です。
最初に
SymfonyはPHPのフレームワークのひとつです。しかし、公式サイトの説明文には
Symfony is a set of PHP Components, a Web Application framework, a Philosophy, and a Community — all working together in harmony.
(SymfonyはPHPコンポーネントのセットで、Webアプリケーションフレームワークで、哲学、そしてコミュニティです。それらがハーモニーを奏でながら動作しています。)
と書かれている通り、PHPコンポーネントのセットで、たくさんのコンポーネントを提供しており、それらを組み合わせてひとつのフレームワークとして動作しています。Symfonyのコンポーネントは、Symfony上だけで動作するのではなく、他のPHPフレームワークやアプリケーションでも動作している強力なものが揃っています。
今回はそれらの中から、役立ちそうなもの・お薦めしたいものを紹介していきたいと思います。
※記事内ではautoloadのインポートは省略します。
環境変数を扱う、"Dotenv"
Dotenvは、.env
ファイルを使って環境変数を扱います。こちらもSymfony以外で動作します。
インストール
composer require symfony/dotenv
.envとは
.env
とは環境ごとに異なる値を定義するためのファイルです。たとえばデータベースの接続情報を直接プログラムに記載すると、テスト環境や本番環境での接続先がひとつになってしまいますが、環境ごとに.env
に設定し、その情報をもとにDBに接続すれば、環境ごとに接続先を変えることができます。
APP_ENV=dev
DATABASE_HOST=localhost
DATABASE_NAME=my_db
DATABASE_USER=root
DATABASE_PASSWORD=strong_password
※環境ごとの.envの作り方に関しては後述
.envを読み込む
.envを読み込むにはDotenv
クラスを使います。
use Symfony\Component\Dotenv\Dotenv;
$dotenv = new Dotenv();
$dotenv->load(__DIR__.'/.env');
// loads .env, .env.local, and .env.$APP_ENV.local or .env.$APP_ENV
$dotenv->loadEnv(__DIR__.'/.env');
load()
メソッドの場合は純粋に指定した.env
ファイルのみを参照します。loadEnv()
メソッドの場合は、該当するファイルに加えて、.env.local
, '.env.{APP_ENV}.local, '.env.{APP_ENV}
ファイルwも参照します。
環境変数を利用する(通常版)
通常は$_ENV
変数を利用すれば値を利用できます。
$dotenv = new Dotenv();
$dotenv->load(__DIR__.'/.env');
print_r($_ENV);
Array
(
[APP_ENV] => dev
[DATABASE_HOST] => localhost
[DATABASE_NAME] => my_db
[DATABASE_USER] => root
[DATABASE_PASSWORD] => strong_password
[SYMFONY_DOTENV_VARS] => APP_ENV,DATABASE_HOST,DATABASE_NAME,DATABASE_USER,DATABASE_PASSWORD
)
追加でSYMFONY_DOTENV_VARS
というキーに対して、Dotenvを使って設定したキーのリストが格納されています。
環境変数を利用する(Symfony版)
Symfonyでも$_ENV
にアクセスすれば利用できますが、基本的には環境変数の値はパラメータに設定した後に、DIでそれぞれのクラスに渡します。
一見めんどくさそうに見えますが、環境変数の値に依存しなくなります。
parameters:
app.database_host: '%env(DATABASE_HOST)%'
services:
APP\Service\SomeService:
arguments:
$host: '%app.database_host%'
class SomeService
{
public function __construct(private readonly string $host)
{
echo($this->host); // -> localhost
}
}
Symfonyでの.envの考え方
Symfonyではいくつか.envの種類が用意されています。それぞれの役割は以下の通りです。
ファイル名 | 用途 |
---|---|
.env | アプリケーションで必要な環境変数の名前とデフォルト値を定義 |
.env.local | 実行マシン上で扱う環境変数の値を追加・上書きします |
.env.{環境名} | APP_ENVで定義された環境名で実行する際に、扱う環境変数のデフォルト値を追加・上書きします |
.env.{環境名}.local | 実行マシン上でAPP_ENVで定義された環境名で実行する際に、扱う環境変数の値を追加・上書きします |
.env
, .env.{環境名}
にはデフォルト値をセットします。イメージ的には扱う環境変数の名前をセットすると思ってもらうとよいかもしれません。
ここに設定された環境変数がないとアプリケーションが動かないためにセットするもので、よって、Symfonyでは .env
, .env.{環境名}
はコミット対象です。
.env.local
, .env.{環境名}.local
は主に歯値を上書きするために利用します。上記で挙げた例のデータベース情報などのセンシティブな情報は、環境ごとにこちら側に定義するのが理想です。よって、 .env.local
, .env.{環境名}.local
はコミット対象外です。
(Symfonyインストール時に、.gitignore
に指定されています)
さらに、実行マシンに設定された環境変数($_ENV
, $_SERVER
)で上書きをするので、それぞれの優先順位は以下のようになります。
優先順位 | ファイル |
---|---|
1 | 実行マシンの環境変数 |
2 | .env.{環境名}.local |
3 | .env.{環境名} |
4 | .env.local |
5 | .env |
まとめ
今回はDotenvを紹介しました。Symfonyでの.env
の取り扱いや値の利用方法は他のフレームワークと比較すると特殊ですが、『なるべく環境に依存することなく、動かせるところまでは動かす』という力強さが感じられます。