ご存知のとおり、socket.send()はすべてのデータが送信されることを保証するものではありません
そしてこの行:
https://github.com/pallets/werkzeug/blob/03faf0569861e9d8c8c94785ad5560f735ba72da/werkzeug/serving.py#L165
geventと、dockerとして知られる最高のウェブスケール技術を組み合わせることで、応答が切り捨てられるというまさにその振る舞いに私を導きました:3
ソケットのようです。SocketIOはそれを気にする必要がありますが、気にしません
あなたはおそらく正しいですが(調査は行っていません)、Werkzeugのサーバーは開発のみを目的としていることに注意してください。 Dockerでgeventを使用して実行すると、その目的には使用しないと思います。
私は実際に開発にdockerを使用しており、コードの一部はgeventmonkeypatchesを非常に熱心に使用していました。
それがドントパニックを壊さなければ、私はおそらくそれに気付かないでしょう:3
私はPython3.5でこのバグを経験しましたが、基礎となるソケットを非ブロッキングモードに設定した場合のみです(たとえば、 settimeout
使用)。 これは実際にはPython3のアップストリームバグが原因であることが判明しました: issue24291 。 この問題はPython3.6で修正されています( issue26721を参照)。
他のWebサーバーで実装されている回避策は、 wfile
をio.BufferedWriter
でラップするか(たとえば、3.5のCPythonのwsgirefで)、 wbufsize
を変更してバッファリングを有効にすることです。デフォルト(例:このgeventの問題を参照)
werkzeugが回避策も実装したいのか、それともwerkzeug以外の問題だと考えているのかわからない。
提供された情報に基づいて、これは確かにgeventバグまたはstdlibバグのいずれかであると私は信じています、werkzeugは想定されるバッファファイルに対して書き込み+フラッシュを使用します。 geventで
@RonnyPfannschmidtはい、 gevent
なしでも取得できます。werkzeugのWSGIRequestHandler
と組み合わせて非ブロッキングソケットを使用する必要があります。 Geventは、Python3.5のアップストリームバグによって間接的に影響を受ける多くのプロジェクトの単なる別の例でした:-)
これが発生する状況と、Python 3.5で修正されたという事実(3.4は3月にEOLになります)を考慮して、これを終了します。
最も参考になるコメント
私はPython3.5でこのバグを経験しましたが、基礎となるソケットを非ブロッキングモードに設定した場合のみです(たとえば、
settimeout
使用)。 これは実際にはPython3のアップストリームバグが原因であることが判明しました: issue24291 。 この問題はPython3.6で修正されています( issue26721を参照)。他のWebサーバーで実装されている回避策は、
wfile
をio.BufferedWriter
でラップするか(たとえば、3.5のCPythonのwsgirefで)、wbufsize
を変更してバッファリングを有効にすることです。デフォルト(例:このgeventの問題を参照)werkzeugが回避策も実装したいのか、それともwerkzeug以外の問題だと考えているのかわからない。