Wie eine Datei über HTTPS mit Indy 10 und OpenSSL zum Download?
-
19-09-2019 - |
Frage
Ich habe folgende Aufgabe: eine Datei herunterladen HTTPS und Authentifizierung. Indy scheint der Weg zu gehen, aber aus irgendeinem Grund ist es nicht so weit zu arbeiten. Ich habe folgendes statt:
- eine TIdHTTP Komponente, die ich für das Herunterladen verwenden
- eine TIdURI Komponente verwendet, um die URL zu erstellen
- eine TIdSSLIOHandlerSocketOpenSSL Komponente, die die sichere Verbindung zur Verfügung stellen soll. Die erforderlichen DLLs sind im binären Ordner.
Die Seite erfordert auch die Authentifizierung und ich war die Benutzer / Pass in der URL wie im Beispiel unten. Kurz, es ist der Code:
URI := TIdURI.Create('https://test.example.com/');
URI.Username := ParamUserName;
URI.Password := ParamPassword;
HTTP := TIdHTTP.Create(nil);
if URI.Protocol = 'https' then
begin
IOHandler := TIdSSLIOHandlerSocketOpenSSL.Create(nil);
IOHandler.SSLOptions.Method := sslvSSLv3;
HTTP.IOHandler := IOHandler;
end;
HTTP.Get(URI.GetFullURI([ofAuthInfo]), FileStream);
Mit diesem Code, den ich sehr schnell einen "Read Timeout" EIdReadTimeout Exception. Testen Sie die URL in einem Browser funktioniert problemlos. Irgendwelche Ideen auf, was fehlt oder was ich falsch gemacht habe?
Lösung
ich endlich Indy und OpenSSL aufgegeben und verwendet WinInet zum Download bereit. Dies ist der Code, der für mich gearbeitet:
function Download(URL, User, Pass, FileName: string): Boolean;
const
BufferSize = 1024;
var
hSession, hURL: HInternet;
Buffer: array[1..BufferSize] of Byte;
BufferLen: DWORD;
F: File;
begin
Result := False;
hSession := InternetOpen('', INTERNET_OPEN_TYPE_PRECONFIG, nil, nil, 0) ;
// Establish the secure connection
InternetConnect (
hSession,
PChar(FullURL),
INTERNET_DEFAULT_HTTPS_PORT,
PChar(User),
PChar(Pass),
INTERNET_SERVICE_HTTP,
0,
0
);
try
hURL := InternetOpenURL(hSession, PChar(URL), nil, 0, 0, 0) ;
try
AssignFile(f, FileName);
Rewrite(f,1);
try
repeat
InternetReadFile(hURL, @Buffer, SizeOf(Buffer), BufferLen) ;
BlockWrite(f, Buffer, BufferLen)
until BufferLen = 0;
finally
CloseFile(f) ;
Result := True;
end;
finally
InternetCloseHandle(hURL)
end
finally
InternetCloseHandle(hSession)
end;
end;
Andere Tipps
Ich habe das Gleiche gesehen. Einstellen des TIdHTTP.ReadTimeout auf Null behebt das Problem für mich.
...
HTTP.IOHandler := IOHandler;
HTTP.ReadTimeout := 0;
Alle SSL-bezogenen Funktionen für sichere Verbindungen schlägt fehl, wenn einige zusätzliche Bibliotheken korrekt installiert sind.
2.) Entpacken und beiden DLLs in Ihre Projektordner kopieren (oder irgendwo in der PATH Ihres Systems)
mit, dass der Code von der Frage, funktioniert gut für mich.
- reinhard