FtpWebRequest Datei herunterladen Falsche Größe
-
02-10-2019 - |
Frage
Ich verwende den folgenden Code, um eine Datei von einem entfernten FTP-Server heruntergeladen werden:
FtpWebRequest request = (FtpWebRequest)WebRequest.Create(serverPath);
request.KeepAlive = true;
request.UsePassive = true;
request.UseBinary = true;
request.Method = WebRequestMethods.Ftp.DownloadFile;
request.Credentials = new NetworkCredential(userName, password);
using (FtpWebResponse response = (FtpWebResponse)request.GetResponse())
using (Stream responseStream = response.GetResponseStream())
using (StreamReader reader = new StreamReader(responseStream))
using (StreamWriter destination = new StreamWriter(destinationFile))
{
destination.Write(reader.ReadToEnd());
destination.Flush();
}
Die Datei, die ich heruntergeladen habe eine dll und mein Problem ist, dass es in irgendeiner Weise durch dieses Verfahren geändert wird. Ich weiß das, weil die Dateigröße zunimmt. Ich habe den Verdacht, dass dieser Abschnitt des Code fehlerhaft ist:
destination.Write(reader.ReadToEnd());
destination.Flush();
Kann jemand bieten alle Ideen, was falsch sein kann?
Lösung
StreamReader
und StreamWriter
Arbeit mit Zeichendaten, so dass Sie den Strom von Bytes Zeichen entschlüsselt und dann codiert, wieder zu Bytes. Eine DLL-Datei enthält binäre Daten, so dass dieser Round-Trip-Konvertierungsfehler einführen. Sie möchten direkt aus dem responseStream
Objekt und Schreiben auf eine FileStream
lesen Bytes, die nicht in einem StreamWriter
gewickelt ist.
Wenn Sie .NET 4.0 verwenden können Sie verwenden Stream.CopyTo
, aber sonst werden Sie den Stream manuell kopieren. diese Frage Stackoverflow eine gute Methode hat Ströme zum Kopieren :
public static void CopyStream(Stream input, Stream output)
{
byte[] buffer = new byte[32768];
while (true)
{
int read = input.Read(buffer, 0, buffer.Length);
if (read <= 0)
return;
output.Write(buffer, 0, read);
}
}
Also, Ihr Code wie folgt aussehen:
using (FtpWebResponse response = (FtpWebResponse)request.GetResponse())
using (Stream responseStream = response.GetResponseStream())
using (FileStream destination = File.Create(destinationFile))
{
CopyStream(responseStream, destination);
}