3

I have looked around the internet for 3 hours now looking for a solution to my problem and I'm starting to wonder if anyone else has ever had this exact problem?

I am using IIS7 to host a website that does some local things around our office. Well, developing the site everything worked fine, but now that I am hosting the site I cannot (and neither can anyone else for that matter) click on the link to download the file that is needed. (lets just pretend they click on a link to download some random file from the webserver)

Well, it fails downloading the file from what I can guess as being a permissions error. I have looked for a solution but cannot seem to find one. I know very little about IIS7 so I do not understand very much about the Application Pool Identity stuff, although I did manage to grant full access for that identity to the file/folders. Anyways, here is the specific area it is messing up on..

This is a piece of the default.cshtml page that calls a Function from a .cs file: //well.. pretty close to the exact thing, just got rid of a bunch of unecessary junk

@{
string tmp = Functions.downloadFile(fileName)
}

<html>
tmp
</html>

This is the part of the .cs file that actually downloads the file to the desktop

public static string downloadFile(string fileName) //i know this example doesnt 
//use filename, but the original code does.
{
    if (Directory.Exists("C:\WebSite\thingsToDownload"))
    {
        string[] files = Directory.GetFiles("C:\WebSite\thingsToDownload");

        foreach (string s in files)
        {
            string[] tmp = s.Split('\\');
            try
            {
                File.Copy(s,
                          Environment.GetFolderPath(Environment.SpecialFolder.Desktop)
                          + "\\" + tmp[tmp.Length - 1]);
            }
            catch (Exception e)
            {
                return "ERROR COPYING: " + e.Message;
            }
        }
        return "GOOD";
    }
    return "DIRECTORY DOESNT EXIST";
}

After that is all said and done, i get "ERROR COPYING: Access to the path '\fileName' is denied.

My Guess is that the webserver does not have access to the person's desktop in order to put the files there. If anyone can shed some light and help me get this it would be greatly appreciated!

Brandon Stout
  • 359
  • 10
  • 22
  • You're trying to write the file to the server's desktop (or wherever `fileName` might point to otherwise). Use [Response.WriteFile](http://msdn.microsoft.com/en-us/library/dyfzssz9.aspx). – Grant Thomas Feb 13 '12 at 19:34
  • Is this code supposed to allow users to download anything? It seems that there's a file being copied between two folders on the server. The problem probably stems from the fact that the `Environment.GetFolderPath` returns an empty path for `LocalSystem` (or whatever user your pool runs under) but this doesn't change the fact that the whole approach seems wrong. – Wiktor Zychla Feb 13 '12 at 19:36

2 Answers2

2

If you want to download a file by clicking a link you should use response.

Here's a sample you can use for example when a user clicks a link or button or something:

  const string fName = @"C:\picture.bmp";
  FileInfo fi = new FileInfo(fName);
  long sz = fi.Length;

  Response.ClearContent();
  Response.ContentType = Path.GetExtension(fName);
  Response.AddHeader("Content-Disposition", string.Format("attachment; filename = {0}",System.IO.Path.GetFileName(fName)));
  Response.AddHeader("Content-Length", sz.ToString("F0"));
  Response.TransmitFile(fName);
  Response.End();
TheBoyan
  • 6,802
  • 3
  • 45
  • 61
  • The user is clicking a link - the server should _serve_ the file. It's not that the OP is writing an application to do these downloads autonomously. – Grant Thomas Feb 13 '12 at 19:38
  • nothing wrong with this answer. obviously it doesn't download to the desktop...because you can't do that. but it does give a clear enough example of how to download a "random" file and should give the OP a start on fixing his problem. – Al W Feb 13 '12 at 19:47
  • Ya, i'm attempting this now and I gave up on automatically trying to send it to the desktop. I didn't think it was possible but figured I would try. – Brandon Stout Feb 13 '12 at 20:02
  • This worked better than I expected to be honest! Except the fact that It would crash when I added in the Response.TransmitFile(fname) for some reason.. but whenever i commented that line out It automatically downloaded the file whenever i clicked on the link. Thank you very much for the help! – Brandon Stout Feb 13 '12 at 20:18
  • @Bojan - What if I have multiple files? My Function.downloadFiles() now returns an array of filenames. This worked when there was only one file to download, but whenever it hit multiple files it didnt like it. "Duplicate headers received from server" I have Response.TransmitFile(fname) and Response.End() commented out because it either doesnt run with TransmitFile uncommented, or it hangs forever if End() is uncommented. Any thoughts? – Brandon Stout Feb 13 '12 at 20:37
  • 1
    @BrandonStout - You might want to consider having them zipped like this post suggests: http://stackoverflow.com/questions/3984590/download-multiple-files-as-zip-in-net – TheBoyan Feb 13 '12 at 20:43
1

It worked when you developed it, because it was running on your computer and thus had access to your desktop. There is no such thing as download to desktop. You can serve files and let the user decide where to save the file; on the desktop or elsewhere. But you have to do this over http, not directly from the server.

Klaus Byskov Pedersen
  • 117,245
  • 29
  • 183
  • 222