Click here to Skip to main content
15,880,469 members
Articles / Programming Languages / Javascript
Article

File Download Using JavaScript

Rate me:
Please Sign up or sign in to vote.
4.39/5 (12 votes)
29 Jan 2010CPL2 min read 252.3K   6.3K   47   12
An article on how to download a file using JavaScript
FileDownloadUsingJavascript_Src

Introduction

I know there are many developers looking for this kind of solution like I was looking. I had the same requirement to download the file from the server using JavaScript and with out postbacking the full page. The beauty of this is, it will work in IE/Firefox/Chrome browsers. I have not used ScriptManager/UpdatePanel anything rather I used Handler and normal JavaScript code. Handler is used to write the response back to the page. I have noted down the steps you may use in your programming. I can not use ActiveXObject in Firefox to create excel object in JavaScript because ActiveXObject will not work in Firefox.

How Did I Do This?

  1. Add span tag on the page which will work as a link
  2. Create FileHandler.ashx to write the response back to the page.
    C#
    public void ProcessRequest(HttpContext context)
        {
            fileName = HttpUtility.UrlDecode(context.Request.Params["fileName"]);
    
            string FullFilePath = context.Server.MapPath("~/Common/Files/" + fileName);
            FileInfo file = new FileInfo(FullFilePath);
            if (file.Exists)
            {
                context.Response.ContentType = 
    		MIMETypeUtility.MIMETypeDescription(MIMEType.Excel);
                context.Response.AddHeader
    	    ("Content-Disposition", "attachment; filename=\"" + file.Name + "\"");
                context.Response.AddHeader("Content-Length", file.Length.ToString());
                context.Response.WriteFile(file.FullName);
                context.Response.End();
            }
        }    

    You can use any MIME Type according to your requirement. I have showed some of the MIME types you can use in your application. For more MIME types, list http://msdn.microsoft.com/en-us/library/ms775147%28VS.85%29.aspx

    C#
    public enum MIMEType
    {
        [DescriptionAttribute("text/HTML")]TextHTML,
        [DescriptionAttribute("image/GIF")]Gif,
        [DescriptionAttribute("image/JPEG")]JPEG,
        [DescriptionAttribute("text/plain")]TextPlain,
        [DescriptionAttribute("Application/msword")]Word,
        [DescriptionAttribute("Application/vnd.ms-excel")]Excel,
        [DescriptionAttribute("Application/vnd.xls")]FirefoxExcel
    }
    public class MIMETypeUtility
    {
        public static string MIMETypeDescription(Enum mimeType)
        {
            FieldInfo fi = mimeType.GetType().GetField(mimeType.ToString());
            DescriptionAttribute[] attributes = 
               	(DescriptionAttribute[])fi.GetCustomAttributes
                	(typeof(DescriptionAttribute), false);
            if (attributes.Length > 0)
            {
                return attributes[0].Description;
            }
            else
            {
                return mimeType.ToString();
            }
        }
    }    
  3. Create FileHandler.js file to do the main work. It will create an iframe dynamically and which has width, height and border as 0. Then create form tag with one input control to pass filename (e.g. ExcelFile.xls) when you submit an iframe.
    C#
    var createFrame = function() 
    {
        var frame = document.createElement("iframe");
        frame.name = "fileFrame";
        frame.id = "fileFrame";
    
        document.body.appendChild(frame);
        generateIFrameContent();
        frame.style.width = "0px";
        frame.style.height = "0px";
        frame.style.border = "0px";
    }
  4. GetExcelFile function will pass Excel file name as parameter and will submit an iframe window and handler will run the code and writes the file response back to the page and the user will get open/save/cancel dialog window.
    C#
    var getExcelFile = function()
    {
        var frmWindow = getIFrameWindow();
        var fileName = frmWindow.document.getElementById("fileName");
        fileName.value = encodeURI("ExcelFile.xls");
        var frm = frmWindow.document.getElementById("frmFile");
        frm.submit();
    }    
  5. Create LoadScript.aspx page to add scripts to the page response. Here you can add any number of scripts and I prefer this way where I can hide the JavaScript and the location of the script file in page source at runtime.
    C#
    private void loadScript()
        {
            List<string> scripts = new List<string>();
            scripts.Add(Server.MapPath("~/Common/JS/FileHandler.js"));
    
            try
            {
                bool isStyles = this.GetType().BaseType.Name == "Styles";
                this.Response.Clear();
                this.Response.ContentType = isStyles ? "text/css" : "text/javascript";
                byte[] data = null;
    
                try
                {
                    StringBuilder sb = new StringBuilder();
                    foreach (string str in scripts)
                        sb.Append(File.ReadAllText(str));
                    data = new ASCIIEncoding().GetBytes(sb.ToString());
                }
                catch (Exception ex)
                {
                    throw ex;
                }
    
                this.Response.AddHeader("Content-Length", data.LongLength.ToString());
                this.Response.BinaryWrite(data);
                this.Response.End();
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }    
  6. Add the following code to the FileHandler.aspx page to load scripts and startupscript with initialization of JavaScript function.
    C#
    protected void Page_Load(object sender, EventArgs e)
    {
        Type type = this.GetType();
        if (!this.ClientScript.IsClientScriptIncludeRegistered(type, "scrScripts"))
             this.ClientScript.RegisterClientScriptInclude
    		(type, "scrScripts", "Common/Loaders/LoadScripts.aspx");
        if (!this.ClientScript.IsStartupScriptRegistered(type, "scrHandlerStartUp"))
             this.ClientScript.RegisterStartupScript
    		(type, "scrHandlerStartUp", GetStartUpScript(), true);
    }
    
    private string GetStartUpScript()
    {
        return "try{{var handler = new FileHandler();handler.init();}}catch(e)
    	{{document.getElementById('divNotLoaded').style.display = '';}}";
    }    

Conclusion

You can use AJAX (Scriptmanager + Updatepanel) to download the file from server, but you have to post back the page. This technique is light weight on the page. I had the requirement in my project to get the data from database and create an Excel file and insert the data and download the file to user machine. And my total website is using AJAX (JS+WebServices and no updatepanel), in this case I cannot use any server controls because that will post back my full page and I do not want that to happen. So after much R&D and many ways, this is one technique I have come up to use and it's working successfully in the production. I am available at phani.nadigadda@gmail.com for any questions you might have.

History

  • 29th January, 2010: Initial version

License

This article, along with any associated source code and files, is licensed under The Common Public License Version 1.0 (CPL)


Written By
Software Developer
United States United States
I started development with Visual Basic 6.0 and then upgraded to Visual Studio .Net and working on .net for 7+ years now.

Comments and Discussions

 
QuestionVB conversion Pin
Michael Grumbach10-Jul-11 10:42
Michael Grumbach10-Jul-11 10:42 
QuestionI have asked you a question by mail Pin
Dach2en129-May-11 20:44
Dach2en129-May-11 20:44 
AnswerRe: I have asked you a question by mail Pin
Phani Nadigadda1-Jun-11 9:10
Phani Nadigadda1-Jun-11 9:10 
GeneralMy vote of 5 Pin
subtwo26-Feb-11 1:33
subtwo26-Feb-11 1:33 
GeneralNeed Help Pin
R140916-Feb-11 19:27
R140916-Feb-11 19:27 
Generali creates error in IE6 Pin
jk.shan16-Jan-11 20:41
jk.shan16-Jan-11 20:41 
i implemented the this solution above and it raises a javascript error saying null value when i click the link second time.
GeneralMy vote of 1 Pin
Firas Nizam17-Sep-10 19:43
Firas Nizam17-Sep-10 19:43 
GeneralActually it a server side file download and not javascript Pin
Firas Nizam17-Sep-10 19:42
Firas Nizam17-Sep-10 19:42 
GeneralRe: Actually it a server side file download and not javascript Pin
ashishjain884-Aug-11 22:12
ashishjain884-Aug-11 22:12 
GeneralRe: Actually it a server side file download and not javascript Pin
Phani Nadigadda5-Aug-11 3:53
Phani Nadigadda5-Aug-11 3:53 
GeneralRe: Actually it a server side file download and not javascript Pin
arti8818-Feb-13 23:15
arti8818-Feb-13 23:15 
GeneralScreenshot Pin
AspDotNetDev29-Jan-10 19:14
protectorAspDotNetDev29-Jan-10 19:14 

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

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.