Bonjour,

J'ai réalisé un tchat basique fonctionnant sur le protocole TCP/IP avec une architecture clients/serveur (en PyQt, mais ceci n'a pas d'importance ici).

Le client est composé d'un QTextEdit où j'affiche la conversation, d'un QListWidget qui affiche la liste des personnes connectés, et enfin d'un QLineEdit (et d'un bouton) pour envoyer les messages au serveur qui s'occupe de renvoyer le message à tout le monde.

Ca ressemble à ça :


Voici le code de mon serveur :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
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
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
# -*- coding: utf-8 -*-
 
import sys, socket
import threading
 
 
class Server:
    def __init__(self, address):
        self.socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        self.socket.bind(address)
        self.socket.listen(5)
 
        self.clients = []
        self.pseudos = []
 
    def wait_for_clients(self):
        while True:
            client, address = self.socket.accept()
            self.clients.append(client)
            t = ListeningThread(self.clients, client, self.pseudos)
            t.start()
 
 
class ListeningThread(threading.Thread):
    def __init__(self, clients, client, pseudos):
        threading.Thread.__init__(self)
        self.clients = clients
        self.client = client
        self.pseudos = pseudos
 
    def run(self):
        name = self.client.recv(1024)
        print type(name)
        address = self.client.getsockname()
        message = "<font color='gray'><b>" + name + "</b> est connecté</font>"
        if len(self.pseudos) > 0:
            self.client.send("MAJsuperman " + str(','.join(self.pseudos)))
        self.send_to_all(message)
        self.pseudos.append(name)
        self.send_to_all("JOINsuperman " + name)
        while True:
            message = self.client.recv(1024)
            if message == "":
                self.clients.remove(self.client)
                message = "<font color='gray'><b>" + name + "</b> s'est déconnecté</font>"
                self.send_to_all("LEFTsuperman " + name)
                self.pseudos.remove(name)
                self.send_to_all(message)
                break
            message = "<b>" + name + "</b> : " + message
            self.send_to_all(message)
 
    def send_to_all(self, message):
        print message
        for client in self.clients:
            client.send(message)
 
if len(sys.argv) != 3:
    print """Usage: python server.py ip port
example: python server.py localhost 54321"""
    sys.exit()
 
address = sys.argv[1], int(sys.argv[2])
server = Server(address)
server.wait_for_clients()
Comme vous pouvez le voir, j'utilise un message "spécial" pour indiquer aux clients la connexion ou la déconnexion d'une personne pour y afficher (ou retirer) son pseudo dans la QListWidget.

Cependant, lorsque je fais appel à la méthode send_to_all 2 fois à la suite, du côté du client je ne reçois pas 2 messages séparément, mais je reçois un seul message avec les 2 messages concaténés...

Concrètement côté serveur j'envoie :
- "<font color='gray'><b>" + name + "</b> est connecté</font>" d'une part, et :
- "JOINsuperman " + name d'autre part

et côté client, au lieu de recevoir ces messages séparément afin d'afficher le premier message dans le QTextEdit, et de traiter le second message en affichant le pseudo dans la QListWidget, je reçois les 2 messages ensemble en une seule fois...
<font color='gray'><b>" + name + "</b> est connecté</font>JOINsuperman mon_pseudo

A noter que ceci est aléatoire, parfois ça fonctionne, et souvent ce phénomène ce produit... (seulement lors de la connexion/déconnexion vu que je fais plusieurs send() en suivant). Lors d'une discussion tout fonctionne bien.

Si besoin, voici la méthode côté client qui s'occupe de recevoir les messages et de les traiter en fonction :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
def run(self):
        while self.running:
            message = self.sock.recv(1024)
            print 'message recu: ' + message
            if message[0:11] == "MAJsuperman":
                pseudos = message[12:]
                self.emit(SIGNAL("maj"), pseudos)
            elif message[0:12] != "JOINsuperman" and message[0:12] != "LEFTsuperman" and message[0:11] != "MAJsuperman":
                self.emit(SIGNAL("message_recu"), message)
            elif message[0:12] == "JOINsuperman":
                pseudo = message[13:]
                self.emit(SIGNAL("join"), pseudo)
            elif message[0:12] == "LEFTsuperman":
                pseudo = message[13:]
                self.emit(SIGNAL("left"), pseudo)
 
            QApplication.processEvents()
Sauriez-vous comment je pourrais y remédier ?

Merci d'avance !