Werkzeug: Разделенные запросы по-прежнему не работают

Созданный на 16 июл. 2017  ·  4Комментарии  ·  Источник: pallets/werkzeug

(Обновлено, потому что я понял, что пытался исправить это, поэтому меня смутила исходная проблема и проблема, которая заставила меня сдаться)

Я делаю частичный запрос к приложению, которое использует Werkzeug (текущий мастер git). get_input_stream завершает вызов LimitedStream(wsgi.input, min(content_length, max_content_length)) . min(content_length, max_content_length) всегда будет None при использовании кодирования по фрагментам.

Пытаясь добиться прогресса, я попытался использовать LimitedStream(stream, content_length or max_content_length) , но затем я получил исключение ClientDisconnected , потому что мы не можем сказать разницу между отключением клиента и простым выполнением фрагментированного запроса. , поскольку wsgi.input.read() в обоих случаях просто возвращает строку нулевой длины.

Самый полезный комментарий

Какой wsgi в настоящее время поддерживает input_terminated ? После того, как весь день прожиг на отладке, почему данные пусты, почему поток пуст, а затем понял, что это из-за кодирования потокового потока, я теперь не могу найти ничего, что поддерживает это: /

Все 4 Комментарий

Это больше, чем просто ошибка с min . После исправления проблема заключается в том, что выполнение wsgi.input.read(max_content_length) с блоками Werkzeug навсегда, если для чтения меньше max_content_length . Или при использовании Gunicorn, который поддерживает фрагменты путем синтаксического анализа и буферизации всего сообщения, длина оказывается меньше max_content_length , поэтому LimitedStream считает, что клиент отключился.

Я протестировал это на Django, чтобы убедиться, что мы не делаем чего-то странного, он тоже видит пустой поток.

Самый простой путь вперед - предоставить промежуточное программное обеспечение, которое устанавливает environ['wsgi.input_terminated'] и говорит людям использовать его при использовании сервера, поддерживающего частичную передачу.

Какой wsgi в настоящее время поддерживает input_terminated ? После того, как весь день прожиг на отладке, почему данные пусты, почему поток пуст, а затем понял, что это из-за кодирования потокового потока, я теперь не могу найти ничего, что поддерживает это: /

Должны ли мы не только проверять environ.get('wsgi.input_terminated') также проверять environ.get('HTTP_TRANSFER_ENCODING') == 'chunked' и в этом случае также напрямую возвращать развернутый поток? Это устраняет такие проблемы, как простой curl -H 'Transfer-Encoding: chunked' ... возвращающий пустой поток.

Согласно RFC2616

4.4.2
Если поле заголовка Transfer-Encoding (раздел 14.41) присутствует и
имеет любое значение, кроме "identity", тогда длина передачи равна
определяется с помощью "фрагментированного" кодирования передачи (раздел 3.6),
если сообщение не прерывается закрытием соединения.

4.4.3
Если поле заголовка Content-Length (раздел 14.13) присутствует, его
десятичное значение в OCTET представляет как длину объекта, так и
длина передачи. Поле заголовка Content-Length НЕ ДОЛЖНО отправляться
если эти две длины различаются (например, если Transfer-Encoding
поле заголовка присутствует). Если сообщение получено с обоими
Поле заголовка Transfer-Encoding и поле заголовка Content-Length,
последнее ДОЛЖНО игнорироваться.

... отмечая, что Transfer-Encoding из chunked требует, чтобы любой заголовок Content-Length игнорировался, и поэтому на его основе не должна выполняться потоковая обработка. В настоящее время это так, если не задано значение wsgi.input_terminated .

Должно ли действительно быть необходимо установить wsgi.input_terminated для нормальной работы кодирования фрагментов, например, 10-байтовой полезной нагрузки JSON?

Была ли эта страница полезной?
0 / 5 - 0 рейтинги