Gunicorn: O objeto 'Response' não tem atributo 'status_code' em wsgi.py com websockets

Criado em 16 fev. 2016  ·  36Comentários  ·  Fonte: benoitc/gunicorn

Eu inicio meu aplicativo usando

gunicorn --worker-class eventlet -w 1 server:app --bind="127.0.0.1:5000"

E ao usar Flack-SocketIO para websockets, muitas vezes recebo um erro com o Gunicorn não retornando de uma função corretamente

[2016-01-30 10:20:53 -0800] [7330] [ERROR] Error handling request
Traceback (most recent call last):
  File "/Users/brianclark/Desktop/Projects/HDP/application/api/venv/lib/python2.7/site-packages/gunicorn/workers/async.py", line 52, in handle
    self.handle_request(listener_name, req, client, addr)
  File "/Users/brianclark/Desktop/Projects/HDP/application/api/venv/lib/python2.7/site-packages/gunicorn/workers/async.py", line 114, in handle_request
    resp.close()
  File "/Users/brianclark/Desktop/Projects/HDP/application/api/venv/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 423, in close
    self.send_headers()
  File "/Users/brianclark/Desktop/Projects/HDP/application/api/venv/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 316, in send_headers
    tosend = self.default_headers()
  File "/Users/brianclark/Desktop/Projects/HDP/application/api/venv/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 297, in default_headers
    elif self.should_close():
  File "/Users/brianclark/Desktop/Projects/HDP/application/api/venv/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 230, in should_close
    if self.status_code < 200 or self.status_code in (204, 304):
AttributeError: 'Response' object has no attribute 'status_code'

Algum conselho sobre as configurações que eu poderia usar para consertar isso ou é um bug?

Feedback Requested Discussion Investigation help wanted

Comentários muito úteis

@ kramer65 entendo . Eu tenho esperado por isso há muito tempo, se alguém tiver a solução, por favor, compartilhe conosco! obrigado!

Todos 36 comentários

@ bclark8923 você tem algum aplicativo que possa ajudar a reproduzir o problema?

Sim! O que você gostaria que eu fizesse?

Na segunda-feira, 28 de março de 2016, Benoit Chesneau [email protected] escreveu:

@ bclark8923 https://github.com/bclark8923 você tem algum aplicativo
que poderia ajudar a reproduzir o problema?

-
Você está recebendo isso porque foi mencionado.
Responda a este e-mail diretamente ou visualize-o no GitHub
https://github.com/benoitc/gunicorn/issues/1210#issuecomment -202484667

Obrigado,
Brian Clark
(248) 990 5616
www.hdphealth.com

Conheça-me no Facebook https://facebook.com/bclark8923 e no Twitter
https://twitter.com/blaurenceclark!

@ bclark8923 se puder ser transmitido, então eventualmente eu poderia incluir alguma parte em um teste que ajudaria :)

Além disso, qual versão do gunicorn você está usando?

Sim por favor! Envie-me um email para [email protected] e 19.x de algum tipo pode verificar
em breve

Na segunda-feira, 28 de março de 2016, Benoit Chesneau [email protected] escreveu:

@ bclark8923 https://github.com/bclark8923 se puder ser transmitido assim
eventualmente, eu poderia incluir alguma parte em um teste que ajudaria :)

Além disso, qual versão do gunicorn você está usando?

-
Você está recebendo isso porque foi mencionado.
Responda a este e-mail diretamente ou visualize-o no GitHub
https://github.com/benoitc/gunicorn/issues/1210#issuecomment -202492005

Obrigado,
Brian Clark
(248) 990 5616
www.hdphealth.com

Conheça-me no Facebook https://facebook.com/bclark8923 e no Twitter
https://twitter.com/blaurenceclark!

Usando a versão 19.4.5

Estou tendo o mesmo problema. Estou usando o gunicorn versão 18.0.

Alguma correção já está disponível?

se alguém tiver código z para reproduzi-lo, ajudaria :)

@benoitc - Isso faz sentido .. ;-)

Vou consertar algo na próxima semana e avisar você!

@benoitc - Tudo bem, consertei algo antes do fim de semana.

Você pode encontrar o repo com instruções no leia-me aqui: https://github.com/kramer65/gunicorn-error

btw: Estou usando o gunicorn versão 18.0

Provavelmente algo precisa retornar gunicorn.workers.async.ALREADY_HANDLED ou gunicorn tentará registrar a solicitação assim que o aplicativo retornar de seu manipulador WSGI. Gunicorn precisa saber, em vez disso, que a solicitação agora é tratada inteiramente pelo aplicativo.

Ambos os exemplos no diretório "examples / websocket" retornam essa constante de seu manipulador WSGI.

@benoitc - O exemplo para reproduzir o erro o ajuda a encontrar o erro? Posso ajudar em alguma outra coisa para ajudar a resolver isso?

@ kramer65 sim reproduzi o erro.

Portanto, Gunicorn é um mecanismo WSGI puro e está esperando uma resposta WSGI contendo um status:
https://github.com/benoitc/gunicorn/blob/master/gunicorn/http/wsgi.py#L242

(relacionado a este código: https://github.com/benoitc/gunicorn/blob/master/gunicorn/workers/async.py#L103-L119)

Como @tilgovi disse, você pode ignorar a manipulação de resposta do gunicorn retornando ALREADY_HANDLED

Pelo que li o código do flash socketio, ele está envolvendo o aplicativo do frasco em socketio.Middleware que se encontra em engineio.middleware.Middleware :
https://github.com/miguelgrinberg/python-engineio/blob/master/engineio/middleware.py

que retornam o aplicativo wsgi ou seu próprio manipulador se encontrar o caminho:
https://github.com/miguelgrinberg/python-engineio/blob/master/engineio/middleware.py#L45 -L52

Portanto, ele retorna socketio.Server.handle_request no caminho do websocket:
https://github.com/miguelgrinberg/Flask-SocketIO/blob/master/flask_socketio/__init__.py#L144

que por si só retorna engineio.Server.handle_request (muitos departamentos circulares neste projeto ...):
https://github.com/miguelgrinberg/python-engineio/blob/master/engineio/server.py#L184

Neste ponto, parece que nem socket.handle_get_request nem socket. handle_post_request definiram o status:
https://github.com/miguelgrinberg/python-engineio/blob/master/engineio/socket.py#L69 -L96

E então um erro pode acontecer aqui:
https://github.com/miguelgrinberg/python-engineio/blob/master/engineio/server.py#L251 -L252

uma vez que pode retornar uma resposta sem ter definido um status ou nada. Posso ver que a atualização usa o mesmo objeto websocket do nosso exemplo:
https://github.com/benoitc/gunicorn/blob/master/examples/websocket/websocket.py

Acho que em vez de devolver os r finais aqui:
https://github.com/miguelgrinberg/python-engineio/blob/master/engineio/server.py#L251 -L252

Provavelmente deve retornar ALREADY_HANDLED como aqui:
https://github.com/benoitc/gunicorn/blob/master/examples/websocket/websocket.py#L115

Só um palpite, já que o código é muito difícil de ler. Espero que ajude.

@ kramer65 deixe-me saber sobre o status deste tíquete para você de qualquer maneira :)

@benoitc a ALREADY_HANDLED é específica para gunicorn. Eventlet tem sua própria versão dessa constante, definida de uma maneira diferente: https://github.com/eventlet/eventlet/blob/2cd5f1d9aea53efb4526e7185017bdcc84732588/eventlet/wsgi.py#L69.

O r que você estava seguindo através do código retorna ALREADY_HANDLED do evenlet quando a conexão do websocket termina. Isso é tratado automaticamente pelo eventlet: https://github.com/eventlet/eventlet/blob/2cd5f1d9aea53efb4526e7185017bdcc84732588/eventlet/websocket.py#L135.

O Gunicorn deve (eu acho) reconhecer a constante ALREADY_HANDLED do eventlet além da sua própria e tratá-la da mesma maneira. Acho que isso resolverá esse problema.

É ótimo se você puder corrigir esse problema. Estou executando flask-socketio & gunicorn na minha produção e não quero perder dados.

Estou tendo problemas semelhantes e gostaria de saber se há alguma notícia sobre esse assunto?

@benoitc - Você acha que a sugestão feita por @miguelgrinberg acima (para permitir que Gunicorn reconheça a constante ALREADY_HANDLED do eventlet além da sua própria e manuseie-a da mesma maneira) é uma boa ideia?

@ kramer65 se você puder encontrar uma maneira de adicionar suporte para isso de forma limpa, acho que faz sentido que o trabalhador de evento cuide disso.

No momento, a lógica para lidar com isso está um pouco enterrada dentro de gunicorn.workers.async.AsyncWorker#handle_request mas talvez isso pudesse ser manipulado indiretamente por meio de propriedade estática que o trabalhador de evento pode substituir ou chamando um método de instância para verificar já manipulado por qualquer trabalhador- lógica específica que pode existir, com a classe base fazendo o que faz agora.

@tilgovi - Já faz um tempo que você não me envia sua mensagem, mas eu queria responder a isso, afinal. O problema é que eu meio que alcancei meu limite no que posso fazer para isso. Eu realmente não tenho ideia de como proceder para resolver isso.

Enquanto isso, meus logs estão cheios de mensagens de erro como a mostrada abaixo, então tenho todos os motivos para colocar um pouco de energia para resolver isso. Só não entendo totalmente qual é a causa exata do problema, muito menos que entendo como poderia resolver isso.

Se alguém quiser entrar em contato, ficarei feliz em discutir o assunto e, então, posso ser de uma ajuda um pouco mais do que sou agora.

2016-08-23 08:07:16 [2185] [ERROR] Error handling request
Traceback (most recent call last):
  File "/var/www/imd/venv/local/lib/python2.7/site-packages/gunicorn/workers/async.py", line 45, in handle
    self.handle_request(listener, req, client, addr)
  File "/var/www/imd/venv/local/lib/python2.7/site-packages/gunicorn/workers/async.py", line 102, in handle_request
    resp.close()
  File "/var/www/imd/venv/local/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 369, in close
    self.send_headers()
  File "/var/www/imd/venv/local/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 284, in send_headers
    tosend = self.default_headers()
  File "/var/www/imd/venv/local/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 265, in default_headers
    elif self.should_close():
  File "/var/www/imd/venv/local/lib/python2.7/site-packages/gunicorn/http/wsgi.py", line 198, in should_close
    if self.status_code < 200 or self.status_code in (204, 304):
AttributeError: 'Response' object has no attribute 'status_code'

um consertou? .....

@qwexvf - Infelizmente não fiz. Meus logs ainda estão cheios de erros. :-(

Alguém mais?

@ kramer65 entendo . Eu tenho esperado por isso há muito tempo, se alguém tiver a solução, por favor, compartilhe conosco! obrigado!

alguma atualização?

Tenho certeza de que existem maneiras mais limpas de consertar isso, mas pelo menos é um começo.

@stefaang obrigado, vou tentar pensei nisso!

Quando a correção para isso será lançada no PyPI?

amanhã
Na sexta-feira, 17 de fevereiro de 2017 às 16:46, Eddie [email protected] escreveu:

Quando a correção para isso será lançada no PyPI?

-
Você está recebendo isso porque modificou o estado abrir / fechar.

Responda a este e-mail diretamente, visualize-o no GitHub
https://github.com/benoitc/gunicorn/issues/1210#issuecomment-280685264 ,
ou silenciar o tópico
https://github.com/notifications/unsubscribe-auth/AAA4ogTRMF7EfR25G6gLrktOdh_iA4Ciks5rdcDYgaJpZM4HbcdP
.

Foi lançado?

@benoitc alguma palavra sobre a atualização que está sendo enviada para pypi?

@defionscode farei um lançamento na quinta de manhã (amanhã).

Otimo obrigado
Na quarta-feira, 22 de fevereiro de 2017 às 11h54 Benoit Chesneau [email protected]
escreveu:

@defionscode https://github.com/defionscode farei um lançamento em
quinta-feira de manhã (amanhã).

-
Você está recebendo isso porque foi mencionado.
Responda a este e-mail diretamente, visualize-o no GitHub
https://github.com/benoitc/gunicorn/issues/1210#issuecomment-281729992 ,
ou silenciar o tópico
https://github.com/notifications/unsubscribe-auth/AEcrYp6QfVpWXhG14f4M-lPDHMn0cFncks5rfGhWgaJpZM4HbcdP
.

Esta correção foi lançada?

O status de https://github.com/benoitc/gunicorn/issues/1471 . Será lançado hoje ...

Esse bug ainda está acontecendo do meu lado com as últimas versões 19 e 20 do gunicorn. Era para ser corrigido @benoitc ?

Esta página foi útil?
0 / 5 - 0 avaliações