Permettez-moi de commencer par la fin
1 2 3 4 5 6 7 8 9 10 11 12
|
def main_thread(output, input, sockets):
import Queue
while True:
try:
data=input.get(block=False)
if data.error:
IO.connect_to_server(sockets, data.serverName, output, input, continueToRun)
else:
# bla bla bla
except Queue.Empty:
time.sleep(1) |
Pourquoi vouloir prendre quelque chose dans la queue en non bloquant si c'est pour bloquer quand il n'y a rien ?
De plus, l'import devrait être en tête de fichier. certainement pas ici.
D'où sort cette variable continueToRun, et à qui dit-elle de continuer à tourner ?
Ceci me parait plus cohérent:
1 2 3 4 5 6 7 8 9 10
|
def main_thread(output, input, sockets):
while True:
try:
data = input.get()
if data.error:
IO.connect_to_server(sockets, data.serverName, output, input, continueToRun)
else:
# bla bla bla |
Continuons avec le commencement:
1 2
| while datas == "" or datas[-2:] != "\r\n":
datas = datas + socketObject.recv(1024) |
socketObject.recv est-il bloquant ?
Si c'est le cas, le while est une erreur: un recv dont le résultat est vide signifie que le socket a été déconnecté de l'autre côté.
Si ce n'est pas le cas, ça n'a pas lieu d'être dans ce code. Remettez le en mode bloquant.
if data[0:19] == "ERROR :Closing Link":
Comme dit plus haut, si le socket est déconnecté de l'autre côté, le recv renverra un résultat vide. Pas besoin donc de signaler la déconnexion dans ce cas. De plus, ce code risque de lancer une IndexError si cette ligne de données est trop courte.
1 2
| except socket.error: # Dans le cas où on n'a rien reçu
pass |
Une socket.error, c'est pire que ça. En général, on coupe la connexion. Dans la plupart des cas, c'est même déjà fait 
Si j'ai bien compris, ce code parse des headers textes style http, de la forme :
1 2 3
| Content-type: text/html\r\n
Content-lenght: 347\r\n
\r\n |
La fonction n'est sensée quitter que si le lien avec le serveur est rompu, autrement il attend la suite des headers.
Voici comment je réécrirais ce bout de code.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42
| def _get_from_server(socket, input):
try:
left = ""
while 1:
raw = socket.recv(1024)
if not raw:
# Le socket est mort
break
left = left + raw
lines = left.split("\r\n")
# Note: est-on certains de recevoir des \r\n ?
# Certains clients ou serveurs http ne mettent que \n
# Vider left : les données sont exploitées
left = ""
for line in lines[:-1]:
input.put(line) # Une queue bloque par défaut si elle est pleine
# Attention, il se peut qu'il y ait eu des données après les headers
# Auquel cas ce code n'est plus valide, puisque les données peuvent
# aussi contenir des \r\n
if line[-1] == "":
# La ligne est vide marque sans doute la fin des headers
faire_quelquechose()
else:
# Il reste quelques données dans cette ligne
# Mais la réception n'est pas complète
# Ex : "Content-ty"
left = line
except socket.error:
# Le socket est ptet mort
pass
finally: # Quoi qu'il en soit, faut être sur que le socket est fermé
try:
socket.close()
except:
pass |
Pour conclure, à mon avis cette utilisation absusive du cpu vient de là:
# Message que le serveur nous envoie (parfois) avant de nous déconnecter
Et quand il ne l'envoie pas, une fois revenu au recv, il renvoie une chaine vide. Du coup, le while boucle, encore, et encore...
Edit : j'avais glissé une erreur a niveau du raw et de l'arret de la boucle. Vérifiez le code. D'ailleurs il peut encore y avoir des erreurs.
Partager