Socket connectée

Résolu
immerczeck Messages postés 27 Date d'inscription jeudi 2 septembre 2004 Statut Membre Dernière intervention 28 juin 2008 - 8 févr. 2006 à 20:57
cs_coq Messages postés 6350 Date d'inscription samedi 1 juin 2002 Statut Membre Dernière intervention 2 août 2014 - 9 févr. 2006 à 13:57
Bonjour!
Pourriez-vous m'indiquer une manière de vérifier qu'une socket est toujours active, que le client à l'autre bout n'a pas fermé l'application?
J'ai essayé la méthode avec Poll et Available==0 mais ça ne donne rien, et j'ai lu que la propriété Connected ne s'actualisait pas au cours du temps, alors pourriez-vous me donner une méthode fiable?

Merci d'avance

Immerczeck

11 réponses

MorpionMx Messages postés 3466 Date d'inscription lundi 16 octobre 2000 Statut Membre Dernière intervention 30 octobre 2008 57
9 févr. 2006 à 10:36
Bonjour,
Je suis très embété parce que je viens de faire un rapide essai, et ca marche.

Le code dans mon thread :


<HR>
lock(
this.clientsList.SyncRoot)
{

foreach (
Client client
in
this.clientsList)
{

if (client.Socket.Poll(10,
SelectMode.SelectRead) && client.Socket.Available == 0)

Console.WriteLine(
string.Format(
"client {0} deconnecté", client.IDClient));
}
}

<HR>

Par contre c'est sur que je mettrais pas ce code dans le thread qui gere les message, mais dans un thread dedié a la detection de deconnexion sauvage..
Et dans ce thread, je ne ferais pas de boucle active ( while(true) ), mais je le déclencherais plutot via un timer, toutes les X secondes.


Mx
MVP C#
3
cs_coq Messages postés 6350 Date d'inscription samedi 1 juin 2002 Statut Membre Dernière intervention 2 août 2014 101
9 févr. 2006 à 10:53
Ou en mettant une pause, ainsi que la gestion de ThreadAbortException.

Sinon tu peux aussi prévoir dans ton protocole un timeout au bout duquel tu considères que ton client est parti si tu n'as pas reçu de données.
Ou définir un message auquel le client doit répondre pour signaler qu'il est toujours là. :-)

/*
coq
MVP Visual C#
*/
3
MorpionMx Messages postés 3466 Date d'inscription lundi 16 octobre 2000 Statut Membre Dernière intervention 30 octobre 2008 57
9 févr. 2006 à 11:19
L'idée du Timer en plus clair :


<HR>


System.Threading.Timer timer =
new System.Threading.
Timer(
new
TimerCallback(ListenForDeconnection),
null, 0, 10000);
[...]

private
void ListenForDeconnection(
object state)
{

foreach (idclient client in ArrayList.Synchronized(clients))
{
if(client.sock.Poll(10, SelectMode.SelectRead) && client.sock.Available==0)
{
....
}
}

}

<HR>

Mx
MVP C#
3
MorpionMx Messages postés 3466 Date d'inscription lundi 16 octobre 2000 Statut Membre Dernière intervention 30 octobre 2008 57
8 févr. 2006 à 21:34
Salut,

Pourtant c'est une bonne technique (la bonne technique ? )
Qu'entends-tu par "ca ne donne rien" ?

Une autre technique, dans le cadre d'un client qui se deconnecte "proprement" (pas de plantage), serait que le client envoie un message au serveur pour le prevenir qu'il se deconnecte.

Sinon, je ne connais pas d'autre méthode que celle du Poll.


Mx
MVP C#
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
immerczeck Messages postés 27 Date d'inscription jeudi 2 septembre 2004 Statut Membre Dernière intervention 28 juin 2008
8 févr. 2006 à 21:57
ben ça ne donne rien dans le sens où ça ne réagit pas lorsque le client se déconnecte. Voici un bout du code :

while(true)
{ [...]
foreach (idclient client in ArrayList.Synchronized(clients))
{
if(client.sock.Poll(10, SelectMode.SelectRead) && client.sock.Available==0)
{
richTextBox1.Text+= "Le client "+ client.nick+" s'est déconnecté\r";
listBox1.Items.Remove(client.nick);
ArrayList.Synchronized(clients).Remove(client);
}[...]
}
}

Pitetre me suis-je trompé quelque part...
Sinon j'avais pensé à la solution du message envoyé par le client à déconnexion, mais comme tu l'as dit, dans le cas d'un plantage... c'est plutôt gênant de garder une socket déconnectée...
0
MorpionMx Messages postés 3466 Date d'inscription lundi 16 octobre 2000 Statut Membre Dernière intervention 30 octobre 2008 57
8 févr. 2006 à 22:22
Ca m'a pourtant bien l'air d'etre ca...
Essayons de diagnostiquer...
Est-ce que le thread dans lequel se trouve ta boucle tourne bien ? As tu essayé de debugger en pas a pas, pour voir les valeurs qu'il pouvait te donner ? (genre ton arraylist vide)
Es-tu sur que le client avec lequel tu testes est bien deconnecté (ca peut paraitre bete comme question, mais bon, parfois on pense qu'on a fermé le client, mais le process tourne encore en fond parce qu'un thread n'a pas sa propriété IsBackground a true)


Mx
MVP C#
0
immerczeck Messages postés 27 Date d'inscription jeudi 2 septembre 2004 Statut Membre Dernière intervention 28 juin 2008
8 févr. 2006 à 22:36
Oui, le client est bien déconnecté, je n'ai pas mis ISBackground à true, c'est trop brutal, j'ai arrangé l'évènement Closing de la form. Je teste en réseau local, j'ai donc tous les moyens de vérifier. Le thread tourne bien, puisque c'est le même qui s'occupe de la gestion des messages (là peut-être que ça vient de là, j'aurais peut-être dû les séparer).
L'arrayList n'est pas vide puis que j'ai en permanence une listbox qui m'affiche tous les client.nick.

Immerczeck
0
MorpionMx Messages postés 3466 Date d'inscription lundi 16 octobre 2000 Statut Membre Dernière intervention 30 octobre 2008 57
9 févr. 2006 à 11:02
J'aurais aussi fait ca, (et d'ailleurs, j'ai toujours fait ca jusque maintenant). Mais j'ai recemment entendu d'un prof que c'etait pas terrible de faire une boucle dans un Thread avec une pause dedans, alors j'ai voulu donner une autre possibilité, en me disant qu'elle etait peut-etre meilleure que la mienne.
Maintenant, si tu ferais comme ca aussi coq, c'est que ca doit pas etre une si mauvaise solution que ca



Mx
MVP C#
0
cs_coq Messages postés 6350 Date d'inscription samedi 1 juin 2002 Statut Membre Dernière intervention 2 août 2014 101
9 févr. 2006 à 11:07
Je ne suis pas très pointu en threading, mais c'est juste que l'utilisation d'un timer pour lancer le thread à intervalle réguliers me paraissait un peu bizarre.
Je vais essayer de trouver des infos sur la question.

/*
coq
MVP Visual C#
*/
0
immerczeck Messages postés 27 Date d'inscription jeudi 2 septembre 2004 Statut Membre Dernière intervention 28 juin 2008
9 févr. 2006 à 12:50
merci de vos réponses!
juste une question, pourquoi une boucle while(true) n'est pas une bonne solution?
0
cs_coq Messages postés 6350 Date d'inscription samedi 1 juin 2002 Statut Membre Dernière intervention 2 août 2014 101
9 févr. 2006 à 13:57
En général on essaie d'éviter les boucles infinies, mais je pense qu'ici Mx parlait plus du principe de passer par le thread en général plutôt que de l'utilisation de la boucle infinie en particulier.
Pour ma part je ne pense pas que ce soit forcément une très mauvaise idée, pour autant que son utilisation soit "justifiée' et qu'on prévoit de quoi en sortir proprement. (et d'y prévoir une temporisation si nécessaire afin de ne pas non plus consommer inutilement du temps)
Mais il est clair que dans ton cas il vaut mieux passer par la méthode proposée par Mx :-)

/*
coq
MVP Visual C#
*/
0
Rejoignez-nous