Upload is not the only reason to need access to binary files - you may need
to construct a protected download system and send the files through an ASP page.
Or you may want to construct download packaging system - user selects what
he/she wants to download, your application packs it in one file and user
downloads it and unpacks it locally (could be very simple with ALP on the user's
machine). We will not try to list here all the possible reasons to access binary
files - the benefits are obvious - more features are always a plus. If they are
not required today, further enhancements of the application may need them and if
they are all in one DLL there is no need to spend time to search more and more
components for every particular task.
Have you ever have the synchronization problem with ASP when you need to
read/write to a file from many pages concourently? If so - the solution is
simple. You just create the free threaded version of SFMain (the root component
of the Storages and Files set), then open the desired file and keep it in a
Session or Application variable. Thus all the file operations will occur through
the same instance of the object and will be automatically synchronized avoiding
data loses. If you need better performance do one step further - leave the
files. Load the file into the memory and just update the disk file when the
application unloads for example. You will be still able to use it as text file
or file containing records.
Let see some very simple sample code (more samples are included in the download
package):
Let us send a local file to the client:
Set sf = Server.CreateObject("newObjects.utilctls.SFMain")
Set f = sf.OpenFile(Server.MapPath("somefile.gif"))
Response.ContentType = "image/gif"
Response.BinaryWrite f.ReadBin(f.Size)
Put a file into a storage:
Set sf = Server.CreateObject("newObjects.utilctls.SFMain")
Set stg = sf.OpenStorage(Server.MapPath("mystorage.stg"))
Set f = sf.OpenFile(Server.MapPath("somefile.gif"))
Set strm = stg.CreateStream("somefile.gif")
f.CopyTo strm, f.Size
The same but if we want to copy to directory will look:
Set sf = Server.CreateObject("newObjects.utilctls.SFMain")
Set stg = sf.OpenDirectory(Server.MapPath("mydirectory"))
Set f = sf.OpenFile(Server.MapPath("somefile.gif"))
Set strm = stg.CreateStream("somefile.gif")
f.CopyTo strm, f.Size
Well in fact in case of directory it can be done in much simple way:
Set sf = Server.CreateObject("newObjects.utilctls.SFMain")
sf.CopyFile Server.MapPath("somefile.gif"), Server.MapPath("mydirectory")
But if we want the same code to deal with the both cases it makes sense to
treat the directory as storage.
Let us read some records from a file:
Set sf = Server.CreateObject("newObjects.utilctls.SFMain.free")
Application.Lock
If Not IsObject(Application("TheFile")) Then
Set Application("TheFile") = sf.OpenFile(Server.MapPath("thefile.bin")
End If
Application.Unlock
' To shorten the next statements let use a variable
Set f = Application("TheFile")
Set rec = Server.CreateObject("newObjects.utilctls.SFRecord")
rec.AddField "Name", vbString, 31
rec.AddField "Age", vbLong
rec.AddField "Sex", vbBoolean
rec.AddField "Weight", vbInteger
rec.BindTo f
rec.Filter.unicodeText = False
f.Pos = 0
Application.Lock
While Not f.EOS
Response.Write "Name: " & rec("Name") & " Age: " & reg("Age") & "
"
rec.MoveNext
Wend
Application.Unlock
Looks like a DB, isn't it? But this is just a file. Why using the ASP
Application - this ensures all the operations will be performed with the same
instance of the SFStream object (the f variable in the sample). By default the
files are opened in exclusive mode (can be changed using the optional flags).
Using the same object for each operation will ensure the file consistency if
some other page attempts write operation for example. If the file is personal
for each user session we can use Session instead of Application. Lock method
lacks? Not a problem - create one CustomLock object (in this package too), set
it in a Session variable and use its Lock and Unlock methods to synchronize
the operations.
See the documentation and the samples in the package for more information.