Delphi-PRAXiS
Seite 1 von 2  1 2      

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Netzwerke (https://www.delphipraxis.net/14-netzwerke/)
-   -   Delphi Server Socket - sendText (https://www.delphipraxis.net/4167-server-socket-sendtext.html)

Billi Berserker 17. Apr 2003 17:21


Server Socket - sendText
 
Ich habe ein kleines Problem mit Server und Client Sockets.
Die Verbindung zwischen beiden steht, Hin und her senden geht auch wunderbar. Nur wenn ich 2 mal direkt hinterander in den Socket schreibe

z.B.
...
socket.SendText('123');
socket.SendText('abc');
...

dann kommt beim Client '123abc' an,
wie kann ich das unterbinden?
ich brauche unbedingt das erst '123' und dann 'abc' ankommt...
Und in einen Timer packen und das ganze versetzt abschicken kommt auch nicht in Frage :wink:

bububox 19. Apr 2003 14:13

Hallo,

genau das gleiche Problem habe ich auch... wollte auch gerade einen Thread erstellen...

Der Client zeigt in einem Memo an, was der Server sendet, zur Verdeutlichung die "<<<":

Code:
procedure TForm1.ClientRead(Sender: TObject; Socket: TCustomWinSocket);
begin
Memo1.Lines.Add('<<< '+Socket.ReceiveText);
end;
Wenn der Client "C000" sendet... schickt der Server 3 SendText's, die der Client aber leider als ein ganzes ClientRead ansieht....

Code:
procedure TForm1.ServerClientRead(Sender: TObject;
  Socket: TCustomWinSocket);
var
receivedshit : string;
sUser : string;
sCName : string;
sLang : string;
begin
sUser := GetUser();
sCName := CurrentComputerName();
sLang := GetOSLanguage();
receivedshit := Socket.ReceiveText;

if Copy(receivedshit,1,4) = 'C000' then
begin
Server.Socket.Connections[0].SendText('S000 '+sUser+#13+#10);
Server.Socket.Connections[0].SendText('S001 '+sCName+#13+#10);
Server.Socket.Connections[0].SendText('S002 '+sLang+#13+#10);
end

end;
Auf dem Memo sieht es dann folgendermaßen aus:

Zitat:

>>> C000
<<< S000 Mein Name halt
S001 Computername
S002 Deutsch (Deutschland)
Mit dem Memo arbeite ich nur provisorisch... wenn es nur um die Darstellung auf dem Memo gehen würde wäre es nicht so schlimm... aber ich möchte jedes SendText vom Server im Client später seperat bearbeiten etc.

Ich hoffe mir/uns kann jemand helfen...

Billi Berserker 19. Apr 2003 16:48

ich hab inzwischen dafür ne Lösung gefunden...
Jede einzelne Nachricht die in den Socket geschrieben wird bekommt einen '-' davor.(Am Ende nichts). Immer wenn der Client oder der Server etwas aus dem Socket ließt dann werden nacheinander alle Strings zwischen zwei '-' bearbeitet...
Wenn man sich dafür einmal ne funktion schreibt die das ganze Zerlegt, am besten noch mit Index, und das dann bei OnRead in ne repeat schleife klemmt mit der man den Text ausm Socket zerlegt dann geht das recht gut...

bububox 19. Apr 2003 16:55

Hm, kannste mal bitte ein Beispiel posten?

edit: Wäre es nicht besser anhand von Zeilenumbruch zu teilen? bei mir wird bestimmt mal "-" vorkommen...

Billi Berserker 19. Apr 2003 17:05

das ist jetzt einfach die funktion GetString aus meinem Projekt...

Delphi-Quellcode:
function TConnectWnd.GetString(Text : String; Index : integer) : String;
var
   stemp : string;
   cIndex,eIndex,n : integer;
begin
     if Pos('-',Text)<>0 then
     begin
          n:=0;
          cIndex:=0;
          stemp:='';  
          repeat
                n:=n+1;
                if Text[n]='-' then cIndex:=cIndex+1;
          until (cIndex=Index) or (n=length(Text));
          if n=length(Text) then
          begin
               GetString:='ERROR | ZU WEIT';
          end
          else
          begin
               cIndex:=n;
               repeat
                     n:=n+1;
               until (n=length(Text)) or (Text[n]='-');
               eIndex:=n;
               if n=length(Text) then eIndex:=eIndex+1;
               for n:=cIndex+1 to eIndex-1 do
               begin
                    stemp:=stemp+Text[n];
               end;
               GetString:=stemp;
          end;
     end
     else GetString:='ERROR | Empfangener String ungültig';
end;
Beispiel :
Es kommt im Socket '-123-abc-defghik' an,
mit dieser funktion lasse ich mir den n-ten String zurück geben.
Wenn man das in eine Repeat schleife von 1 bis Ende macht kann man so bequem alle Strings nacheinander nutzen...


im Client Socket - onRead :
Delphi-Quellcode:
begin
     n:=0;
     Text:=Socket.ReceiveText;
     repeat
          n:=n+1;
          s:=GetString(Text,n);  //Alle Ereignisse aus dem empfagenem String
                                  //zerlegen und einzeln analysieren!

          {...}

     until (GetAktion(s)='ERROR') or (n>20);
end;
bei meinem Programm werden sämtlichte Nachrichten im Netzwerk im format 'AKTION | TEXT' verschickt... ich hab dafür noch zwei funktionen die mir einmal AKTION und einm TEXT zurück liefern, deshalb dort bei until GetAktion(s)... Er beendet halt erst wenn die GetString funktion einen Error zurück gibt.

edit:
Zitat:

Zitat von bububox
edit: Wäre es nicht besser anhand von Zeilenumbruch zu teilen? bei mir wird bestimmt mal "-" vorkommen...

das kannst du machen wie du es brauchst. Er sucht ja einfach nach dem '-' bzw. dem Zeichen was du angiebst...

bububox 19. Apr 2003 18:16

Danke für die Hilfe... scheint die richtige Methode zu sein...

So sendet der Server nun:

Code:
Server.Socket.Connections[0].SendText(#13'S000 '+sUser);
Server.Socket.Connections[0].SendText(#13'S001 '+sCName);
Server.Socket.Connections[0].SendText(#13'S002 '+sLang);
Meine GetString() Funktion:

Code:
function GetString(Text : String; Index : integer) : String;
var
   stemp : string;
   cIndex,eIndex,n : integer;
begin
     if Pos(#13,Text)<>0 then
     begin
          n:=0;
          cIndex:=0;
          stemp:='';
          repeat
                n:=n+1;
                if Text[n]=#13 then cIndex:=cIndex+1;
          until (cIndex=Index) or (n=length(Text));
          if n=length(Text) then
          begin
               GetString:='ERROR | ZU WEIT';
          end
          else
          begin
               cIndex:=n;
               repeat
                     n:=n+1;
               until (n=length(Text)) or (Text[n]=#13);
               eIndex:=n;
               if n=length(Text) then eIndex:=eIndex+1;
               for n:=cIndex+1 to eIndex-1 do
               begin
                    stemp:=stemp+Text[n];
               end;
               GetString:=stemp;
          end;
     end
     else GetString:='ERROR | Empfangener String ungültig';
end;
Dass er nun jede Zeile einzelt bearbeitet scheint soweit zu klappen, Memo:

Zitat:

>>> C000
<<< S000 Vorname Nachname
<<< S001 Computername
<<< S002 Deutsch (Deutschland)
Bei der Repeat-Schleife habe ich allerdings noch ein Problem

Code:
until (GetAktion(s)='ERROR') or (n>20);
Die Funktion GetAktion() habe ich nicht, ich möchte einfach, dass er bis zum letzten String durchmacht, habe provisorisch folgendes gemacht:

Code:
until (n>2);
...was auf Langzeit natürlich nicht hinhaut... da die Inhalte dynamisch werden usw... :| wäre dankbar, wenn jemand dafür noch einen Lösungsvorschlag hätte.

Nebenbei fiel mir noch auf, dass die Caption vom ganzen Form geändert wird sobald der Server etwas sendet.. und zwar in den Inhalt von SendText (?).. dabei habe ich kein einziges mal das Wort "Caption" im Code..

Billi Berserker 19. Apr 2003 19:29

ändere "GetString:='ERROR | ZU WEIT';" und "GetString:='ERROR | Empfangener String ungültig';" zu "GetString:='ERROR';" und mache "until (s='ERROR') or (n>20); "


was das mit der Caption soll weiß ich auch nicht,
such einfach mal in allen Units nach Caption :wink:

magicshadow 29. Apr 2003 19:01

mal ganz was anderes, setze mal zwischen die beiden sends ein "application.processmessages" (hoffe das ist richtig geschrieben) oder ein "sleep(1)"

Dann sollte das auch nach ein ander beim anderen ankommen :)

OrallY 30. Apr 2003 19:06

Ich habe hier noch was dazu gefunden. Der Autor meint, dass wenn man ein Write(0) nach jedem SendText schreibt, tritt das Problem nicht auf. Ich habs allerdings noch nicht getestet.
Delphi-Quellcode:
//Beispiel:
ClientSocket1.Socket.SendText('blabla');
ClientSocket1.Socket.Write(0);
ClientSocket1.Socket.SendText('lalala');
ClientSocket1.Socket.Write(0);
Ansonsten könnte ich noch die Indy-Kompos empfehlen ( www.indyproject.org )

sECuRE 2. Mai 2003 06:27

normalerweise werden mehrere Zeilen mit #13#10 getrennt, meine Parsing-Methode sieht so aus:

Delphi-Quellcode:
procedure TForm1.SocketOnRead(Sender: TObject; Socket: TCustomWinSocket);
var rec:string;
begin
rec:=Socket.ReceiveText;
while (pos(#13#10,rec) <> 0) do begin
ParseMessage(copy(rec,0,pos(#13#10,rec)));
rec:=copy(rec,pos(#13#10,rec)+2,length(rec));
end;
end;
die is'n bischen simpler als die oben gepostete ;)


Alle Zeitangaben in WEZ +1. Es ist jetzt 01:05 Uhr.
Seite 1 von 2  1 2      

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz