How can I get an ASP.net web form (v3.5) to post a file using a plain old <input type="file" />
?
I am not interested in using the ASP.net FileUpload server control.
How can I get an ASP.net web form (v3.5) to post a file using a plain old <input type="file" />
?
I am not interested in using the ASP.net FileUpload server control.
In your aspx :
<form id="form1" runat="server" enctype="multipart/form-data">
<input type="file" id="myFile" name="myFile" />
<asp:Button runat="server" ID="btnUpload" OnClick="btnUploadClick" Text="Upload" />
</form>
In code behind :
protected void btnUploadClick(object sender, EventArgs e)
{
HttpPostedFile file = Request.Files["myFile"];
//check file was submitted
if (file != null && file.ContentLength > 0)
{
string fname = Path.GetFileName(file.FileName);
file.SaveAs(Server.MapPath(Path.Combine("~/App_Data/", fname)));
}
}
Here is a solution without relying on any server-side control, just like OP has described in the question.
Client side HTML code:
<form action="upload.aspx" method="post" enctype="multipart/form-data">
<input type="file" name="UploadedFile" />
</form>
Page_Load method of upload.aspx :
if(Request.Files["UploadedFile"] != null)
{
HttpPostedFile MyFile = Request.Files["UploadedFile"];
//Setting location to upload files
string TargetLocation = Server.MapPath("~/Files/");
try
{
if (MyFile.ContentLength > 0)
{
//Determining file name. You can format it as you wish.
string FileName = MyFile.FileName;
//Determining file size.
int FileSize = MyFile.ContentLength;
//Creating a byte array corresponding to file size.
byte[] FileByteArray = new byte[FileSize];
//Posted file is being pushed into byte array.
MyFile.InputStream.Read(FileByteArray, 0, FileSize);
//Uploading properly formatted file to server.
MyFile.SaveAs(TargetLocation + FileName);
}
}
catch(Exception BlueScreen)
{
//Handle errors
}
}
You'll have to set the enctype
attribute of the form
to multipart/form-data
;
then you can access the uploaded file using the HttpRequest.Files
collection.
use the HTML control with a runat server attribute
<input id="FileInput" runat="server" type="file" />
Then in asp.net Codebehind
FileInput.PostedFile.SaveAs("DestinationPath");
There are also some 3'rd party options that will show progress if you intrested
Yes you can achive this by ajax post method. on server side you can use httphandler. So we are not using any server controls as per your requirement.
with ajax you can show the upload progress also.
you will have to read the file as a inputstream.
using (FileStream fs = File.Create("D:\\_Workarea\\" + fileName))
{
Byte[] buffer = new Byte[32 * 1024];
int read = context.Request.GetBufferlessInputStream().Read(buffer, 0, buffer.Length);
while (read > 0)
{
fs.Write(buffer, 0, read);
read = context.Request.GetBufferlessInputStream().Read(buffer, 0, buffer.Length);
}
}
Sample Code
function sendFile(file) {
debugger;
$.ajax({
url: 'handler/FileUploader.ashx?FileName=' + file.name, //server script to process data
type: 'POST',
xhr: function () {
myXhr = $.ajaxSettings.xhr();
if (myXhr.upload) {
myXhr.upload.addEventListener('progress', progressHandlingFunction, false);
}
return myXhr;
},
success: function (result) {
//On success if you want to perform some tasks.
},
data: file,
cache: false,
contentType: false,
processData: false
});
function progressHandlingFunction(e) {
if (e.lengthComputable) {
var s = parseInt((e.loaded / e.total) * 100);
$("#progress" + currFile).text(s + "%");
$("#progbarWidth" + currFile).width(s + "%");
if (s == 100) {
triggerNextFileUpload();
}
}
}
}
As others has answer, the Request.Files is an HttpFileCollection that contains all the files that were posted, you only need to ask that object for the file like this:
Request.Files["myFile"]
But what happen when there are more than one input mark-up with the same attribute name:
Select file 1 <input type="file" name="myFiles" />
Select file 2 <input type="file" name="myFiles" />
On the server side the previous code Request.Files["myFile"] only return one HttpPostedFile object instead of the two files. I have seen on .net 4.5 an extension method called GetMultiple but for prevoious versions it doesn't exists, for that matter i propose the extension method as:
public static IEnumerable<HttpPostedFile> GetMultiple(this HttpFileCollection pCollection, string pName)
{
for (int i = 0; i < pCollection.Count; i++)
{
if (pCollection.GetKey(i).Equals(pName))
{
yield return pCollection.Get(i);
}
}
}
This extension method will return all the HttpPostedFile objects that have the name "myFiles" in the HttpFileCollection if any exists.
The Request.Files collection contains any files uploaded with your form, regardless of whether they came from a FileUpload control or a manually written <input type="file">
.
So you can just write a plain old file input tag in the middle of your WebForm, and then read the file uploaded from the Request.Files collection.
I've used this all the time.
//create a folder in server (~/Uploads)
//to upload
File.Copy(@"D:\CORREO.txt", Server.MapPath("~/Uploads/CORREO.txt"));
//to download
Response.ContentType = ContentType;
Response.AppendHeader("Content-Disposition", "attachment;filename=" + Path.GetFileName("~/Uploads/CORREO.txt"));
Response.WriteFile("~/Uploads/CORREO.txt");
Response.End();