Comment éviter un tuyau cassé errno 32?

120

Actuellement, j'utilise une application construite en python. Lorsque je l'exécute sur un ordinateur personnel, cela fonctionne sans problème.

Cependant, lorsque je le déplace vers un serveur de production. Il continue de me montrer l'erreur ci-dessous:.

J'ai fait des recherches et j'ai trouvé la raison pour laquelle le navigateur de l'utilisateur final arrête la connexion alors que le serveur est toujours occupé à envoyer des données.

Je me demande pourquoi cela s'est produit et quelle est la cause première qui l'empêche de fonctionner correctement sur le serveur de production, alors qu'il fonctionne sur mon ordinateur personnel. Tout conseil est apprécié

    Exception happened during processing of request from ('127.0.0.1', 34226)
Traceback (most recent call last):
  File "/usr/lib/python2.7/SocketServer.py", line 284, in
_handle_request_noblock
    self.process_request(request, client_address)
  File "/usr/lib/python2.7/SocketServer.py", line 310, in process_request
    self.finish_request(request, client_address)
  File "/usr/lib/python2.7/SocketServer.py", line 323, in finish_request
    self.RequestHandlerClass(request, client_address, self)
  File "/usr/lib/python2.7/SocketServer.py", line 641, in __init__
    self.finish()
  File "/usr/lib/python2.7/SocketServer.py", line 694, in finish
    self.wfile.flush()
  File "/usr/lib/python2.7/socket.py", line 303, in flush
    self._sock.sendall(view[write_offset:write_offset+buffer_size])
error: [Errno 32] Broken pipe
SƲmmēr Aƥ
la source
Est -ce que ce «résoudre votre problème?
Pureferret
Ou connectez-vous avec uwsgi, etc.
KyungHoon Kim

Réponses:

85

Votre processus serveur a reçu une SIGPIPEécriture sur une socket. Cela se produit généralement lorsque vous écrivez dans un socket complètement fermé de l'autre côté (client). Cela peut se produire lorsqu'un programme client n'attend pas que toutes les données du serveur soient reçues et ferme simplement un socket (en utilisant la closefonction).

Dans un programme C, vous essayez normalement de régler pour ignorer le SIGPIPEsignal ou de définir un gestionnaire de signal fictif pour celui-ci. Dans ce cas, une simple erreur sera renvoyée lors de l'écriture dans une socket fermée. Dans votre cas, un python semble lancer une exception qui peut être gérée comme une déconnexion prématurée du client.

Maksim Skurydzin
la source
2
Voici une bonne réponse concernant la gestion des déconnexions des clients: stackoverflow.com/a/180922/276274
Maksim Skurydzin
9

Cela dépend de la manière dont vous l'avez testé, et éventuellement des différences dans l'implémentation de la pile TCP de l'ordinateur personnel et du serveur.

Par exemple, si votre se sendalltermine toujours immédiatement (ou très rapidement) sur l'ordinateur personnel, la connexion peut simplement ne jamais s'être interrompue pendant l'envoi. Ceci est très probable si votre navigateur fonctionne sur la même machine (car il n'y a pas de réelle latence du réseau).


En général, il vous suffit de gérer le cas où un client se déconnecte avant d'avoir terminé, en gérant l'exception.

N'oubliez pas que les communications TCP sont asynchrones, mais cela est beaucoup plus évident sur les connexions physiquement distantes que sur les connexions locales, de sorte que des conditions comme celles-ci peuvent être difficiles à reproduire sur un poste de travail local. Plus précisément, les connexions en boucle sur une seule machine sont souvent presque synchrones.

Inutile
la source
Je le teste en exécutant "paster serve abc.ini --reload", mais la page Web n'a jamais pu être atteinte. Et pour la station de travail VMWare, j'utilise l'option Host-only pour la connexion réseau. Alors, pouvez-vous nous conseiller un moyen de l'exécuter correctement?
SƲmmēr Aƥ
1
Je pense que c'est une question distincte de configuration du réseau VMWare (j'ai bien peur de ne rien savoir à ce sujet). La raison pour laquelle le poste de travail et le serveur peuvent se comporter différemment est cependant ci-dessus, et la solution est simplement de gérer l'exception avectry ... except
Inutile
7

L'erreur de tuyau cassé se produit généralement si votre demande est bloquée ou prend trop de temps et après le délai d'expiration côté demande, elle fermera la connexion et ensuite, lorsque le côté réponse (serveur) essaiera d'écrire sur le socket, il lancera un erreur de rupture de tuyau.

Aaren Shar
la source
3

Cela peut être dû au fait que vous utilisez deux méthodes pour insérer des données dans la base de données, ce qui ralentit le site.

def add_subscriber(request, email=None):
    if request.method == 'POST':
        email = request.POST['email_field']
        e = Subscriber.objects.create(email=email).save()  <==== 
        return HttpResponseRedirect('/')
    else:
        return HttpResponseRedirect('/')

Dans la fonction ci-dessus, l'erreur est l'endroit où la flèche pointe. La mise en œuvre correcte est ci-dessous:

def add_subscriber(request, email=None):
    if request.method == 'POST':
        email = request.POST['email_field']
        e = Subscriber.objects.create(email=email)
        return HttpResponseRedirect('/')
    else:
        return HttpResponseRedirect('/')
Kuldeep K. Rishi
la source