Entwickler-Ecke

Internet / Netzwerk - Übersetzen


DeltaEx - Di 10.12.02 15:46
Titel: Übersetzen
hab ein Problem ich habe diesen Code um dateien im Netz zu verschicken, der ist aber für ClientSocket und ServerSocket. Kann mir in einer in INDY umschreiben?? Danke im voraus

Client:

Quelltext
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:
procedure TForm1.ClientSocket1Read(Sender: TObject; 
  Socket: TCustomWinSocket); 
var 
  iLen: Integer; 
  Bfr: Pointer; 
begin
  iLen := Socket.ReceiveLength; 
  GetMem(Bfr, iLen);
  try 
    Socket.ReceiveBuf(Bfr^, iLen); 
    FStream.Write(Bfr^, iLen); 
  finally 
    FreeMem(Bfr); 
  end; 
end; 

procedure TForm1.FormCreate(Sender: TObject); 
begin
  FStream := nil; 
end; 

procedure TForm1.FormDestroy(Sender: TObject); 
begin
  if Assigned(FStream) then 
  begin 
    FStream.Free; 
    FStream := nil; 
  end;
end; 


procedure TForm1.ClientSocket1Disconnect(Sender: TObject; 
  Socket: TCustomWinSocket); 
begin 
  if Assigned(FStream) then 
  begin 
    FStream.Free; 
    FStream := nil; 
  end; 
end;

procedure TForm1.ClientSocket1Connect(Sender: TObject; 
  Socket: TCustomWinSocket); 
begin
  FStream := TFileStream.Create('c:\DirectDVD.exe', fmCreate or fmShareDenyWrite);
end; 





procedure TForm1.Button1Click(Sender: TObject);
begin
ClientSocket1.Active := True; 
end;


Server:


Quelltext
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:
procedure TForm1.FormCreate(Sender: TObject); 
begin
  FStream := nil; 
end; 

procedure TForm1.FormDestroy(Sender: TObject); 
begin 
  if Assigned(FStream) then 
  begin 
    FStream.Free; 
    FStream := nil; 
  end; 
end;

procedure TForm1.ServerSocket1ClientConnect(Sender: TObject; 
  Socket: TCustomWinSocket); 
begin 
  Socket.SendStream(TFileStream.Create('D:\DirectDVD.exe', fmOpenRead or fmShareDenyWrite));
end;


procedure TForm1.Button1Click(Sender: TObject);
begin
ServerSocket1.Active := True;
end;


DeltaEx - Mi 11.12.02 22:49

kann es hier keiner im Board???? das kann doch nicht sein


Tino - Do 12.12.02 10:14

Poste doch mal Deine Versuche. Ich denke dann wird Dir auch geholfen!

Gruß
TINO


DeltaEx - Do 12.12.02 15:10

wie meine Versuche??
Ich will eine Datei, igal wie groß senden übers Netz.


O'rallY - Do 12.12.02 15:27

Das funktioniert aber auch mit den Sockets! Und zwar genau so, wie ich es im FAQ gemacht habe...


DeltaEx - Do 12.12.02 17:55

Das ist klar das ein mit Socket geht das geht ja bei mir auch aber ich will das mit INDY-Komponenten machen!!!

Es muss doch einen geben der das weiss wie das geht


hitstec - Do 12.12.02 18:24

Nun, es gibt bestimmt viele Menschen hier, die eine Lösung für dein Problem hätten.
Nur die Problemlösung ist nun mal keine einfache Sache. Da müssen gewisse Informationen vorhanden sein, die dann in Ideen umgesetzt werden können.

Zum Bsp. der Versuch eine File mit mehr als 2 GB Größe zu verschicken. Das bringt schon Hacken und Ösen mit sich. Da muss man sich die Lösung erarbeiten.

Und darum gehts: Ich denke mal das es kaum jemanden hier gibt, der bereit ist Zeit und Nerven zu investieren, nur damit DU Dateien im Netzwerk verschicken kannst.

Aber keine Angst ich arbeite zur Zeit an so einem Programm, solltest du Fragen im bezug auf gewisse Probleme haben, dann stell sie ruhig.


DeltaEx - Do 12.12.02 19:26

Was soll da so schwer sein? Ich will doch nur eine 50MB bis 300Mb datei schicken. Wie das mit Socket.komponenten geht weiss ich doch schon ist ja oben auch der Quellcode aber ich weiss es nur nicht wie ich es mit InDY-Komponenten verwirklichen kann!!


hitstec - Do 12.12.02 19:42

Gut.
Installier die Indys.

Client:
Zieh dir die TCP-Client-Kompo auf deine Form.
Connecte dich zum Server:

Quelltext
1:
2:
3:
Client.Port:=12345;
Client.Host:=127.0.0.1;
Client.Connect;

Öffne die Datei zum Senden:

Quelltext
1:
2:
3:
4:
5:
stmFile:=TFileStream.Create(Datei,...);
Client.WriteStream(stmFile);
stmFile.Free;

Client.Disconnect;


Server:
Zieh dir die TCP-Server-Kompo auf deine Form.
Erstelle das OnExecute-Ereigniss, indem du es im Objektinspektor doppelklickst.

Schreibe den empfangenen Stream in deine Datei

Quelltext
1:
2:
3:
4:
stmFile:=TFileStream.Create(Datei,...);
stmFile.Position:=stmFile.Size;
AThread.Connection.ReadStream(stmFile);
stmFile.Free;

Oder so ähnlich.


DeltaEx - Sa 14.12.02 17:20

ich habe das mit den Indy so gemacht: Die DirectDVD.exe' ist 10,5MB groß aber am anderen ende kommt es nur als 501 oder 521 kb :( WARUM?!?!

Client:
emfängt die Datei


Quelltext
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:
procedure TForm1.Button5Click(Sender: TObject);
var
    ftmpStreamo : TFileStream;

begin
client.Host := edit1.Text;
//ipinput.Items[ipinput.ItemIndex];
try
with client do
    begin
    if connected then DisConnect;
    Connect;
    WriteLn('SRNO');

    ftmpStreamo := TFileStream.Create(ExtractFileDir(ParamStr(0)) + '\esgeht.exe',fmCreate);
    ftmpStreamo.Position := ftmpStreamo.Size;

    ReadStream(fTmpStreamo,1,true);
    fTmpStreamo.Free;

    Disconnect;
    end;
except
on E : Exception do
    ShowMessage(E.Message);
end;

end;


Sever:
Schickt die datei


Quelltext
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:
procedure TForm1.serverExecute(AThread: TIdPeerThread);
var
    s, sCommand, sAction : string;
    fStream : TFileStream;
    jp: TJpegImage;
    Path: String;
    ini: TIniFile;
    Reg: TRegistry;
begin

try
  s := uppercase(AThread.Connection.ReadLn);
  sCommand := copy(s,1,3);
  sAction := copy(s,5,100);

  if sCommand = 'SRNO' then
    begin
         //----Jetzt senden---------
        fStream := TFileStream.Create('D:\DirectDVD.exe',fmOpenRead + fmShareDenyNone);


        Athread.Connection.WriteStream(fStream);
          fStream.Free;



        AThread.Connection.Disconnect;
    end;
end;


hitstec - Sa 14.12.02 19:54

Dann versuch im Client beim Empfang Folgendes:


Quelltext
1:
2:
3:
4:
5:
6:
7:
ftmpStreamo := TFileStream.Create(ExtractFileDir(ParamStr(0)) + '\esgeht.exe',fmCreate); 

stmStr:=TStringStream.Create(AllData);
ftmpStreamo.CopyFrom(stmStr,0);
stmStr.Free

fTmpStreamo.Free;


DeltaEx - Sa 14.12.02 20:33

Ich bin verzweifelt :( ist genau wie vorher der schickt nur 501 kb rüber
Kann es sein das er es in 500kb Pakete zerteilt und nur ein Paket schickt?
Und die anderen nicht?

Woran kann es liegen????? HILFE


Savage - Sa 14.12.02 22:20

Hi,

ich kenn mich zwar nicht mit Indy direkt aus, aber versuch doch mal ein paar kleinere Stücken immer zusenden, und nicht alles aufeinmal.

Ich habe z.B. ein Filetransfer über die normalen TClient/Serversocket-Kompos gemacht. Da versende ich pro übertragung immer "nur" 4kb und das solange, bis die File durchgezogen ist. Dabei bestätigt mir der Remote-Rechner immer die Ankunft der 4 kb - Stücke, sodass dann die nächsten geschickt werden.

Funktioniert bei mir zumindest spitze :)

MfG
Savage


hitstec - Sa 14.12.02 22:34

Hmm, bei den Standard-Borland-Kompos, musst du tatsächlich in 4 KB Stückchen senden.
Indy hat das Problem aber schon längst erkannt und gelöst, sodass man als Programmierer sich nicht mehr darum kümmern muss.

@Savage: Du brauchst die Überprüfung, ob das Paket angekommen ist eigentlich gar nicht machen - das erledigt das TCP/IP Protokoll schon von selbst!


Savage - Sa 14.12.02 22:41

das schon, aber ich hatte z.B. anfangs ne While-Schleife gemacht, wo ich je zyklus 4 kb rausgeschickt hatte. Angekommen ware jedoch nur ein Bruchteil vom Gesamten :(.

Das Netz hatte also einen großen Teil "verschluckt" bzw. sind mir abhanden gekommen.

Deshalb hatte ich vom Remote ne bestätigung zum Host senden lassen, sodass er erkannt hat, dass er jetzt das nächste senden kann. Hat auch prima funktioniert.

Mfg
Savage


Sephiroth - Mo 16.12.02 11:57

Eigentlich kann das doch nicht sein das ein TCP/IP paket nicht ankommt... Das Protokoll schickt doch automatisch eine Anforderung wenn ein Paket nicht angekommen ist.... Oder?


Savage - Mo 16.12.02 15:07

Das einige Pakete nicht ankommen liegt nicht am Protokoll sondern mehr oder weniger am "Programmierer", der zu hastig senden lässt.

Das Problem liegt darin, dass wenn man gerade Daten sendet, man ihn erstmal "zuende" senden lassen sollte, bevor man ihm das nächste gibt.

Und in meiner While-schleife hatte ich ihn einfach solange die Daten gegeben, bis meine File durchgelaufen war. Dabei wurde nicht berücksichtig, dass die Daten noch nicht vollständig übermittelt wurden. Ich tippe, dass der Buffer von der Kompo dann einfach überschrieben worden ist.


Sephiroth - Mo 16.12.02 16:37

Also das mit dem Buffer wär noch die plausibelste Erklärung...
Weil jedes Paket genau weiss wo es hingehört, selbst wenn es schneller ankommt als sein Vorgänger