oder von Server zu Server. Nachdem hier auf Devtrain schon einige Artikel über Datei-Upload vom Client auf den Server zu finden sind, möchte ich heute auf "automatisierten Download" eingehen. Das heisst, wie kann man eine Datei vom Server auf den Client, oder von Server zu Server transportieren. Und vorallem, wie kann ich das ohne aufwendig programmierte ActiveX-Steuerelemente tun? Das ganze ist mit ASP/JS-Scripting möglich.
Wie funktioniert´s?
Nur über Umwege... Es gibt hier einige Schwierigkeiten...
1. Sie können die Datei nicht direkt holen.
2. Wenn Sie die Daten auf dem Client haben, wie wollen Sie sie binär Speichern
- das Scripting-FileSystem-Object kann nur mit den binär-Funktionen von VB-Script binäre Files abspeichern. Meines Wissens ist das Speichern einer Bin-Datei mittels Javascript und FSO nicht möglich.
Lösung!
- Server
Auf den Server können Sie eine x-beliebige Datei als XML-Stream verpacken ( XML besitzt als Standard einen binären Datentypen). Das so generierte XML-File können Sie direkt in den Response-Stream schreiben.
- Client
Sie erzeugen mittels Javascript XML-Objekte mit denen Sie das XML-File entgegennehmen.
UND SIE VERWENDEN DAS "Stream-Object" von ADO, um diese XML-Daten als File auf dem Client speichern.
Also ergeben sich so einige Software-Voraussetzungen für den Client und den Server.
- XML Object Library (getest mit 3.0)
- Active Data Object Library (getest mit 2.5)
Sicherheitseinstellungen:
Sie müssen die Browser Sicherheitseinstellungen so einstellen, dass ActiveX erlaubt ist.
Sample:
1. Datei auf dem Server als XML-File bereitstellen.
xmlstream.asp
<%@ Language=VBScript %> <% const adTypeBinary = 1 ' Const für Binär-Daten des Stream-Objectes sFilePath = Server.MapPath("./") & "\" & Request.QueryString("FileName") 'File das transportiert werden soll set oDoc = Server.CreateObject("MSXML2.DOMDocument") oDoc.resolveExternals = true ' erzeugen der "Processing Instruction" set oNode = oDoc.createProcessingInstruction("xml", "version='1.0'") set oNode = oDoc.insertBefore(oNode, oDoc.childNodes.Item(0)) ' Root-Element erzeugen set oRoot = oDoc.createElement("Root") set oDoc.documentElement = oRoot oRoot.setAttribute "xmlns:dt", "urn:schemas-microsoft-com:datatypes" set oNode = oDoc.createElement("FileName") oNode.Text = sFilePath oRoot.appendChild oNode ' Knoten-Element für Datei Daten einfügen set oNode = oDoc.createElement("Data") oRoot.appendChild oNode set oEle = oNode ' Zuweisen des Datentyps sorgt für validieren der Daten oEle.dataType = "bin.base64" ' Datei-Daten lesen set oStream = Server.CreateObject("ADODB.Stream") oStream.Type = adTypeBinary oStream.Open oStream.LoadFromFile sFilePath oEle.nodeTypedValue = oStream.Read set oStream = nothing ' Schreiben des XML Contents Response.Clear Response.ContentType="text/xml" Response.Write oDoc.xml %>
|
2. Datei auf dem Client speichern.
GetXMLSaveFile.asp
<%@ Language=VBScript %> <HTML> <HEAD> <SCRIPT LANGUAGE=javascript> <!-- function GetAndSaveAFile(sFileName) { // für XMLHTTP abholen des Streams var XMLHTTP = new ActiveXObject("MSXML2.XMLHTTP"); // open mit false = für syncrones holen der Daten (Async = false) XMLHTTP.open("Get","http://localhost/developer2/XML/XMLStream.asp?FileName=" + sFileName,false); XMLHTTP.send(); var XMLDoc = new ActiveXObject("MSXML2.DOMDocument"); XMLDoc.loadXML(XMLHTTP.responseText);
// Daten-Stream knoten referenziieren var Node = XMLDoc.documentElement.selectSingleNode("/Root/Data");
// mit Hilfe des Stream-Objektes den XML-Daten-Stream als Datei abspeichern var Stream = new ActiveXObject("ADODB.Stream"); Stream.Type=1; // 1 = adTypeBinary Stream.Open(); Stream.Write(Node.nodeTypedValue); Stream.SaveToFile("C:downloadedfile.doc",2); // 2 = adSaveCreateOverWrite } //--> </SCRIPT>
</HEAD> <BODY> <input type="button" name="bGetFile" value="Download a File" onclick="GetAndSaveAFile('File1.doc')"> </BODY> </HTML>
|
TIP!!!Wenn Sie von Server zu Server Dateien transferieren wollen, müssen Sie nur das 2. Script als Server-Script um schreiben.Den kompletten Source-Code gibts natürlich wieder als ZIP-File zum Download.