ASP.NET MVC: C# Download file and save as dialog [duplicate] - asp.net

This question already has answers here:
Setting mime type for excel document
(6 answers)
Closed 9 years ago.
i've written this code which will generate an excel spreadsheet and save it to a specified location. I want to then display a "Save as" dialogue box by reading the file from the stored location and then asking then user where they want to store it.
Excel.Application excelApp = null;
Excel.Workbook wb = null;
Excel.Worksheet ws = null;
Excel.Range range = null;
excelApp = new Excel.Application();
wb = excelApp.Workbooks.Add();
ws = wb.Worksheets.get_Item(1) as Excel.Worksheet;
for(int i = 0; i< 10;++i) {
ws.Cells[i, 1] = i+
}
wb.SaveAs(#"C:\test.xls", Excel.XlFileFormat.xlWorkbookNormal);
wb.Close(true);
excelApp.Quit();
How to download in the following format?
string str = "Hello, world";
byte[] bytes = System.Text.Encoding.UTF8.GetBytes(str);
return File(bytes, "text/plain");

Given that is an Excel doc saved at c:\temp\excelDoc.xls and given that you have a WebForm that has a link like this
<asp:LinkButton runat="server" ID="GetExcel" OnClick="GetExcel_Click">Download</asp:LinkButton>
In your code-behind you can read the file from disk and send to the user by something like this
protected void GetExcel_Click(object sender, EventArgs e)
{
var fileName = "excelDoc.xls";
using (var cs = new FileStream(#"c:\temp\" + fileName, FileMode.Open))
{
Response.Clear();
Response.AddHeader("content-disposition", "attachment; filename=" + fileName);
Response.ContentType = "application/vnd.ms-excel";
byte[] buffer = new byte[32768];
int read;
while ((read = cs.Read(buffer, 0, buffer.Length)) > 0)
{
Response.OutputStream.Write(buffer, 0, read);
}
Response.End();
Response.Flush();
}
}

Related

Converting Byte[] to stream file asp.net

i need to converting Byte() to stream then flush
its in asp.net application
here is my code :
Dim fileBytes As Byte() = Nothing
....
apiProp.BodyRequest = New JavaScriptSerializer().Serialize(entFile)
apiProp.EndPoint = "example.com/DownloadFile"
apiProp = api.MessageInvoke(apiProp)
entResponse = JsonConvert.DeserializeObject(Of FileResponse)(apiProp.BodyResponse)
fileBytes = Convert.FromBase64String(entFile.fileContent)
i've tried :
Response.BinaryWrite(fileBytes)
Response.Flush()
and i've tried any filestream, memorystream etc. the file ask to download, but if i download the file, the file get corrupted
i need the file converted to stream because i have to add the watermark on the image file. im using groupdocs.watermark for adding the watermark.
using (Stream InputStream = fl.PostedFile.InputStream)
{
Object o = new object();
lock (o)
{
byte[] buffer = new byte[InputStream.Length];
InputStream.Read(buffer, 0, (int)InputStream.Length);
lock (o)
{
File.WriteAllBytes(rpath, buffer);
buffer = null;
}
InputStream.Close();
}
}

iTextSharp 7 - Save Dialog

Can anyone tell me how can I create a pdf file using iTextSharp 7 and popup a save dialog instead of saving it to a specific disk location?
My test code is the following:
protected void btnPrint_OnClick(object sender, EventArgs e)
{
Document doc = new Document(PageSize.A4, 25f, 20f, 20f, 10f);
var output = new FileStream(Server.MapPath("MyFirstPDF.pdf"), FileMode.Create);
var writer = PdfWriter.GetInstance(doc, output);
doc.Open();
doc.Add(new Paragraph("test!"));
doc.Close();
}
The workaround I found is the following:
After creating the document:
string path = "C:\\...";
string fileName = "PdfFile.pdf";
FileInfo fileInfo = new FileInfo(path);
Byte[] FileBuffer = File.ReadAllBytes(fileInfo.FullName);
if (FileBuffer != null)
{
Response.ContentType = "application/pdf";
Response.AddHeader("Content-Disposition", "attachment; filename=" + fileName);
Response.AddHeader("content-length", FileBuffer.Length.ToString());
Response.BinaryWrite(FileBuffer);
Response.Flush();
//DELETE FILE AFTER DOWNLOAD
fileInfo.Delete();
Response.End();
}

Open Generated pdf file through code directly without saving it onto the disk

I use Sharepoint 2010 and I am developing a web part where on a button click event, a pdf file needs to be generated and opened directly. Should not be saving onto the disk.
I tried the below code
protected void Button1_OnClick(object sender, EventArgs e)
{
Document myDoc = new Document(PageSize.A4.Rotate());
try
{
PdfWriter.GetInstance(myDoc, new FileStream(#"C:\Directory\Test.pdf", FileMode.Create));
myDoc.Open();
myDoc.Add(new Paragraph("Hello World"));
}
catch (DocumentException ex)
{
Console.Error.WriteLine(ex.Message);
}
myDoc.Close();
}
I also tried the below code which also generates the file on the Server which I dont want.
Document document = new Document(PageSize.A4);
PdfWriter.GetInstance(document, new FileStream(HttpContext.Current.Server.MapPath("~/Test.pdf"), FileMode.Create));
document.Open();
var WelcomePara = new Paragraph("Hello World");
document.Add(WelcomePara);
document.Close();
This one creates the pdf file on the desktop, I need it to be opened in the pdf format.Can someone help me please.
Almost every time that something accepts a FileStream is actually really accepts a generic System.IO.Stream object which FileStream is a subclass of. This means that you can instead use its cousin System.IO.MemoryStream which is what you are looking for:
byte[] bytes;
using (System.IO.MemoryStream ms = new System.IO.MemoryStream()) {
using (iTextSharp.text.Document doc = new iTextSharp.text.Document(iTextSharp.text.PageSize.A4.Rotate())) {
using (iTextSharp.text.pdf.PdfWriter w = iTextSharp.text.pdf.PdfWriter.GetInstance(doc, ms)) {
doc.Open();
doc.NewPage();
doc.Add(new iTextSharp.text.Paragraph("Hello world"));
doc.Close();
bytes = ms.ToArray();
}
}
}
//Do whatever you want with the byte array here
You don't have to create the byte array if you don't want, I was just showing how to create a PDF and give you something ".net-like" for you to work with.
I was able to get it work finally.
using (var ms = new MemoryStream())
{
using (var document = new Document(PageSize.A4,50,50,15,15))
{
PdfWriter.GetInstance(document, ms);
document.Open();
document.Add(new Paragraph("HelloWorld"));
document.Close();
}
Response.Clear();
//Response.ContentType = "application/pdf";
Response.ContentType = "application/octet-stream";
Response.AddHeader("content-disposition", "attachment;filename= Test.pdf");
Response.Buffer = true;
Response.Clear();
var bytes = ms.ToArray();
Response.OutputStream.Write(bytes, 0, bytes.Length);
Response.OutputStream.Flush();
}
This Works for me.
using (var ms = new MemoryStream())
{
using (var document = new Document(PageSize.A4,50,50,15,15))
{
// step 2
PdfWriter writer = PdfWriter.GetInstance(document, ms);
// step 3
document.Open();
// XML Worker
XMLWorker worker = new XMLWorker(css, true);
XMLParser p = new XMLParser(worker);
p.Parse(new StringReader(--Your HTML--));
// step 5
document.Close();
}
Byte[] FileBuffer = ms.ToArray();
if (FileBuffer != null)
{
Response.ContentType = "application/pdf";
Response.AddHeader("content-length", FileBuffer.Length.ToString());
Response.BinaryWrite(FileBuffer);
}
}

save multiple image to local from folder in asp.net

ive got a file download issue can you help me for that...
here is the code:
DirectoryInfo directoryInfo = new DirectoryInfo(Server.MapPath(#"/Bailiffs/BailiffFiles/"));
string cukurNumber = string.Empty;
if (txtCukurNumber.Text != string.Empty) {
cukurNumber = txtCukurNumber.Text;
}
FileInfo[] fileInfoEnum = directoryInfo.GetFiles(cukurNumber + "*");
Response.Clear();
Response.AddHeader("Content-Disposition", "attachment;filename=" + txtCukurNumber.Text + ".zip");
Response.ContentType = "application/zip";
using (ZipOutputStream zipStream = new ZipOutputStream(Response.OutputStream)) {
zipStream.SetLevel(9);
byte[] zipBuffer = new byte[4096];
foreach (FileInfo fileInfo in fileInfoEnum) {
string fileFullName = fileInfo.FullName;
ZipEntry zipEntry = new ZipEntry(Path.GetFileName(fileFullName));
zipEntry.DateTime = DateTime.Now;
zipStream.PutNextEntry(zipEntry);
using (FileStream fileStream = File.OpenRead(fileFullName)) {
int sourceBytes = 0;
do {
sourceBytes = fileStream.Read(zipBuffer, 0, zipBuffer.Length);
zipStream.Write(zipBuffer, 0, sourceBytes);
} while (sourceBytes > 0);
}
}
zipStream.Finish();
zipStream.Close();
Response.Flush();
Response.End();
}
this code must be get all image files by filter and save to disk but save file dialog of browser is opening just one time and one bizarre file is saving... where am i doing wrong...
thanks..
Edit : Bizzarre file issue is solved now the main issue is single file saving instead of multiple..
thanks again...
Although you are looping over each file in the directory, once you do your Response.End() on the first iteration of the loop, the response to the user is done. They would only get the first file that is found by the enumerator.
The browser doesn't have a concept of receiving multiple files in the way you are attempting.
You may consider collecting the various image files and putting them together in a ZIP file, and then returning a single ZIP back to the user.
Here is example code that will build a ZIP (using SharZipLib) of the images and reply with a single file called "images.zip"
Include these using statements for SharpZipLib:
using ICSharpCode.SharpZipLib.Core;
using ICSharpCode.SharpZipLib.Zip;
using ICSharpCode.SharpZipLib.Checksums;
Then in the method where you want to stream back the ZIP file:
DirectoryInfo directoryInfo = new DirectoryInfo(Server.MapPath(#"/Bailiffs/BailiffFiles/"));
string cukurNumber = string.Empty;
if (txtCukurNumber.Text != string.Empty) {
cukurNumber = txtCukurNumber.Text;
}
IEnumerable<FileInfo> fileInfoEnum = directoryInfo.EnumerateFiles( cukurNumber + "*" );
Response.Clear();
Response.AddHeader( "Content-Disposition", "attachment;filename=images.zip" );
Response.ContentType = "application/zip";
using( ZipOutputStream zipstream = new ZipOutputStream( Response.OutputStream ) ) {
zipstream.SetLevel( 9 ); // 0-9, 9 being the highest compression
byte[] buffer = new byte[4096];
foreach( FileInfo fileInfo in fileInfoEnum ) {
string file = fileInfo.FullName;
ZipEntry entry = new
ZipEntry( Path.GetFileName( file ) );
entry.DateTime = DateTime.Now;
zipstream.PutNextEntry( entry );
using( FileStream fs = File.OpenRead( file ) ) {
int sourceBytes;
do {
sourceBytes = fs.Read( buffer, 0, buffer.Length );
zipstream.Write( buffer, 0, sourceBytes );
} while( sourceBytes > 0 );
}
}
zipstream.Finish();
zipstream.Close();
}
Response.Flush();
Response.End();

Streaming a zip file over http in .net with SharpZipLib

I'm making a simple download service so a user can download all his images from out site.
To do that i just zip everything to the http stream.
However it seems everything is stored in memory, and the data isn't sent til zip file is complete and the output closed.
I want the service to start sending at once, and not use too much memory.
public void ProcessRequest(HttpContext context)
{
List<string> fileNames = GetFileNames();
context.Response.ContentType = "application/x-zip-compressed";
context.Response.AppendHeader("content-disposition", "attachment; filename=files.zip");
context.Response.ContentEncoding = Encoding.Default;
context.Response.Charset = "";
byte[] buffer = new byte[1024 * 8];
using (ICSharpCode.SharpZipLib.Zip.ZipOutputStream zipOutput = new ICSharpCode.SharpZipLib.Zip.ZipOutputStream(context.Response.OutputStream))
{
foreach (string fileName in fileNames)
{
ICSharpCode.SharpZipLib.Zip.ZipEntry zipEntry = new ICSharpCode.SharpZipLib.Zip.ZipEntry(fileName);
zipOutput.PutNextEntry(zipEntry);
using (var fread = System.IO.File.OpenRead(fileName))
{
ICSharpCode.SharpZipLib.Core.StreamUtils.Copy(fread, zipOutput, buffer);
}
}
zipOutput.Finish();
}
context.Response.Flush();
context.Response.End();
}
I can see the the worker process memory growing while it makes the file, and then releases the memory when its done sending. How do i do this without using too much memory?
Disable response buffering with context.Response.BufferOutput = false; and remove the Flush call from the end of your code.
use Response.BufferOutput = false; at start of ProcessRequest and flush response after each file.
FYI. This is working code to recursively add an entire tree of files, with streaming to browser:
string path = #"c:\files";
Response.Clear();
Response.ContentType = "application/zip";
Response.AddHeader("Content-Disposition", string.Format("attachment; filename=\"{0}\"", "hive.zip"));
Response.BufferOutput = false;
byte[] buffer = new byte[1024 * 1024];
using (ZipOutputStream zo = new ZipOutputStream(Response.OutputStream, 1024 * 1024)) {
zo.SetLevel(0);
DirectoryInfo di = new DirectoryInfo(path);
foreach (string file in Directory.GetFiles(di.FullName, "*.*", SearchOption.AllDirectories)) {
string folder = Path.GetDirectoryName(file);
if (folder.Length > di.FullName.Length) {
folder = folder.Substring(di.FullName.Length).Trim('\\') + #"\";
} else {
folder = string.Empty;
}
zo.PutNextEntry(new ZipEntry(folder + Path.GetFileName(file)));
using (FileStream fs = File.OpenRead(file)) {
ICSharpCode.SharpZipLib.Core.StreamUtils.Copy(fs, zo, buffer);
}
zo.Flush();
Response.Flush();
}
zo.Finish();
}
Response.Flush();

Resources