シンプルなSymfony 4プロジェクトをDockerコンテナーで実行しようとしています。私は通常のPHPスクリプトをテストしましたが、それらは非常にうまく機能します。しかし、Symfonyプロジェクトでは、実行が途方もなく遅くなります。たとえば、重要なコンテンツのないページは5〜6秒かかります。
Symfonyのパフォーマンスプロファイラーのスクリーンショットを添付しました。
この実行時間を許容可能なレベルに削減する方法について何か考えがありますか?
提供された回答はmacOSXでのみ機能するため、Docker for Windowsにはパフォーマンスの問題が存在するだけでなく、推奨される回答は私の場合は役に立ちませんでした。私は、SOでの同様の質問への回答で部分的に説明されているさまざまなアプローチに従っていました。
パフォーマンスのベストプラクティス によると、Symfonyアプリケーションのvendor
やvar
などの負荷の高いフォルダーは、共有マウントの一部であってはなりません。これらのフォルダーを永続化する必要がある場合は、代わりにボリュームを使用する必要があります。
/app
の共有ボリュームへの干渉を防ぐため、これら2つのフォルダーをコンテナー内の別のフォルダー/symfony
に再配置しました。 Dockerfileフォルダーには、/symfony/var
および/symfony/vendor
が追加で作成されます。
コンテナの開始時に実行されるスクリプトは、シンボリックリンクを/app/var
から/symfony/var
へ、および/app/vendor
から/symfony/vendor
へ設定しています。これらの2つの新しいフォルダーは、ボリュームにマウントされます。 docker-compose.yml
ファイル内。
これが私がDockerfileにaddingしたものです:
RUN mkdir /app && mkdir /symfony/{var,vendor}
COPY setup-symfony.sh /setup-symfony.sh
VOLUME /symfony/var
VOLUME /symfony/vendor
これは、composer update
またはbin/console
を介したタスクを呼び出す直前に起動スクリプトにaddingしたものです。
[ -e /app/var ] || ln -s /symfony/var /app/var
[ -e /app/vendor ] || ln -s /symfony/vendor /app/vendor
これが最終的に私の構成は次のようになります。
version: "3.5"
services:
database:
build:
context: docker/mysql
volumes:
- "dbdata:/var/lib/mysql"
environment:
MYSQL_ALLOW_EMPTY_PASSWORD: 1
application:
depends_on:
- database
build:
context: docker/lamps
ports:
- "8000:8000"
volumes:
- ".:/app:cached"
- "var:/symfony/var"
- "vendor:/symfony/vendor"
environment:
DATABASE_URL: mysql://dbuser:dbuser@database/dbname
volumes:
dbdata:
var:
vendor:
この設定を使用すると、symfonyは4000ミリ秒以上かかるのではなく、500ミリ秒以内に応答します。
UPDATE:IDEを使用してPhpStormのようなSymfonyベースのアプリケーションを開発する場合、vendor /コードアシストまたは同様のもの。私の場合、それらのファイルのスナップショットを撮って、ホストと共有されている別のフォルダーに置くことができました。 、ただしSymfony/PSRでは積極的に使用されていません(例:vendor.dis /)。このスナップショットは、インストール/アップグレードごとに手動で取得されます(例:次のようにシェルでコンテナを実行する:
docker exec -it IDofContainer /bin/sh
次に、シェルで呼び出します
cp -Lr vendor vendor.dis
パス名を修正するか、最初にアプリを含むフォルダーに切り替える必要があるかもしれません。
PhpStormを使用している私の場合、vendor.dis /はバックグラウンドインデックスによって取得され、コードインスペクションとコードアシストに従いました。 Visual Studioコードには、gitに関する多くの追跡されていない変更に関する問題があったため、このスナップショットをgitによって明示的に無視させ、。gitignoreファイル。
整合性レベルを変更すると、Symfonyのパフォーマンスが大幅に向上するようです。 ( Docker docs を参照)
これが私の新しいdocker-compose.ymlファイルです。ボリュームの後にある「:cached」に注意してください。
version: '3'
services:
web:
image: Apache-php7
ports:
- "80:80"
volumes:
- .:/app:cached
tty: true
Dockerファイルで、ベンダーフォルダーがコンテナーと同期しないようにすることができます。フォルダが非常に大きくなるため、これはパフォーマンスに最大の影響を与えます。
#DockerFile:
volumes:
- /local/app:/var/www/html/app
- /var/www/html/app/vendor # ignore vendor folder
これにより、ビルド後、およびcomposer依存関係を更新するときに、ベンダーフォルダーを手動でコンテナーに手動でコピーする必要があります。
docker cp /local/app/vendor <CONTAINER_ID>:/var/www/html/app/
あなたのsrc/Kernel.php:
public function getCacheDir()
{
// for docker performance
if ($this->getEnvironment() === 'test' || $this->getEnvironment() === 'dev') {
return '/tmp/'.$this->environment;
} else {
return $this->getProjectDir().'/var/cache/'.$this->environment;
}
}
開発環境でのボリュームマウントに委任モードを使用します。
委任:コンテナーのビューは信頼できます(コンテナーの更新がホストに表示される前に遅延を許可) ボリュームマウントのDockerパフォーマンスチューニング
これはdev envrionemtnsにとって理にかなっています。通常は、コンテナ内ではないホストでIDEを使用してコードを変更し、コンテナに同期します。#DockerFile:
volumes:
- /local/app:/var/www/html/app:delegated
dockerがデバッグモードでないかどうかを確認します。
docker info
# It Should display: Debug Mode: false
Docker-configで無効化:
{
"debug": false,
}