2017-07-05 7 views
3

私は、モノリシックなPHP SymfonyアプリケーションをDockerを使っていくらか拡張性のあるソリューションに移行しようとしています。アプリケーションとRabbitMQとの間には通信があり、私はdocker-composeを使用してすべてのコンテナ(この場合はアプリとRabbitMQサーバー)を持ち込みます。ドッキングされたRabbitMQをどのように構造化すればよいですか?

あり、トピックの周りの議論の多くは、一つの容器が一つだけプロセスを生成する必要があるということです、そしてDocker best practicesはこの点ややあいまいです:

このマントラは善意を持っていますが、それは必ずしも真実ではありませんその コンテナごとに1つのオペレーティングシステムプロセスが必要です。 では、コンテナがinit プロセスで生成されるという事実に加えて、いくつかのプログラムでは、独自のプロセスである の追加プロセスが生成されることがあります。

各RabbitMQコンシューマに対して別々のDockerコンテナを作成することは理にかなっていますか?それは、 "正しい"と "きれいな"気がして、キューを処理するために使用される言語/ツールをrabbitmqサーバに知らせないようにします。私はnohupを使用してrabbitmq_consumerコンテナまたはバックグラウンドでそれらを実行している他のいくつかの方法で、いくつかの消費者を実行することができ

app : 
    # my php-fpm app container 

    rabbitmq_server: 
    container_name: sf.rabbitmq_server 
    build: .docker/rabbitmq 
    ports: 
     - "15672:15672" 
     - "5672:5672" 
    networks: 
     - app_network 

    rabbitmq_consumer: 
    container_name: sf.rabbit_consumer 
    extends: app 
    depends_on: 
     - rabbitmq_server 
    working_dir: /app 
    command: "php bin/console rabbitmq:consumer test" 
    networks: 
     - app_network 

:私は(docker-compose.ymlの関連部分)を思い付きました。

私は私の質問があると思います。毎回

私は(ansibleのように、など)ドッカーの「ビルドスクリプト」を編集する必要がないように、私は何とか、「新しい消費者を追加」を自動化することができます新しい消費者がコードから追加されますか?

RabbitMQサーバーをコンシューマーから分離することは理にかなっていますか、またはラビットサーバーをバックグラウンドで実行しているラビットサーバーを使用する必要がありますか?

または、それらをアプリコンテナの背景に配置する必要がありますか?

答えて

3

私は自分の経験を共有して、それについて批判的に考えます。

コンシューマーは、Webアプリケーションとは別のコンテナで実行する必要があります。コンシューマコンテナは、プロセスマネージャlike theseを実行します。その責任は、子コンシューマプロセッサを生成し、終了した場合は再起動し、SIGUSR1信号にリロードし、SIGTERMで正しくシャットダウンします。メインプロセスが存在する場合は、コンテナ全体も存在します。このような場合は、常に再起動するような警察がいるかもしれません。私が編集する必要がないように、私は何とか、「新しい消費者を追加」を自動化することができ

app_consumer: 
    restart: 'always' 
    entrypoint: "php bin/consume.php" 
    depends_on: 
     - 'rabbitmq_server' 

:コンテナの設定がどのように見える

<?php 

// bin/consume.php 
use App\Infra\SymfonyDaemon; 
use Symfony\Component\Process\ProcessBuilder; 

require __DIR__.'/../vendor/autoload.php'; 

$workerBuilder = new ProcessBuilder(['bin/console', 'enqueue:consume', '--setup-broker', '-vvv']); 
$workerBuilder->setPrefix('php'); 
$workerBuilder->setWorkingDirectory(realpath(__DIR__.'/..')); 
$daemon = new SymfonyDaemon($workerBuilder); 
$daemon->start(3); 

:ここconsume.phpスクリプトはどのように見えるかです新しい消費者がコードから追加されるたびに、Dockerの「ビルドスクリプト」(そして他のものも可能でしょうか?)

は残念ながら、RabbitMQのバンドルキュー経営管理論はまだ十分とは言えません。デフォルトでは、キューごとに1つのコマンドを実行する必要があります。 100個のキューがある場合は、100個のプロセスが必要です。キューごとに少なくとも1つは必要です。 configure a multi-queue consumerへの道がありますが、完全に異なる設定が必要です。ちなみに、エンキューはそれをもっと良くします。一度にすべてのキューから消費する単一のコマンドを実行できます。 --queueコマンドオプションを使用すると、より正確な調整を行うことができます。

RabbitMQサーバーをコンシューマーから分離することは理にかなっていますか、またはラビットサーバーをバックグラウンドで実行する必要がありますか?

RabbitMQサーバーは別のコンテナで実行する必要があります。私はそれらを1つのコンテナに混ぜて追加することを推奨しません。

または、それらをアプリコンテナの背景に配置する必要がありますか?

少なくとも2つのアプリケーションコンテナがあることをお勧めします。 1つはWebサーバーを実行し、もう1つはキュー消費者を実行するHTTP要求を処理します。

+0

あなたの洞察と要点をありがとうございます。追加のキューを処理できるプロセスマネージャコンテナを持つことは、多くのことを解決して分離する素晴らしいアイデアです。そして、やはり、PHPは長時間実行されるプロセスを扱うのにはちょっと辛いです。私は実際にはいくつかの選択肢を試してみたいと思っています。おそらくいくつかのpythonやsmthに取り組んでいます。 – reafle

関連する問題