I have an Azure App (.Net 4.5) and I have some static files stored on the filesystem that I want to read from, but I get a System.UnauthorizedAccessException like so
string template = string.Empty;
var file = HostingEnvironment.MapPath("~/App_Data/EmailTemplates/" + fileName);
if (!string.IsNullOrEmpty(file))
{
template = File.ReadAllText(file); <-- Unauthorized Access Exception Here
}
return template;
I know the best practice is Azure Storage, but how do I make this work this way?
As File.ReadAllText states about UnauthorizedAccessException, it could be caused by one of the following conditions:
path specified a file that is read-only.
-or-
This operation is not supported on the current platform.
-or-
path specified a directory.
-or-
The caller does not have the required permission.
You could leverage kudu console and use Attrib command to check the attributes for your files or directories. Also, you could try to use TYPE command to display the contents of your file or click the Edit button from the file list table as follows:
Also, I created a new web app and deployed my MVC application for displaying the files under the App_Data folder, it could work as expected, you could refer to it.
UPDATE:
//method for getting files
public List<DownLoadFileInformation> GetFiles()
{
List<DownLoadFileInformation> lstFiles = new List<DownLoadFileInformation>();
DirectoryInfo dirInfo = new DirectoryInfo(HostingEnvironment.MapPath("~/App_Data"));
int i = 0;
foreach (var item in dirInfo.GetFiles())
{
lstFiles.Add(new DownLoadFileInformation()
{
FileId = i + 1,
FileName = item.Name,
FilePath = dirInfo.FullName + #"\" + item.Name
});
i = i + 1;
}
return lstFiles;
}
//action for downloading a file
public ActionResult Download(string FileID)
{
int CurrentFileID = Convert.ToInt32(FileID);
var filesCol = obj.GetFiles();
string fullFilePath = (from fls in filesCol
where fls.FileId == CurrentFileID
select fls.FilePath).First();
string contentType = MimeMapping.GetMimeMapping(fullFilePath);
return File(fullFilePath, contentType, new FileInfo(fullFilePath).Name);
}
UPDATE2:
public ActionResult ViewOnline(string FileID)
{
int CurrentFileID = Convert.ToInt32(FileID);
var filesCol = obj.GetFiles();
string fullFilePath = (from fls in filesCol
where fls.FileId == CurrentFileID
select fls.FilePath).First();
string text = System.IO.File.ReadAllText(fullFilePath);
return Content(text);
}
Related
The image uploading is working perfectly in the development server in the windows environment but when I run the code in the Remote Linux server, the files get uploaded but in the root folder and for which the files can not be accessed by the website.
public async Task<IActionResult> Index(IList<IFormFile> files,Type type)
{
Startup.Progress = 0;
foreach (IFormFile source in files)
{
if (isFileImage(source))
{
string filename = ContentDispositionHeaderValue.Parse(source.ContentDisposition).FileName.ToString().Trim('"');
filename = this.EnsureCorrectFilename(filename);
string serverFilePath = this.GetPathAndFilename(filename);
try
{
await source.CopyToAsync(new FileStream(serverFilePath,FileMode.Create));
}
catch (Exception e)
{
}
finally
{
}
}
}
return Content("Success");
}
private string GetPathAndFilename(string filename)
{
string path = Path.Combine(Directory.GetCurrentDirectory(),#"wwwroot\images\materials", filename);
return path;
}
This is the code responsible for uploading an image. In the development windows environment, it works perfectly as the files get saved in the "wwwroot\images\materials" folder.
But when the code is run the Remote Linux serves the files get uploaded but are saved in the root folder with "wwwroot\images\materials*.jpg" name. Even when running the code in development mode in the Remote server this problem occurs.
Since you're using Path.Combine I would suggest passing each part of the path as a parameter. So instead of #"wwwroot\images\materials" as one parameter, you would pass them separately "wwwroot", "images", "materials".
Try this simple. In this you have to inject _hostingEnvironment so you can get ContentRootPath
string folderName = "Upload/Profile/" + user.Id;
string webRootPath = _hostingEnvironment.ContentRootPath;
string newPath = Path.Combine(webRootPath, folderName);
if (!Directory.Exists(newPath))
{
Directory.CreateDirectory(newPath);
}
string extention = file.ContentType.Split("/")[1];
string fileName = user.Id + ".jpg";
string fullPath = Path.Combine(newPath, fileName);
string envpath = folderName + "/" + fileName;
using (var stream = new FileStream(fullPath, FileMode.Create))
{
file.CopyTo(stream);
}
I am trying to upload an image file on an online link of a domain i have bought. Link is live. I can upload it in a local directory. but not working for online link. I cant find the correct way to give online path of my online directory to command
string filePath = HttpContext.Server.MapPath("???");
here is the code.
[HttpPost]
public ActionResult UpdateBanners(UpdateBanners banner)
{
zasa_company_slider sliderData = new zasa_company_slider();
if (banner != null && banner.file.ContentLength > 0)
{
string filePath = HttpContext.Server.MapPath("http://ak.eat-ax.com/akpanel/images/" + Path.GetFileName(banner.file.FileName));
banner.file.SaveAs(filePath);
}
return RedirectToAction("Index");
}
Retrieve your images like this
string filePath = Server.MapPath("~/Images/" + Path.GetFileName(index.FileName));
index.SaveAs(filePath);
string[] filePaths = Directory.GetFiles(Server.MapPath("~/Images/"));
foreach (string var in filePaths)
{
if (Path.GetFileName(var) == index.FileName)
{
sliderData.SLIDER_IMAGE = ("liveServerURL/" + Path.GetFileName(var));
}
}
After using the File.Copy function to copy a text file from one location to another i try the exact same functionality (that i've already gotten to work) on another text file fails to write. However, the weird part is that there is NO EXCEPTION thrown! I know the file exists by doing
if(File.Exist(myFile))
My File.Copy code:
File.Copy(sourceFilePathCombined, targetFilePathCombined, true);
This works well for one file in the same directory, but not for the other. There is NO exception. Why won't it write the file, but the other file gets copied without issue?
Code for those who need it:
var indexFileDirectory = ConfigurationManager.AppSettings["Accident.IndexFileDirectory"];
var xRefToDoList = ConfigurationManager.AppSettings["Accident.XRefToDoList"];
var xRefToDoResult = ConfigurationManager.AppSettings["Accident.XRefToDoResult"];
var toDoFilePath = Path.Combine(indexFileDirectory, xRefToDoResult);
var indexFilePath = Path.Combine(indexFileDirectory , xRefToDoList);
//Includes date-time stamp to suffix the file
var xRefToDoResultsDateTime = DateTime.Now.ToString("yyMMddhhmmss");
//If the directory does not exist then create it
if (!Directory.Exists(XRefPath))
{
Directory.CreateDirectory(XRefPath);
}
var indexToStart = xRefToDoList.IndexOf(".");
var test2 = xRefToDoList.Remove(indexToStart, 4);
indexToStart = xRefToDoResult.IndexOf(".");
var test3 = xRefToDoResult.Remove(indexToStart, 8);
var xRefToDoListCombinedPath = Path.Combine(XRefPath, (test2 + "_lst" + "." + xRefToDoResultsDateTime));
var xRefResultListCombinedPath = Path.Combine(XRefPath, (test3 + "_results" + "." + xRefToDoResultsDateTime));
string extension = Path.GetExtension(toDoFilePath);
try
{
File.Copy(indexFilePath, xRefToDoListCombinedPath, true);//THIS WORKS!
File.Copy(toDoFilePath, xRefResultListCombinedPath, true);//this does NOT
}
catch (Exception ex)
{
var test = ex;
}
Try using foreach to move all files
if (!System.IO.Directory.Exists(targetPath))
System.IO.Directory.CreateDirectory(targetPath);
string[] files = Directory.GetFiles(sourcePath);
foreach (var file in files)
{
string name = Path.GetFileName(file);
string target = Path.Combine(targetPath, name);
File.Copy(file, target, true);
}
Be sure to not confuse Date Modified with Date Created when looking for the file in a directory. It may look like it didn't get created if it has a Date Modified value.
I've got some strange behavior during execution in a ASP.NET application.
It doesn't matter if I set workingFolder (see code below) to System.IO.Path.GetTempPath or any other public folder (current case).
I receive a ZIP file, unpack that file (using SharpZipLib) and try to digest the files in that folder, but the System.IO GetFiles returns an empty list.
I've tried to use DirectoryInfo.GetFiles and Directory.GetFiles : both an empty list.
If I breakpoint on the Directory.Delete and look at the folder I can see the files, they're not locked and I can do anything with the files - even if I set the "run from cursor" point at the beginning of the foreach no luck - the GetFiles still return an empty list (although I can see the files in explorer).
private const string EXTENSION_LOG_FILE = ".txt";
private const string VALID_EXTENSION_MASK = "*." + EXTENSION_LOG_FILE;
var zipFolder = unpackZip(filePath, workingFolder);
foreach (var zipFileInfo in new DirectoryInfo(zipFolder).GetFiles(VALID_EXTENSION_MASK, SearchOption.TopDirectoryOnly))
{
// never get's here
value.AddRange(getLogItems(zipFileInfo.FullName));
File.Delete(zipFileInfo.FullName);
}
// this fails: folder is not empty
Directory.Delete(zipFolder);
and the unpackZip method:
private static string unpackZip(string zipFile, string workingFolder)
{
// doesn't matter what name I use, GUID or no GUID the GetFiles still returns an empty lists
var tempFolder = Path.Combine(workingFolder, Guid.NewGuid().ToString());
Directory.CreateDirectory(tempFolder);
using (var unzipStream = new ZipInputStream(File.OpenRead(zipFile)))
{
ZipEntry entry;
while ((entry = unzipStream.GetNextEntry()) != null)
{
var fileName = Path.GetFileName(entry.Name);
if (fileName == string.Empty) continue;
using (var streamWriter = File.Create(Path.Combine(tempFolder, Path.GetFileName(entry.Name))))
{
var size = 2048;
var data = new byte[2048];
while (size > 0)
{
size = unzipStream.Read(data, 0, data.Length);
streamWriter.Write(data, 0, size);
}
}
}
}
return tempFolder;
}
any suggestions?
Problem which I guessed in
private const string VALID_EXTENSION_MASK = "*." + EXTENSION_LOG_FILE;
retruns *..txt because EXTENSION_LOG_FILE = ".txt"
This question already has answers here:
Where can I write a temp file from ASP.NET?
(1 answer)
How to get temporary folder for current user
(3 answers)
Closed 8 years ago.
I have this code for my drag&drop-function for images. The problem with it is that it saves the file to my computer #"C:\Users\xxxx\Desktop\ temporarily. This is a problem because it means that a user cant use this function. So how can i adjust my code in order to make it work online?
I somehow need to find a way that stores the image temporarily.
public ActionResult SaveUploadedFile(string test)
{
foreach (string fileName in Request.Files)
{
HttpPostedFileBase file = Request.Files[fileName];
var filename = Path.GetFileName(file.FileName);
var sourceimage = System.Drawing.Image.FromStream(file.InputStream);
img = sourceimage;
var dog = new Dog();
byte[] tempImg = dog.imageToByteArray(sourceimage);
var fullPath = #"C:\Users\xxxx\Desktop\" + filename;
file.SaveAs(fullPath);
string link = dog.UploadImage(fullPath);
JObject o = JObject.Parse(link);
string name = (string) o.SelectToken("data.link");
System.IO.File.Delete(#"C:\Users\xxxx\Desktop\" + filename);
var page = RavenSession.Load<DogContentPage>(test);
page.Image = name;
RavenSession.SaveChanges();
}
The method that uploads img to imahehost(dunno if it is relevant):
public string UploadImage(string xOut)
{
using (var w = new WebClient())
{
var values = new NameValueCollection
{
{"image", Convert.ToBase64String(File.ReadAllBytes(xOut))}
};
w.Headers.Add("Authorization", "Client-ID " + ClientId);
var response = w.UploadValues("https://api.imgur.com/3/image", values);
var sr = new StreamReader(new MemoryStream(response));
string result = sr.ReadLine();
return result;
}
Have a look at Path.GetTempPath() as well as Path.GetTempFileName() which can help you.
A quick solution would be:
// var fullPath = #"C:\Users\xxxx\Desktop\" + filename; // Not good, since user folder
var fullPath = Path.GetTempFileName(); // Temp file, with unqiue name
The reason I would recommend Path.GetTempFileName() rather than Path.GetTempPath() + filename is that the filename doesn't matter when you only upload the file-bytes, and it guarantees a unique filename so it is impossible to have filename clashes.
var fullPath = Path.GetTempPath() + filename; // No good, could clash if the filenames were the same
Rather than using a hard-coded string, you should use the following to find the temporary folder in which to store temporary files:
string tempPath = System.IO.Path.GetTempPath();
2 solutions I think:
N°1: a task in the server that check, let's say 2 times a day, if any file have to be deleted
N°2: a procedure called by your application to verify the difference between Now and the expiration date of your file.
Hope this ideas can help.