Action Result File - Filename when downloading is wrong in some cases - c#

So this is the Code that returns the file. It is in a Method named GetMainReport.
var mBytes = MergePDF(formLanguage, mergedForms);
if (mBytes != null)
{
var cd = new System.Net.Mime.ContentDisposition
{
FileName = formLanguage.FileName,
Inline = formLanguage.FileExtension == FileExtension.PDF
};
Response.Headers.Add("content-disposition", cd.ToString());
AddDownloadedForm(formLanguage.Id);
return File(mBytes, type);
}
My Problem now is that if i go via this url:
http://localhost:8090/Library/105020.pdf
The filename when downloaded is 105020.pdf
if i use this one
http://localhost:8090/FormSearch/FormSearch/getMainReport?FormNumber=105020%20%20de
The filename is GetMainReport.pdf
any ideas why?

try this settings for ContentDisposition:
var cd = new System.Net.Mime.ContentDisposition
{
FileName = formLanguage.FileName,
DispositionType = DispositionTypeNames.Attachment,
Inline = formLanguage.FileExtension == FileExtension.PDF
};

Related

How to get files seperately to their extensions in MVC?

I wrote a function that when user clicks on button for pdf, user will only show the pdf documents. I'm having a difficulty about where to put returns in this function.
public IActionResult GetFiles(string dir) {
if ((dir == null) || (!Directory.Exists(dir))) { return BadRequest(); }
var filesList = new List<FileImage>();
var pdffilesList = new List<FileImage>();
var dirInfo = new DirectoryInfo(dir);
var files = dirInfo.GetFiles();
foreach (var file in files)
{
if (file.Extension.Contains(".pdf"))
{
pdffilesList.Add(new FileImage
{
Name = file.Name,
FullName = Regex.Match(file.FullName, "wwwroot(.*)").Groups[1].Value,
LastWriteTime = file.LastWriteTime.ToString("yyyy.MM.dd HH:mm"),
DirectoryName = file.DirectoryName,
Length = file.Length,
Extension = file.Extension
});
return Ok(pdffilesList);
}
else
{
filesList.Add(new FileImage
{
Name = file.Name,
FullName = Regex.Match(file.FullName, "wwwroot(.*)").Groups[1].Value,
LastWriteTime = file.LastWriteTime.ToString("yyyy.MM.dd HH:mm"),
DirectoryName = file.DirectoryName,
Length = file.Length,
Extension = file.Extension
});
}
}
return Ok(pdffilesList);
}
What should I change in here ?
If you just want the PDF files, then don't do anything to include the others:
foreach (var file in files)
{
if (file.Extension.Contains(".pdf"))
{
pdffilesList.Add(new FileImage
{
Name = file.Name,
FullName = Regex.Match(file.FullName, "wwwroot(.*)").Groups[1].Value,
LastWriteTime = file.LastWriteTime.ToString("yyyy.MM.dd HH:mm"),
DirectoryName = file.DirectoryName,
Length = file.Length,
Extension = file.Extension
});
// note: removed this `return`
//return Ok(pdffilesList);
}
// It's not a .pdf, so ignore it
}
return Ok(pdffilesList);
You might also consider whether you really want Contains here. Do you want to include files with extensions like ".pdfqpz" or "foopdf"? Contains will give you any file whose extension contains the string "pdf" anywhere in it. You also will miss files that have extensions ".PDF" or ".pDf", etc. You probably want something like:
if (file.Extension.Equals(".pdf", StringComparison.InvariantCultureIgnoreCase))
DirectoryInfo.GetFiles and EnumeratFiles can be used with a pattern. Instead of using separate branches you can use separate patterns:
var pattern=onlyPdfs? "*.pdf":"*";
var regex=new Regex("wwwroot(.*)");
var files=dirInfo.EnumerateFiles(pattern)
.Select(fi=>new FileImage
{
Name = file.Name,
FullName = regex.Match(file.FullName).Groups[1].Value,
LastWriteTime = file.LastWriteTime.ToString("yyyy.MM.dd HH:mm"),
DirectoryName = file.DirectoryName,
Length = file.Length,
Extension = file.Extension
});
return Ok(pdffilesList);
GetFiles waits until it finds all files and returns them in an array. EnumerateFiles on the other hand produces an IEnumerable<FileInfo> which returns each file as soon as it's found

How to display image angular from .net core API and database

I would like to display a picture whose path it stores in the database
this is how it transfers the image file to the database.
public string UploadImage(IFormFile file)
{
if (file == null) throw new Exception("Pusty plik");
if (file.Length == 0)
{
throw new Exception("Pusty plik");
}
if (!ACCEPTED_FILE_TYPES.Any(s => s == Path.GetExtension(file.FileName).ToLower())) throw new Exception("Zły typ pliku");
if (string.IsNullOrWhiteSpace(host.WebRootPath))
{
host.WebRootPath = Path.Combine(Directory.GetCurrentDirectory(), "wwwroot");
}
var uploadFilesPath = Path.Combine(host.WebRootPath, "images");
if (!Directory.Exists(uploadFilesPath))
Directory.CreateDirectory(uploadFilesPath);
var fileName = Guid.NewGuid().ToString() + Path.GetExtension(file.FileName);
var filePath = Path.Combine(uploadFilesPath, fileName);
using (var stream = new FileStream(filePath, FileMode.Create))
{
file.CopyToAsync(stream);
}
var path = Path.Combine(Directory.GetCurrentDirectory(), #"/wwwroot/images/", fileName);
return path;
}
here stores files:
https://zapodaj.net/a8829a7a3a90b.png.html
In your sample code I do not see path returning from database.
Also from security point of view it would be bad practice to return /wwwroot/images/ in response. You can create a folder on shared location and return shared location path.
Seems you question and same code isn't aligning.

How to save Images to different folders in database using ASP.NET Core?

I have an ASP.NET MVC project that is working fine to save images to different folders and sub folders. But when I want to do similarly in ASP.NET Core 2.2, it is not working as it is and I need help to solve this problem and I would appreciate your help very much.
Here is my ASP.NET MVC version that not working in ASP.NET Core 2.2:
public ActionResult AddCar(CarVM model, HttpPostedFileBase file)
{
using (ApplicationDbContext db = new ApplicationDbContext())
{
Car c = new Car();
c.Name = model.Name;
c.Mileage = model.MileAge;
db.Car.Add(c);
db.SaveChanges();
// Get Inserted Id;
int id = c.CarId;
}
// to insert Image of the car in different folders in ASP.NET MVC I do like this, but this not working in ASP.NET Core 2.2
// Create necessary directories
var originalDirectory = new DirectoryInfo(string.Format("{0}Images\\Uploads", Server.MapPath(#"\")));
// I add folder "CarsImage" because I have other Products image too
var pathString1 = Path.Combine(originalDirectory.ToString(), "CarsImage");
var pathString2 = Path.Combine(originalDirectory.ToString(), "CarsImage\\" + id.ToString());
var pathString3 = Path.Combine(originalDirectory.ToString(), "CarsImage\\" + id.ToString() + "\\Thumbs");
var pathString4 = Path.Combine(originalDirectory.ToString(), "CarsImage\\" + id.ToString() + "\\Gallery");
var pathString5 = Path.Combine(originalDirectory.ToString(), "CarsImage\\" + id.ToString() + "\\Gallery\\Thumbs");
// Check if directory exist, if not then create them
if (!Directory.Exists(pathString1))
Directory.CreateDirectory(pathString1);
if (!Directory.Exists(pathString2))
Directory.CreateDirectory(pathString2);
if (!Directory.Exists(pathString3))
Directory.CreateDirectory(pathString3);
if (!Directory.Exists(pathString4))
Directory.CreateDirectory(pathString4);
if (!Directory.Exists(pathString5))
Directory.CreateDirectory(pathString5);
// Check if file was uploaded
if (file != null && file.ContentLength > 0)
{
// Get file extension
string ext = file.ContentType.ToLower();
// Verify extension
if (ext != "image/jpg" &&
ext != "image/jpeg" &&
ext != "image/pjpeg" &&
ext != "image/gif" &&
ext != "image/x-png" &&
ext != "image/png")
{
using (ApplicationDbContext db = new ApplicationDbContext())
{
model.Categories = new SelectList(db.Category.ToList(), "CategoryId", "CategoryName");
model.Mileages = new SelectList(db.MileAge.ToList(), "MileAgeId", "Mile");
ModelState.AddModelError("", "The image was not uploaded - Wrong image extension");
return View(model);
}
}
// Init image name
string imageName = file.FileName;
// Save image name to Car table
using (ApplicationDbContext db = new ApplicationDbContext())
{
Car dto = db.Car.Find(id);
dto.ImageName = imageName;
db.SaveChanges();
}
// Set Original and image paths
var path = string.Format("{0}\\{1}", pathString2, imageName);
var path2 = string.Format("{0}\\{1}", pathString3, imageName);
// Save Original
file.SaveAs(path); // Not working in core
// Create and save thumb
WebImage img = new WebImage(file.InputStream); // WebImage not working in core
img.Resize(200, 200);
img.Save(path2);
}
}
So I have tried with IFormFile.... and
string uploadFolder = Path.Combine(hostingEnvirnment.WebRootPath, "images\\upload");
But I don't how to do. Please help!
In ASP.NET Core , you could use Directory.GetCurrentDirectory() to get the current working directory of the application and combine the folder path under the static file root directory .
var originalDirectory = Path.Combine(Directory.GetCurrentDirectory(), "wwwroot\\Images\\Uploads");
Then use Path.Combine() to set the original and image paths , and you could save the files of type IFormFile like below :
// Set Original and image paths
var filePath = Path.Combine(pathString2, imageName);
var filePath2 = Path.Combine(pathString3, imageName);
// Save Original
file.CopyTo(new FileStream(filePath, FileMode.Create));
For saving the thumbnail image , you could Installed System.Drawing.Common package and use the below code :
Stream stream = file.OpenReadStream();
Image newImage = GetReducedImage(200, 200, stream);
newImage.Save(filePath2);
public Image GetReducedImage(int width, int height, Stream resourceImage)
{
try
{
Image image = Image.FromStream(resourceImage);
Image thumb = image.GetThumbnailImage(width, height, () => false, IntPtr.Zero);
return thumb;
}
catch (Exception e)
{
return null;
}
}
The complete code is as follows:
public readonly ApplicationDbContext _context;
public HomeController( ApplicationDbContext context)
{
_context = context;
}
[HttpPost]
public ActionResult AddCar(Car model, IFormFile file)
{
Car c = new Car();
c.Name = model.Name;
c.Mileage = model.MileAge;
_context.Car.Add(c);
_context.SaveChanges();
// Get Inserted Id;
int id = c.CarId;
// Create necessary directories
var originalDirectory = Path.Combine(Directory.GetCurrentDirectory(), "wwwroot\\Images\\Uploads");
// different image folder
var pathString1 = Path.Combine(originalDirectory.ToString(), "CarsImage");
var pathString2 = Path.Combine(originalDirectory.ToString(), "CarsImage\\" + id.ToString());
var pathString3 = Path.Combine(originalDirectory.ToString(), "CarsImage\\" + id.ToString() + "\\Thumbs");
var pathString4 = Path.Combine(originalDirectory.ToString(), "CarsImage\\" + id.ToString() + "\\Gallery");
// Check if directory exist, if not then create them
if (!Directory.Exists(pathString1))
Directory.CreateDirectory(pathString1);
if (!Directory.Exists(pathString2))
Directory.CreateDirectory(pathString2);
if (!Directory.Exists(pathString3))
Directory.CreateDirectory(pathString3);
if (!Directory.Exists(pathString4))
Directory.CreateDirectory(pathString4);
// Check if file was uploaded
if (file != null && file.Length > 0)
{
// Get file extension
string ext = file.ContentType.ToLower();
// Verify extension
if (ext != "image/jpg" &&
ext != "image/jpeg" &&
ext != "image/pjpeg" &&
ext != "image/gif" &&
ext != "image/x-png" &&
ext != "image/png")
{
using (ApplicationDbContext db = new ApplicationDbContext())
{
model.Categories = new SelectList(db.Category.ToList(), "CategoryId", "CategoryName");
model.Mileages = new SelectList(db.MileAge.ToList(), "MileAgeId", "Mile");
ModelState.AddModelError("", "The image was not uploaded - Wrong image extension");
return View();
}
}
// Init image name
string imageName = file.FileName;
// Save image name to Car table
Car dto = _context.Car.Find(id);
dto.ImageName = imageName;
_context.SaveChanges();
// Set Original and image paths
var filePath = Path.Combine(pathString2, imageName);
var filePath2 = Path.Combine(pathString3, imageName);
// Save Original
file.CopyTo(new FileStream(filePath, FileMode.Create));
// Create and save thumb
Stream stream = file.OpenReadStream();
Image newImage = GetReducedImage(200, 200, stream);
newImage.Save(filePath2);
}
return View();
}
public Image GetReducedImage(int width, int height, Stream resourceImage)
{
try
{
Image image = Image.FromStream(resourceImage);
Image thumb = image.GetThumbnailImage(width, height, () => false, IntPtr.Zero);
return thumb;
}
catch (Exception e)
{
return null;
}
}
You need to use IHostingEnvironment to get the application path in ASP.NET Core. Check this SO answer for more details.

How to download file from FileCabinet in NetSuite using C#

I need to download text file from FileCabinet in NetSuite. I am able to search for all files in a folder and get back the file size, name and URL. But when I check the 'content' property, it is NULL. How can I download the file locally?
I tried using the URL to download the file using WebClient, but it returns 403 which makes sense.
var result = Client.Service.search(fileSearch);
var recordList = (Record[])result.recordList;
if (recordList != null && recordList.Length != 0)
{
foreach (var item in recordList)
{
var file = (com.netsuite.webservices.File)item;
int fileSize = (int)file.fileSize; // Returns the correct file size
byte[] fileContent = file.content; // NULL reference ??
Console.WriteLine(file.url + " ==== " + file.name );
// How to download the File from the url above??
// Can't do this, 403 error, below client dont use the same security context
//using (var client = new WebClient())
//{
// client.UseDefaultCredentials = false;
// client.DownloadFile(baseUrl + file.url, file.name);
//}
}
}
I expected 'content' to contain the file content.
When you execute a search, the search results do not include the contents of the file, but you DO have the file id. Below is an extension method on the NetSuite service to get a file by it's id:
public static NetSuite.File GetFileById(this NetSuiteService ns, int fileId)
{
var file = new NetSuite.File();
var response = ns.get(new RecordRef()
{
type = RecordType.file,
internalId = fileId.ToString(),
typeSpecified = true
});
if (response.status.isSuccess)
{
file = response.record as File;
}
return file;
}
var f = ns.GetFileById(3946);
var path = Path.Combine(Directory.GetCurrentDirectory(), f.name);
var contents = f.content;
System.IO.File.WriteAllBytes(path, contents);
Console.WriteLine($"Downloaded {f.name}");

Using powershell reflection to perform database updates

I'm editing my question to make it more readily understood.
Here is an example solution: https://github.com/mckenn55/PowershellTest
I created a brand new net47 MVC project. I added an area called "Database" and a controller within that area called "Update". Within that controller, I have the following:
public ActionResult Index()
{
return View(Execute());
}
public static List<string> Execute()
{
var returnable = new List<string>();
var assembly = Assembly.GetExecutingAssembly();
string codeBase = assembly.CodeBase;
UriBuilder uri = new UriBuilder(codeBase);
string path = Uri.UnescapeDataString(uri.Path);
var assemblyLocation = Path.GetDirectoryName(path);
string resourcePath = "";
string ModuleName = assembly.ManifestModule.Name;
ModuleName = ModuleName.Substring(0, ModuleName.LastIndexOf("."));
ModuleName = ModuleName.Replace(' ', '_').Replace(".", "");
string FolderPath = "Areas.Database.SQL";
FolderPath = FolderPath.Replace(' ', '_');
if (FolderPath != null && FolderPath.Length > 0 && FolderPath[FolderPath.Length - 1] == '.')
FolderPath = FolderPath.Substring(0, FolderPath.Length - 1);
StringBuilder filepath = new StringBuilder();
filepath.Append(ModuleName);
if (FolderPath != null && FolderPath.Length > 0)
{
filepath.Append('.' + FolderPath);
filepath.Append('.');
}
resourcePath = filepath.ToString();
string[] resourceNames = assembly.GetManifestResourceNames();
foreach (var resourceName in resourceNames)
{
if (Regex.Match(resourceName, "^" + resourcePath).Success)
{
returnable.Add(resourceName);
}
}
var orderedFileNames = new List<string>();
if (returnable != null && returnable.Any())
{
orderedFileNames = returnable.OrderBy(q => q).ToList();
}
else
{
returnable.Add("No files found");
}
return returnable;
}
Within the Database area, I have a directory called "SQL" and within that directory, I have a single file, TestFile.sql, included in the solution as an embedded resource. The results of the Execute() method, when viewed using the index action is "PSTest.Areas.Database.SQL.TestFile.sql". I would like to see the same thing in Powershell. I have tried the following:
> Add-Type -path "C:\Temp\PSTest\PSTest\bin\PSTest.dll"
> [PSTest.Areas.Database.UpdateController]::Execute()
No Files Found
Is my goal possible through powershell and if so, how?
I was not able to find a solution to this using powershell alone. I wrote a C# console app that is able to perform these actions without any issue.

Categories