Click here to Skip to main content
Click here to Skip to main content

File Server - Web Service

By , 22 Feb 2003
 

Introduction

This article shows how to use Web Services to create a service to manage (put and get) files in your Web Server using HTTP protocol.

If you don't have a physical access to the web server or just for sharing your web server content like pictures or files, this web service can be really useful and fast.

The code

So, let's stop talking and go to the code : )

First we need to import extra classes:

Imports System.Web.Services
Imports System.Configuration
Imports System.IO

A basic enumerator of files extensions:

Public Enum FileExtensions
        htm
        html
        asp
        aspx
        jpg
        gif
        dll
        exe
        all
End Enum

The class FileInformation will be populated with information about each file.

Public Class FileInformation
        Public Name As String
        Public Size As Long
        Public CreadedDate As DateTime
        Public LastModified As DateTime
        Public LastAccess As DateTime
        Public FileType As String
        Public FileLocation As String
        Public FileContent As Byte()
End Class

The WebMethod Browse will return an array of FileInformation class:

<!--<WebMethod(Description:="Retrieve an array of files 
                      with name, attributes and content.")> _-->
Public Function Browse(ByVal VirtualPath As String, ByVal FileExtension _
                       As FileExtensions) As FileInformation()
        Dim i As Integer
        Dim fi As FileInfo
        Dim aFiles As FileInformation()
        Dim mExtension As String
        Select Case FileExtension
            Case FileExtensions.asp
                mExtension = "asp"
            Case FileExtensions.aspx
                mExtension = "aspx"
            Case FileExtensions.gif
                mExtension = "gif"
            Case FileExtensions.htm
                mExtension = "htm"
            Case FileExtensions.html
                mExtension = "html"
            Case FileExtensions.jpg
                mExtension = "jpg"
            Case FileExtensions.dll
                mExtension = "dll"
            Case FileExtensions.exe
                mExtension = "exe"
            Case FileExtensions.all
                mExtension = "*"
        End Select

        Dim di As New DirectoryInfo(WebServerPath & VirtualPath)
        Dim afi As FileInfo() = _
         di.GetFiles("*." & mExtension)

        ReDim Preserve aFiles(afi.Length - 1)

        For Each fi In afi
            aFiles(i) = New FileInformation()
            aFiles(i).Name = fi.Name
            aFiles(i).Size = fi.Length
            aFiles(i).LastAccess = fi.LastAccessTime
            aFiles(i).CreadedDate = fi.CreationTime
            aFiles(i).LastModified = fi.LastWriteTime
            aFiles(i).FileType = fi.Extension
            aFiles(i).FileLocation = fi.DirectoryName
            aFiles(i).FileContent = ReadFile(WebServerPath & _
                                     VirtualPath & "\" & fi.Name)
            i += 1
        Next
        Return aFiles
End Function

The Private Shared method ReadFile returns a byte() with the file content:

Private Shared Function ReadFile(ByVal FilePath As String) As Byte()
        Dim fs As FileStream
        Try
            ' Read file and return contents
            fs = File.Open(FilePath, FileMode.Open, FileAccess.Read)
            Dim lngLen As Long = fs.Length
            Dim abytBuffer(CInt(lngLen - 1)) As Byte
            fs.Read(abytBuffer, 0, CInt(lngLen))
            Return abytBuffer
        Catch exp As Exception
            Return Nothing
        Finally
            If Not fs Is Nothing Then
                fs.Close()
            End If
        End Try
End Function

UploadFile WebMethod is used to send a single file to the web server:

<!--<WebMethod(Description:="Upload a single file to
                                                 web server.")> _-->
Public Function UploadFile(ByVal VirtualPath As String, _
           ByVal Name As String, ByVal Content As Byte()) As Boolean
        Dim objFile As File, objStream As StreamWriter, _
                                 objFstream As FileStream
        Try
            objFstream = File.Open(WebServerPath & VirtualPath & "\" & _
                                Name, FileMode.Create, FileAccess.Write)
            Dim lngLen As Long = Content.Length
            objFstream.Write(Content, 0, CInt(lngLen))
            objFstream.Flush()
            objFstream.Close()
            Return True
        Catch exc As System.UnauthorizedAccessException
            Return False
        Catch exc As Exception
            Return False
        Finally
            If Not objFstream Is Nothing Then
                objFstream.Close()
            End If
        End Try
End Function

The WSFileServer has another two useful methods called DirectoryExists and FileExists.

Using the code

There is a simple console application to retrieve a list of files. First create a new console application project and add a Web Reference to that:

Now add an import to System.IO class, we need that for the save file method.

Imports System.IO

Add some private variables:

Private mWSFileServer As WSFileServer.FileServer
Private mFileInformation() As WSFileServer.FileInformation
Private mBar As New String("-", 50)
Public Const SaveFilePath As String = "C:\Temp\"

Now we'll create a method to save the file content, receiving the filename and file content:

Public Function SaveFile(ByVal Name As String, _
                           ByVal Content As Byte()) As Boolean
        Dim objFstream As FileStream
        Try
            objFstream = File.Open(SaveFilePath & Name, _ 
                            FileMode.Create, FileAccess.Write)
            Dim lngLen As Long = Content.Length
            objFstream.Write(Content, 0, CInt(lngLen))
            objFstream.Flush()
            Return True
        Catch exp As Exception
            Return False
        Finally
            objFstream.Close()
        End Try
End Function

The Sub Main method will initialize the file server Web service and show each file's specified web server virtual path:

Sub Main()
        Try
            mWSFileServer = New WSFileServer.FileServer()
            mFileInformation = mWSFileServer.Browse("/ProgramGuide", _
                                     WSFileServer.FileExtensions.aspx)
            Dim i As Integer
            For i = 0 To mFileInformation.Length - 1
                With mFileInformation(i)
                    Console.WriteLine(mBar.ToString())
                    Console.WriteLine("File: {0}", .Name)
                    Console.WriteLine("Size: {0}", .Size)
                    Console.WriteLine("Location: {0}", .FileLocation)
                    Console.WriteLine("LastModified: {0}", .LastModified)
                    Console.WriteLine("CreateDate: {0}", .CreadedDate)
                    Console.WriteLine("LastAccess: {0}", .LastAccess)
                    If SaveFile(.Name, .FileContent) Then
                        Console.WriteLine("File saved sucessfull at:{0}", _
                                                   SaveFilePath & .Name)
                    Else
                        Console.WriteLine("Save file failure!")
                    End If
                End With
            Next
            Console.WriteLine(mBar.ToString())
            Console.Read()
        Catch exp As Exception
            Console.WriteLine(mBar)
        Finally
            mWSFileServer.Dispose()
        End Try
End Sub

The result of the web service call can be seen in the following screen:

Console application calls the Browser method of the web service, displays all files information and saves it.

Points of interest

I think that when you use Web Services technology, there are no limits for your applications, you just need to be creative ;-)

History

  • 2/18/2003 - First release.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here

About the Author

Ricardo Martins
Architect Sky Brasil
Brazil Brazil
Member
Ricardo Martins
.NET Architect
Brazil

Sign Up to vote   Poor Excellent
Add a reason or comment to your vote: x
Votes of 3 or less require a comment

Comments and Discussions

 
You must Sign In to use this message board.
Search this forum  
    Spacing  Noise  Layout  Per page   
Generalok articlememberDonsw22 Nov '09 - 14:19 
Ok article especially written in 2003
 
cheers,
Donsw
My Recent Article : CDC - Change Data Capture

GeneralPermission to publicmembersubramanya198327 Apr '08 - 20:34 
Hi,
 
I am writing a document on uploading files using web service and planning to post it on our Knowledge Management intranet in our company, so that other employees in my company can also benefit from reading it. I came across an article written by you on the same subject. I would like to include parts of this in my document. I request you to kindly grant me permission to do so. I assure you that I would give appropriate credits and references (in-line citations) to your article in my document
 
Regards,
Subramanya
GeneralRe: Permission to publicmemberRicardo Martins28 Apr '08 - 5:30 
Subramanya,
 
Feel free to use this article / code as you need.
It's shared for all.
 
Best regards and thanks for your feedback
Ricardo
 
Ricardo Martins
.NET Architect
ricarddo@terra.com.br

GeneralThank You for this great article [modified]memberYaagoub20 Sep '07 - 10:37 
You have saved my life and time, as I needed such web service to complete my Flex project. I do really appreciate sharing your project. Smile | :)
 
I would also appreciate if you email me the Client version you mentioned that uses this web service.
 
Yaagoub Al-Nujaidi
Flex Developer (Beginner)
 

-- modified at 23:21 Thursday 20th September, 2007
GeneralUpload Doesn't Workmemberjtokach25 Apr '07 - 8:27 
I am unable to get the uploadfile method to work. I set permissions for ASPNET to full, and then everyone to FULL but still no go even though the return is TRUE.
QuestionWant to upload my text file to local server using vs .net console applicationmembersonimitu2 Apr '07 - 19:12 
Hello,
I am doing project in .net and i want t upload my text file to local server so what i have to do? can u guide me please??
 
M I T U

GeneralUpload Problemmemberall4it19 Dec '06 - 8:05 
Dear ,
i'm tring to upload tif file (Multi Pages) but i get exception,please replay,
thanx
The Exception Description:
 
System.Web.Services.Protocols.SoapException was unhandled
Actor=""
Lang=""
Message="System.Web.Services.Protocols.SoapException: There was an exception running the extensions specified in the config file. ---> System.Web.HttpException: Maximum request length exceeded.
at System.Web.HttpRequest.GetEntireRawContent()
at System.Web.HttpRequest.get_InputStream()
at System.Web.Services.Protocols.SoapServerProtocol.Initialize()
--- End of inner exception stack trace ---
at System.Web.Services.Protocols.SoapServerProtocol.Initialize()
at System.Web.Services.Protocols.ServerProtocolFactory.Create(Type type, HttpContext context, HttpRequest request, HttpResponse response, Boolean& abortProcessing)"
Node=""
Role=""
Source="System.Web.Services"
StackTrace:
at System.Web.Services.Protocols.SoapHttpClientProtocol.ReadResponse(SoapClientMessage message, WebResponse response, Stream responseStream, Boolean asyncCall)
at System.Web.Services.Protocols.SoapHttpClientProtocol.Invoke(String methodName, Object[] parameters)
at UploadFileToServer.WSFileServer.FileServer.UploadFile(String VirtualPath, String Name, Byte[] Content) in C:\Documents and Settings\Administrator\My Documents\Visual Studio 2005\Projects\UploadFileToServer\UploadFileToServer\Web References\WSFileServer\Reference.vb:line 213
at UploadFileToServer.Form1.btnBrowse_Click(Object sender, EventArgs e) in C:\Documents and Settings\Administrator\My Documents\Visual Studio 2005\Projects\UploadFileToServer\UploadFileToServer\Form1.vb:line 16
at System.Windows.Forms.Control.OnClick(EventArgs e)
at System.Windows.Forms.Button.OnClick(EventArgs e)
at System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent)
at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
at System.Windows.Forms.Control.WndProc(Message& m)
at System.Windows.Forms.ButtonBase.WndProc(Message& m)
at System.Windows.Forms.Button.WndProc(Message& m)
at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m)
at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
at System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg)
at System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(Int32 dwComponentID, Int32 reason, Int32 pvLoopData)
at System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context)
at System.Windows.Forms.Application.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context)
at System.Windows.Forms.Application.Run(ApplicationContext context)
at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.OnRun()
at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.DoApplicationModel()
at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.Run(String[] commandLine)
at UploadFileToServer.My.MyApplication.Main(String[] Args) in 17d14f5c-a337-4978-8281-53493378c1071.vb:line 81
at System.AppDomain.nExecuteAssembly(Assembly assembly, String[] args)
at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Threading.ThreadHelper.ThreadStart()

 
Mezian Ziad Altawill
Software & Information Systems Engineer
Hamah - Syria
Phone: +963 95 573070
Email: mz_altawill82@hotmail.com

QuestionHow about C# Version {Please}member| Muhammad Waqas Butt |28 Apr '06 - 1:02 
Ha Nice Infact Very Nice Artical. Can you please make a C#.Net Version Please.
 
|Muhamad Waqas Butt|
waqasb4all@yahoo.com
www.sktech.freewebspace.com
AnswerRe: How about C# Version {Please}memberRicardo Martins8 Jun '09 - 14:08 
Hi,
 
please take a look at this article http://www.codeproject.com/KB/webservices/wcftransfer.aspx
 
The solution is very similar to my article but WCF based ...
 
Best Regards,
 
Ricardo Martins
.NET Architect
ricarddo@terra.com.br

GeneralTransfering large filesmemberNigel-Findlater20 Jan '05 - 3:11 
I am trying to biuld a web service designed to transfer files between 5 and 15 MB big. There are a number of problems connected with transfering large amounts of data over a webservice:
 
1. The default timeout is 90 s
2. The default maximum data is 4.9 MB
3. The SOAPhandler does not know when a webservice has been stopped (it waits for the timeout to happen)
 
This means:
Simply increasing the timeout and maximum data sizes cause the problem that if a number of users simply stop the data transfer before completion the thread pool for webservices will run out causing Denial of Service
 
There are 2 choices:
 
1. Transfer data in one shot
2. Tranfer the data by paging through the data set.
 
If you transfer in one shot:
1. The user may not stop the transfer process
2. You need to at least increase the maximum data size (and probably the timeout)
3. You need SOAPExtentions to handle the problem with threads
 
If you transfer data by paging
1. You need to setup some kind of background operation to asynchrously transfer data.
2. You need some way of marking or deleting data that has already been transfered, just in case the program is terminated
3. You need a mechanism of reconstructing the data and possibly testing for incomplete datasets
 
In both cases data compression is usefull to reduce the transmition times
 
Has anyone got an example of a webservice that can handle the uploading of large files. In particular SOAPExtensios that zip the data being transfered?
 
Does anyone know if there is a better way of doing this with the WebService Service Pack 2?
 
have fun...
 
Nigel...
GeneralUpload Functionmemberokantekeli15 Feb '04 - 22:43 
How can we upload function? I can't use it. Please Help. Does anybody can give me an example?
GeneralRe: Upload FunctionsussShawn Carr30 Apr '04 - 7:41 
This is not exect but it should get you close
 
http://www.webserviceresource.com
 
Shawn Carr
WebService Resource

GeneralCall the webservice from an HTML formmemberkcl6 Jan '04 - 6:34 
Hi people, hope you can help...
 
I've been trying to get a similar webservice running but to be able to access it using plain HTML (not an ASPX page - the HTML code will be generated and run by a Flash UI which needs to post to the webservice)
 
I have seen that this is possible by creating some code behind and manipulating the file object and THEN sending it to the webservice - but we need to be able use a static HTML page which is not hosted on the .NET server. I really don't want to have to have the Flash UI call an ASPX page, for that ASPX page to then call the WebService - it breaks our security model to name just one.
 
E.g. - the simple HTML form might look like:
 
<HTML>
<HEAD>
	<TITLE>Test File Uploader
	</TITLE>
</HEAD>
<BODY>
	<FORM action="http://mydomain/myWebService/myWebService.asmx/UploadFile" method="POST" enctype="multipart/form-data" id="form1">
		Name: <INPUT TYPE="text" Name="filename" /><br />
		File: <INPUT TYPE="file" Name="file" /><br /><br />
		<INPUT TYPE="submit" Value="Upload" />
	</FORM>
</BODY>
</HTML>
 
But the error thrown is:
 
System.InvalidOperationException: Request format is invalid: multipart/form-data; boundary=---------------------------7d413e1db08b4.
at System.Web.Services.Protocols.HttpServerProtocol.ReadParameters()
at System.Web.Services.Protocols.WebServiceHandler.Invoke()
at System.Web.Services.Protocols.WebServiceHandler.CoreProcessRequest()

 
I'm guessing this is all to do with the webservice needing to receive the right type of HTTP request encoding....
 
Anyone any bright ideas for a solution?
 
Thanks in advance!!

 
KCL
GeneralWSFileServer.FileExtensions.aspxsussAnonymous11 Dec '03 - 9:47 
where is the WSFileServer.FileExtensions.aspx file at?
 
thanks,
 
tom
GeneralBinary UploadersussLuis Botero9 Dec '03 - 3:57 
The following code is to upload binary files. The code provided in the article works well for text files.
 
WebService
==========
///
///
///

/// Encoded binary file
/// Contains virtual directory and filename
///
[WebMethod]
public bool UploadFile(Byte[] fs, string strFullFileName)
{
BinaryWriter objWriter = null;
FileStream fsStream = null;
try
{
// Make sure directory exists
string strFolderName = Utils.GetFolderFromPath(strFullFileName);
string strFileName = Utils.GetFileNameFromPath(strFullFileName);
CreateDirectory(strFolderName);
string strLocalPath = Context.Request.MapPath(strFolderName);
string strFullLocalPath = Utils.JoinPaths(strLocalPath, strFileName);
// Remove file if already exists
DeleteFile(strFolderName, strFileName);
// Upload file
fsStream = new FileStream(strFullLocalPath, FileMode.CreateNew);
objWriter = new BinaryWriter(fsStream);
objWriter.Write(fs);
objWriter.Flush();
}
catch (Exception ex)
{
try {throw new AdminToolException(ex);}
catch{}
return false;
}
finally
{
if (objWriter != null) objWriter.Close();
if (fsStream != null) fsStream.Close();
}
return true;
}
 

Example
=======
///
/// Uploads a file to a URL
///

///
///
///
private bool UploadFile(string strSourceFilePath, string strTargetFilePath)
{
FileStream fsStream = null;
BinaryReader objReader = null;
try
{
myWebServiceClass objMyWebServiceCls
= new myWebServiceClass ();
string strFileNameOnly = Utils.GetLastAppPath(strTargetFilePath, 1);
// If source is Url, then download file first
if (Utils.ValidateURL(strSourceFilePath))
{
WebClient objWebClient = new WebClient();
string strLocalPath = Utils.JoinPaths(
Application.StartupPath, strFileNameOnly);
objWebClient.DownloadFile(strSourceFilePath, strLocalPath);
strSourceFilePath = strLocalPath;
}
// Now, read binary file
fsStream = new FileStream(strSourceFilePath, FileMode.Open, FileAccess.Read);
Byte[] bytBytes = new byte[fsStream.Length];
objReader = new BinaryReader(fsStream);
objReader.Read(bytBytes, 0, bytBytes.Length);
// And, upload file through web service
objMyWebServiceCls.UploadFile(bytBytes, strTargetFilePath);
}
catch (Exception ex)
{
return false;
}
finally
{
if (objReader != null) objReader.Close();
if (fsStream != null) fsStream.Close();
}
return true;
}

GeneralRe: Binary UploadermemberRicardo Martins9 Dec '03 - 13:32 
Hi Luis,
 
Thank you to send a code for upload Binary Files.
I think the main subject of Code Project is: "Knowledge Exchange", and when we post a code, make comments, test applications etc, we just do it!
 
Thank you one more time.Smile | :)
 
Regards,

 
Ricardo Martins
Senior Web Analyst - ASP & .NET Technologies
Brazil
QuestionAre there practical limitations to file size?memberjweiss19 Nov '03 - 11:59 
What considerations should I address regarding file size? Is it practical to simply assume the service can accomodate any size file? Even if it can reliably handle rather large files (say >50Mb )does response time become an issue?
Thanks.
-jeff
AnswerRe: Are there practical limitations to file size?memberThomas-H.26 Oct '05 - 5:13 
there are a lot of restrictions:
 
1st) Setting in config-File for maxRequestLength
2nd) Memory of WebServerprocess. Files are loaded into memory first and then available within .NET-Code. This means large files or a lot of uploads at the same time will easily kill the server.
3rd) Max-Memory usage of IIS. There is a memory limit when IIS will kill a process, because it does try to prevent running out of memory due to memory leaks.
 
There is an article by Microsoft at http://support.microsoft.com/default.aspx?scid=kb;en-us;323245
about how to upload a file via .NET and the problems with it.
 
If anyone has a solution how to stream a file directly uploaded to a webservice directly to disk let me know.

Questionwhat about the upload method?sussvinhvu2 Oct '03 - 8:50 
Can you please give example on how to implement on uploading method?? Thanks.
Generalupload functionmemberguru3721 Apr '03 - 23:12 
Can you give an example on how to implement the upload function, I am having trouble defining the "content" parameter of the function. Thanks;P
 
Ivan
Generalupload functionmemberguru3721 Apr '03 - 23:08 
Can you give an example on how to implement the upload function, I am having trouble defining the "content" parameter of the function. Thanks;P
QuestionHow about retries or resuming?memberMatt Philmon24 Feb '03 - 5:07 
It would be particularly neat if you could build into the process the ability to resume an aborted or failed transfer. Would that be possible with this? With FTP you can do this if the FTP server supports it.
AnswerRe: How about retries or resuming?memberRicardo Martins26 Feb '03 - 0:17 
Hi Matt,
 
Well, I think that to implement a routine for resume an aborted tranfer can be a little complicated.
See the message posted by Jan, his sugestion is to broke a file in blocks of 100 kb and tranfer each block over web service, using that idea we can think about the way to create a resume feature.
Sincerely, my suggestion is to implement a FTP server that supports abort/retry features and deploy the midware component to interact with this FTP server over TCP and then to publish the methods of this component as a Web Service.

I hope that my answer is useful for you.

 
Regards,
Suspicious | :suss: Ricardo Martins
Senior Web Analyst - ASP & .NET Technologies
Brazil
GeneralRe: How about retries or resuming?memberNigel-Findlater20 Jan '05 - 3:01 
Hallo Jan,
 
Last year you made a comment about using an FTP Server which supports abort/retry features. Do you have a suggestion which one to choose?
 
Nigel...

GeneralSome ideasmemberJan Tielens23 Feb '03 - 20:45 
Hi,
 
First of all, thanx for your article!
 
I've some ideas, in case you want to extend your work. For example, I think it would be nice if there could be some sort of notification when files are recieved or sent. So it would be possible for the client app. to display a progress bar or something like that.
 
Greetz
Jan

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Permalink | Advertise | Privacy | Mobile
Web03 | 2.6.130523.1 | Last Updated 23 Feb 2003
Article Copyright 2003 by Ricardo Martins
Everything else Copyright © CodeProject, 1999-2013
Terms of Use
Layout: fixed | fluid