![]() |
Serversocket ClientRead Problem
hi,
mein Problem ist folgendes: da der Tclientsocket erst daten/in meinem fall text schickt wenn er genug daten hat kann es dazu kommen, dass einzelne befehe abgeschnitten sind! deshalb habe ich mir folgendes ausgedacht:
Delphi-Quellcode:
nun zu meinem Problem:
procedure TForm1.ss_serverClientRead(Sender: TObject; Socket: TCustomWinSocket);
var s_receve,s_temp:string; b_da:boolean; I,i_sockethander: Integer; begin i_sockethander:=socket.SocketHandle; for I := 0 to lv_bots.Items.Count - 1 do begin if (lv_bots.Items.Item[i].SubItems.Strings[8]=inttostr(i_sockethander)) then begin s_receve:=lv_bots.Items.Item[i].SubItems.Strings[9]; end; end; s_receve:=s_receve+Socket.ReceiveText; repeat begin b_da:=false; //<- break punkt erklärung kommt gleich s_temp:=''; for I := 0 to length(s_receve) -1 do begin if (s_receve[i]='|') then begin b_da:=true; end; end; if (b_da=true) then begin s_temp := copy(s_receve, 1, pos('|', s_receve) - 1); s_receve := copy(s_receve, pos('|', s_receve) + 1, length(s_receve)); for I := 0 to lv_bots.Items.Count - 1 do begin if (lv_bots.Items.Item[i].SubItems.Strings[8]=inttostr(i_sockethander)) then begin lv_bots.Items.Item[i].SubItems.Strings[9]:=s_receve; end; end; if (s_temp<>'') then begin handle(i_sockethander,s_temp); end; end; end; until (b_da=false); end; die handle procedure wir nicht ausgelöst! Nur wenn ich entweder einen Brak-Punkt ein an die beschiebene stelle setzte oder ich einen button mit
Delphi-Quellcode:
machen (der muss aber mindestens 3 sec haben sonst wird die handle Procedure nicht ausgelöst)
sleep(3000);
wie kann ich mienem Problem abhilfe schaffen? mfg gandime |
Re: Serversocket ClientRead Problem
Er schickt auch kleinere Packete, aber er macht es abhängig davon ob eine gewisse Grösse erreicht ist oder eine gewisse Zeit vergangen ist.
Dein grundlegendes Problem ist ein Verständnisproblem: Die ClientRead Procedure wird entsprechend auch mehrmals aufgerufen. Du musst also mit jedem ClientRead die Daten akkumulieren und danach schauen, ob du ein komplettes, für dich verarbeitbares, Datenpacket erhalten hast und kannst dann entsprechend Handle() aufrufen. Von daher müsstest du deinen s_receve (receive eigentlich) als Member deklarieren, etc. |
Re: Serversocket ClientRead Problem
ich habe
Zitat:
|
Re: Serversocket ClientRead Problem
Das war auch nur einer der ersten Schritte bis zur Lösung deines Problems. Du musst deine OnClientRead grundsätzlich so umstellen, dass sie mehrfache Aufrufe bis zu einem kompletten Datenpacket abkann und sie auch entsprechend handelt. Grundlegender Ablauf, welcher in deiner ClientRead sein sollte:
1. neue Daten empfangen 2. neue Daten an den Puffer hinten anhängen (s_receive bei dir) 3. vom Anfang des Puffers nachschauen ob ein komplettes Packet enthalten ist (wenn nein, dann Schritt 7) 4. das empfangene Packet aus dem Puffer rausschneiden (also Puffer vorne um diese Länge kürzen) 5. rausgeschnittenes Packet verarbeiten (deine Handle() Methode) 6. zurück zu Punkt 4 (es können mehr als ein komplettes Packet angekommens ein) 7. fertig, Ende der OnClientRead Wie gesagt, das umdeklarieren war nur der erste Schritt, dazu gehört aber mehr. Du hast den Code bis hierher auch selbst entwickelt, also kannst du die Umstellung auch entsprechend machen. |
Re: Serversocket ClientRead Problem
joo danke jetzt gehts aber warum muss ich es so machen?
|
Re: Serversocket ClientRead Problem
Du weisst nie wie die Topologie und Infrastruktur aufgebaut ist und von daher weisst du nicht, wie die Packete aufgeteilt werden. Somit muss dein Code ganz grundlegend damit umgehen können.
Du kannst auch einen anderen Weg einschlagen, das Problem ist einfach nur, dass die Sockets asynchron zu deinem Programm Daten versenden und empfangen. Sie geben dir per Callback (event) explizit Bescheid, wenn irgendwas eintritt, auf das du reagieren musst/kannst. Du hast also eine fertige Event-Driven Architektur, warum willst du diese (resourcenschonende) Verarbeitungsweise mit einem Polling (resourcenfressend) ersetzen? |
Re: Serversocket ClientRead Problem
Mich hat es nur interessiert warum ich es auf diese Weise machen muss.
Jetzt weiss ich es also noch mal danke :-) |
AW: Re: Serversocket ClientRead Problem
Sorry, dass ich einen so alten Thread aufwärme, aber ich habe ein Verständnisproblem mit der folgenden Erklärung:
Zitat:
Aber was passiert, wenn Handle() sehr lange braucht und in der Zwischenzeit über die TCP-Verbindung neue Daten eintreffen, wie wird dann "hintenrum" verfahren(?): - Wird ClientRead parallel (also in einer neuen "Instanz") aufgerufen? (da müssten ClientRead und auch Handle() ja threadsicher sein) - Oder wartet "die Verbindung" so lange, bis Handle() abgelaufen ist, und ruft dann ClientRead erneut auf? Falls das eine Rolle spielt, ich verwende einen nicht-blockierenden ServerSocket. Grüße Caps |
Alle Zeitangaben in WEZ +1. Es ist jetzt 01:04 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz