Webseiten herunterladen per Winsock-Control

Veröffentlicht: 08. Jan 2002 | Aktualisiert: 13. Jun 2004

Von Mathias Schiffer

Mit dem Internet Transfer Control können Sie auf einfachste Weise eine Datei aus dem Internet herunterladen:

Dim sWebPage As String 
sWebPage = Inet1.OpenURL("http://www.microsoft.com/default.htm")

Doch auch die Nutzung des Winsock-Steuerlements bietet sich an, soweit das Internet Transfer Control nicht verwendet werden soll: Selbstverständlich ist in diesem Steuerelement das benötigte HTTP-Protokoll noch nicht berücksichtigt, weshalb ein wenig mehr Aufwand hinter dieser Variante steht.

Der grundsätzliche Ablauf eines Seitenabrufs ist jedoch nicht weiter kompliziert: Der Abrufende sendet eine formulierte Anfrage (den "HTTP Request") an den Server, der Server liefert daraufhin Informationen zur Datei sowie die Datei selbst zurück.

Die formulierte Anfrage an den Server kann etwa so aussehen:

GET /default.htm HTTP/1.0 
Host: www.microsoft.com 
Accept: */* 
Connection: close

Hinter "GET" wird dabei der Pfad zum Dokument auf dem Server angegeben, in der "Host:"-Zeile wird der erwünschte Servername angegeben. Angefragt wird hier also das Dokument http://www.microsoft.com/default.htm. In der Zeile "Accept: */*" wird angegeben, dass beliebige Dokumentarten angenommen werden, während die letzte Zeile darauf hinweist, dass die Verbindung zwischen Anfragendem und Server nach Ablieferung der Datei geschlossen werden soll. Zuletzt wird die Anfrage durch eine Leerzeile beendet.

Eine Antwort des Servers auf diese Anfrage kann beispielsweise so aussehen:

HTTP/1.0 200 OK 
Server: Microsoft -IIS / 5# 
Date: Wed, 23 Aug 2000 11:23:58 GMT 
Content-Type: text/html 
Accept-Ranges: bytes 
Last-Modified: Mon, 10 Aug 2000 17:15:16 GMT 
ETag: "a9c235318ac01:884" 
Content-Length: 5462 
Age: 0 
Connection: Close 
<HTML> 
... 
</HTML>

In den ersten Zeilen (dem "HTTP Header") finden sich diverse Informationen über den Fehlerstatus der Anfrage und über das abgerufene Dokument. Nach diesen Angaben folgt eine Leerzeile, nach der das eigentliche Dokument beginnt. Auf diesen Teil der Serverantwort bezieht sich die Headerzeile "Content-Length: 5462": Im Beispiel wäre das Dokument 5462 Bytes lang. Diese Information macht es möglich, die päckchenweise ankommenden Daten auf das Ende einer vollständigen Übertragung hin zu prüfen.

Mit Hilfe des Winsock-Controls ergibt sich damit ein durchaus noch überschauberer Code für das Herunterladen eines Dokuments:

Private Sub Connect() 
' Diese Prozedur rufen Sie auf, um den Download zu starten: 
  With Winsock1 
    .RemoteHost = "www.microsoft.com" 
    .RemotePort = 80 ' HTTP-Standardport 
    .Connect 
  End With 
End Sub 
Private Sub Winsock1_Connect() 
' Nach erfolgreicher Kontaktaufnahme HTTP-Anfrage zum Server senden 
Dim sRequest As String 
  ' HTTP-Anfrage erstellen und mit leerer Zeile abschließen: 
  sRequest = "GET /default.htm HTTP/1.0" & vbNewLine 
  sRequest = sRequest & "Host: www.microsoft.com" & vbNewLine 
  sRequest = sRequest & "Accept: */*" & vbNewLine 
  sRequest = sRequest & "Connection: close" & vbNewLine 
  sRequest = sRequest & vbNewLine 
  ' Die Anfrage absenden: 
  Winsock1.SendData sRequest 
End Sub 
Private Sub Winsock1_DataArrival(ByVal BytesTotal As Long) 
' Es kommen Daten vom RemoteHost an 
Static sReply As String 
Dim sNewData As String 
Dim lPos1 As Long 
Dim lPos2 As Long 
Dim lLenHeader As Long 
Dim lLenBody As Long 
  ' Neue Daten abholen und anhängen 
  Winsock1.GetData sNewData 
  sReply = sReply & sNewData 
  ' Im Header die Größenangabe des Dokuments suchen: 
  lPos1 = InStr(sReply, "Content-Length: ") + 16 
  If lPos1 = 16 Then ' Noch nicht angekommen 
    Exit Sub 
  End If 
  ' Den folgenden Zeilenumbruch suchen: 
  lPos2 = InStr(lPos1, sReply, vbCrLf) 
  If lPos2 = 0 Then ' Noch nicht angekommen 
    Exit Sub 
  End If 
  ' Hieraus die Größe des Dokuments in Bytes ermitteln: 
  lLenBody = Val(Mid$(sReply, lPos1, lPos2 - (lPos1))) 
  ' Die Abtrennung zwischen HTTP-Header und HTML-Code suchen: 
  lLenHeader = InStr(sReply, vbNewLine & vbNewLine) + 3 
  If lLenHeader = 3 Then ' Noch nicht angekommen 
    Exit Sub 
  End If 
  ' Ist die Übertragung vollständig? 
  If Len(sReply) - lLenHeader = lLenBody Then 
    ' HTML-Code (ohne Header) in einem Textbox-Control anzeigen 
    sReply = Mid$(sReply, lLenHeader + 1) 
    txtSource.Text = sReply 
  End If 
End Sub