I have a GridView which has following template field that holds the filename, when the user clicks the filename, I call window.open() to open the file. My question is I can only pass relative path to window.open(). I got an error if I use full path. Is there any way I can use full path to open a file? Thanks.
<asp:TemplateField HeaderText="FileName">
<ItemTemplate>
<asp:LinkButton ID="lnkFile" runat="server"
Text='<%# Eval("FileName")%>' OnClick="lnkFile_Click">
</asp:LinkButton>
</ItemTemplate>
</asp:TemplateField>
Added: The actual location of the file is defined in web.config.
I have wrote following lnkFile_Click(). The old part will open a new window for the file, but I cannot pass fullpath of the file. The new part will let you have a choice to open or save the file. My question is, will this cause security issue?
protected void lnkFile_Click(object sender, System.EventArgs e)
{
string fileName = ConfigurationSettings.AppSettings["SPRAttachmentLocation"] + "\\SPR" + sprID + "\\" + ((LinkButton)sender).Text;
if (!File.Exists(fileName))
{
Exception ex = new Exception("Could not find the file, please contact your administrator.");
Response.Write("<p align=\"center\"><br /><br /><br /><br />There has been an Error: <strong>" + ex.Message + "</strong></p>\n");
return;
}
New:
byte[] bts = System.IO.File.ReadAllBytes(fileName);
Response.Clear();
Response.ClearHeaders();
Response.AddHeader("Content-Type", "");
Response.AddHeader("Content-Length", bts.Length.ToString());
Response.AddHeader("Content-Disposition", "attachment; filename=" + fileName);
Response.BinaryWrite(bts);
Response.Flush();
Response.End();
Old:
string newWindowUrl = "/SPR_Upload/SPR" + sprID + "/" + ((LinkButton)sender).Text;
string javaScript =
"<script type='text/javascript'>\n" +
"<!--\n" +
"window.open('" + newWindowUrl + "');\n" +
"// -->\n" +
"</script>\n";
Page.ClientScript.RegisterStartupScript(GetType(), "", javaScript);
}
Your question gives the impression that you think that you can open a file from the user's local computer. If that's the case, this is not possible.
Window.open expects a URL because the file is located on the server side, not the client side.
With that said, if you are trying to open a file located on the server side and you know the full path to the file; what you need to do is generate the virtual path within your application where the file can be found. You do this by creating a Virtual Directory in your APP from the IIS Admin Manager (Control Panel-->Admin Tools -->IIS Mgmt) and mapping this directory to the actual physical directory.
EDIT:
Say for example your whole website is physically located on the server on c:\inetpub\wwwroot\your_app. Let's assume your app can be accessed via http://example.com and the files you want to serve are physically located on d:\files. Assume further that you created a virtual directory for your app (as I explained above) and that you called this virtual folder public_files. If one knows the file name it should be possible to access the file by simply going to http://example.com/public_files/filename.ext. Since you in your app already know the file name, all you need to pass as parameter to window.open is this url (http://example.com/public_files/filename.txt)
You could try using the AppDomainAppVirtualPath to get the virtual path to the file.
string vPath = HttpRuntime.AppDomainAppVirtualPath + "/my/relative/path"
if the file is not located within the virtual directory there are a number of security issues you need to consider and address. in general it's not a good idea to access a file outside of the virtual directory.
if you must, then you will need to raise security permissions and grant access to the file on the network.
Related
It is fairly common to allow users to download a file via having some path modifier in the URL
//MVC Action to download the correct file From our Content directory
public ActionResult GetFile(string name) {
string path = this.Server.MapPath("~/Content/" + name);
byte[] file = System.IO.File.ReadAllBytes(path);
return this.File(file, "html/text");
}
quoted from http://hugoware.net/blog/dude-for-real-encrypt-your-web-config
An application I'm working with has liberal path downloads ( directory based ) sprinkled throughout the application, hence it is super vulnerable to requests like "http://localhost:1100/Home/GetFile?name=../web.config" or ( ..%2fweb.config )
Is there an easy way to restrict access to the config file - do I need to provide a custom Server.MapPath with whitelisted directories - or is there a better way.
How do you secure your file downloads - are path based downloads inherently insecure?
A simple option, assuming that all files in the ~/Content directory are safe to download would be to verify that the path is actually under (or in) the ~/Content directory and not up from it, as ~/Content/../web.config would be. I might do something like this:
// MVC Action to download the correct file From our Content directory
public ActionResult GetFile(string name) {
// Safe path
var safePath = this.Server.MapPath("~/Content");
// Requested path
string path = this.Server.MapPath("~/Content/" + name);
// Make sure requested path is safe
if (!path.StartsWith(safePath))
// NOT SAFE! Do something here, like show an error message
// Read file and return it
byte[] file = System.IO.File.ReadAllBytes(path);
return this.File(file, "html/text");
}
I save file to server with below code but when i want to create folder says : "URI formats are not supported"
//Save File
string folderPath = MapPath(#"Attachment\");
FileUpload1.SaveAs(folderPath + name);
//Directory
Directory.CreateDirectory(folderPath+#"\111");
check exist before
string folderPath =Server.MapPath("Attachment");
if(!Directory.Exists(folderPath))
Directory.CreateDirectory(folderPath);
side note:
when you concat paths better to use Path.Combine
FileUpload1.SaveAs(Path.Combine(folderPath , name));
OR try with
Directory.CreateDirectory(new Uri(folderPath+#"\111").LocalPath);
since you get "URI formats are not supported" error message
I wanna to display all the files in a directory in ASP.NET. when i click on the list of files available in that it should get download to local or it should open to view?
How to achieve this ? i got all the files in directory but i don't know to make those files to download?
Thanks in advance.
In order to make the file downlodble you have to add for each file an href
eg
foreach(string fileName in Dir)
{
Response.Write("<a href='"+fileName+"'>file name...</a>");
}
ore you have to force download in such way
public static void ForceDownload(this HttpResponse Response, string virtualPath, string fileName)
{
Response.Clear();
Response.AddHeader("content-disposition", "attachment; filename=" + fileName);
Response.WriteFile(virtualPath);
Response.ContentType = "";
Response.End();
}
One way to do this is to enable directory browsing in IIS.
For whatever reason, directory browsing also displays the web.config file for the directory. The following link discuses how to not show it: http://forums.iis.net/t/1149484.aspx/1
I am working on website in which i want to copy the file from my application folder to other folder on same server (But this folder is out of my application folder i.e. my application on C driver and the destination folder is on D drive).Is this possible using any functionality of Asp.Net?
Thanks in advance.
YES it's possible, the only concern that you have to watch for is that the CopyTo path should be the full path, not the relative one (ex: c:\websites\myOtherFolder).
this way, you can successfully copy/move the file from your ASP.NET code.
below is a pseudo code to show you how to get it done (assuming that the file has been placed on the root folder of your ASP.NET Application).
using System.IO;
..
..
..
// Get the current app path:
var currentApplicationPath = HttpContext.Current.Request.PhysicalApplicationPath;
//Get the full path of the file
var fullFilePath = currentApplicationPath + fileNameWithExtension;
// Get the destination path
var copyToPath = "This has to be the full path to your destination directory.
Example d:\myfolder";
// Copy the file
File.Copy(fullFilePath , copyToPath );
use this function:
System.IO.File.Copy(FileToCopy, NewCopy)
It's very easy to move file from one folder to other folder. you can change the file name while moving...
string Tranfiles, ProcessedFiles;
//Tranfiles = Server.MapPath(#"~\godurian\sth100\transfiles\" + Filename);
Tranfiles = Server.MapPath(#"~\transfiles\" + Filename);
if (File.Exists(Server.MapPath(#"~\transfiles\" + Filename)))
{
File.Delete(Server.MapPath(#"~\transfiles\" + Filename));
}
//ProcessedFiles = Server.MapPath(#"~\godurian\sth100\ProcessedFiles");
ProcessedFiles = Server.MapPath(#"~\ProcessedFiles");
File.Move(Tranfiles, ProcessedFiles);
That's it now you can check your application folder to confirm the move process status
I'd like to redirect the user to a directory on a file server using its UNC path. I've tried using something like the following but I just get a 404 error.
Response.Redirect(#"file:\\fileserver\data\");
What's the correct syntax to make this work?
You don't quite have the file protocol identifier correct.
Try:
string location = String.Format("file:///{0}", #"\\fileserver\data\");
Response.Redirect(location, true);
I'm not sure about the Response.Redirect method, but you can always write the file for download by the user using Response.WriteFile.
This link might help: http://support.microsoft.com/kb/307603/EN-US/
Code Snippet from above link:
private void Page_Load(object sender, EventArgs e)
{
//Set the appropriate ContentType.
Response.ContentType = "Application/pdf";
//Write the file directly to the HTTP output stream.
Response.WriteFile(#"\\server\folder\file.pdf");
Response.End();
}
file:////server/directory
Or, create a virtual directory in your Website and map it to a path, like /data/