Djangoアプリケーションをgunicornとnginxでホストするための2つの戦略を見てきました。
1つの戦略は、ネットワークポートでgunicornを実行することです。例(from http://goodcode.io/blog/Django-nginx-gunicorn/ ):
location / {
proxy_pass_header Server;
proxy_set_header Host $http_Host;
proxy_redirect off;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
proxy_connect_timeout 10;
proxy_read_timeout 10;
proxy_pass http://localhost:8000/;
}
別の戦略は、起動時にgunicornをUNIXソケットにバインドすることです(例 http://michal.karzynski.pl/blog/2013/06/09/Django-nginx-gunicorn-virtualenv-supervisor/ )
upstream hello_app_server {
server unix:/tmp/gunicorn.sock fail_timeout=0;
}
...
location / {
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_Host;
proxy_redirect off;
if (!-f $request_filename) {
proxy_pass http://hello_app_server;
break;
}
}
どの戦略が優れているのか?それぞれの適切な方法についてのコメントはありますか?私はTCPによって導入されると想像するオーバーヘッドのため、ソケットアプローチに傾いています。私が見た実装例の間のヘッダー、接続タイムアウトなどの違いについて最も心配しています。
小さなTCP/IPオーバーヘッド以外に、大きな違いはありません。各listen()ソケットは接続キューを取得し、accept()はそのキューから接続をポップするだけです。 gunicornでは、各ワーカーはそのキューから新しい接続をポップするだけなので、変更されません。違いは、パフォーマンス(ソケットが少し速い)と移植性(port:IPの方が柔軟性がある)です。 Unixドメインソケットを使用すると、パフォーマンスが少し向上しますが、サーバーアプリを別のOSに移動すると、ローカルホストに接続されたソケットを使用すると、移植性が少し向上します。IPアドレスをローカルホストから別のホスト名に変更するだけで実行できます。 。
ソケットトラフィックは、Webサーバーとアプリサーバー(wsgi)の両方が同じマシンに存在する場合、簡単に選択できます。ただし、ソケットはネットワーク経由では機能しないため、ネットワーク接続経由でネットワークポートが必要になります。
追加のポートを開く必要がないため、TCP/IPよりもソケットトラフィックが優先されます。開いているポートが少ないほど、システムが強化されます
ここで提案されているように、「偏執狂的である」 https://hynek.me/talks/python-deployments/
「制限付きのアクセス権を持つUNIXファイルソケットはあなたの友達です。そして、ポート番号を思い付くのをやめることができます」
私はこのパーティーに遅れていることを知っています。これをSELinuxが適用されたRed HatフレーバーLinuxで動作させようとしている場合、これは役に立つかもしれません。
ソケットを使おうとすると邪魔になります。私はあきらめた。
また、任意のTCPポートを介してGunicornをバインドしようとすると、邪魔になります。デフォルトでは(Centos 1708の場合)、SELinuxで使用できるポートのサブセットがあります:80 、81、443、488、8008、8009、8443、9000
私は8009で行きましたが、明らかに他のいくつかのポートでは使用できます
semanage -a -t http_port_t -p tcp $PORTNUMBER
ポートのリストを表示する
semanage port -l