I'm trying to download an xls file from a url:
http://www.site.com/ff/excel/file.aspx?deven=0
I'm using this code but when the download is complete the file is not properly downloaded. How can I download this file correctly?
string remoteFilename="http://www.site.com/ff/excel/file.aspx?deven=0";
string localFilename = "D:\\1\\1.xls";
Stream remoteStream = null;
Stream localStream = null;
WebResponse response = null;
try
{
// Create a request for the specified remote file name
WebRequest request = WebRequest.Create(remoteFilename);
if (request != null)
{
// Send the request to the server and retrieve the
// WebResponse object
response = request.GetResponse();
response.ContentType = "application/vnd.ms-excel";
if (response != null)
{
// Once the WebResponse object has been retrieved,
// get the stream object associated with the response's data
remoteStream = response.GetResponseStream();
// Create the local file
localStream = File.Create(localFilename);
// Allocate a 1k buffer
byte[] buffer = new byte[1024];
int bytesRead;
// Simple do/while loop to read from stream until
// no bytes are returned
do
{
// Read data (up to 1k) from the stream
bytesRead = remoteStream.Read(buffer, 0, buffer.Length);
// Write the data to the local file
localStream.Write(buffer, 0, bytesRead);
// Increment total bytes processed
} while (bytesRead > 0);
}
}
}
catch (Exception e)
{
MessageBox.Show(e.Message);
}
finally
{
// Close the response and streams objects here
// to make sure they're closed even if an exception
// is thrown at some point
if (response != null) response.Close();
if (remoteStream != null) remoteStream.Close();
if (localStream != null) localStream.Close();
}
MessageBox.Show("file downl");
Use WebClient, it's much simpler:
using (WebClient webClient = new WebClient())
{
webClient.DownloadFile(remoteFileName, localFilename);
}
if(File.Exists(localFilename))
MessageBox.Show("File Downloaded");
Try flushing with localStream.Flush() AFTER your do {} while(), you might also want to wrap with a using statement.
For example:
// Create the local file
using (localStream = File.Create(localFilename)) {
// Allocate a 1k buffer
byte[] buffer = new byte[1024];
int bytesRead;
// Simple do/while loop to read from stream until
// no bytes are returned
do {
// Read data (up to 1k) from the stream
bytesRead = remoteStream.Read(buffer, 0, buffer.Length);
// Write the data to the local file
localStream.Write(buffer, 0, bytesRead);
// Increment total bytes processed
} while (bytesRead > 0);
localStream.Flush();
}
This is how I download Excel files using a FilePathResult.
public FilePathResult DownloadFile(int ID)
{
var log = _db.Logs.FirstOrDefault(x => x.LogID == ID);
//Download the spreadsheet
string fileName = string.Format("{0}.xlsx", ID);
string path = _directory + "\\" + fileName;
return File(path, "application/vnd.ms-excel", string.Format("{0}.xlsx", log.ReportTitle));
}
Related
I need to download an .PDF file from a website : https://XXXXX/XXXX/XXXXXXX.pdf when user click's on link button. Below code is working fine in local but when I try to click on link button for downloading the file after deploying into server, First time it is working fire but next consecutive downloads, It is displaying as The XXXX.PDF download was interrupted or file cannot be downloaded.
try
{
string fullFileName =string.Empty;
LinkButton btn = (LinkButton)(sender);
string filepath = btn.CommandArgument;
string fileName = btn.Text;
if (fileName != null && !string.IsNullOrEmpty(fileName))
{
fullFileName = filePath +fileName ;
int bytesToRead = 10000;
// Buffer to read bytes in chunk size specified above
byte[] buffer = new Byte[bytesToRead];
//string fileName = System.IO.Path.GetFileName(fullFileName);
//Create a WebRequest to get the file
System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Ssl3 | System.Net.SecurityProtocolType.Tls | (SecurityProtocolType)768/*TLS1.1*/ | (SecurityProtocolType)3072/*TLS1.2*/;
HttpWebRequest fileReq = (HttpWebRequest)HttpWebRequest.Create(fullFileName);
//Create a response for this request
HttpWebResponse fileResp = (HttpWebResponse)fileReq.GetResponse();
if (fileReq.ContentLength > 0)
fileResp.ContentLength = fileReq.ContentLength;
//Get the Stream returned from the response
stream = fileResp.GetResponseStream();
// prepare the response to the client. resp is the client Response
var resp = HttpContext.Current.Response;
//Indicate the type of data being sent
resp.ContentType = "application/PDF";
//Name the file
resp.AddHeader("Content-Disposition", "attachment; filename=\"" + fileName + "\"");
resp.AddHeader("Content-Length", fileResp.ContentLength.ToString());
int length;
do
{
// Verify that the client is connected.
if (resp.IsClientConnected)
{
// Read data into the buffer.
length = stream.Read(buffer, 0, bytesToRead);
// and write it out to the response's output stream
resp.OutputStream.Write(buffer, 0, length);
// Flush the data
resp.Flush();
//Clear the buffer
buffer = new Byte[bytesToRead];
}
else
{
// cancel the download if client has disconnected
length = -1;
}
} while (length > 0); //Repeat until no data is read
}
else
{
lblFile.Text = "File Name is missing";
lblFile.Visible = true;
}
}
catch (Exception ex)
{
}
finally
{
if (stream != null)
{
//Close the input stream
stream.Close();
}
}
Can someone please guide me why it is failing in server
So I'm trying to build some sort of a media player, the application prepares audio from an external source (HTTP server sitting on another device), when trying to seek the MediaPlayer returns "Stream has no duration and is therefore not seekable"
Note: I saw questions about the same error but they were about live streams, this is a static MP3 file.
Code from the other device (the server of the audio files)
private static void WriteFile(HttpListenerContext ctx, Android.Net.Uri uri, Activity activity)
{
var response = ctx.Response;
Debug.Print(ctx.Request.RemoteEndPoint.ToString());
using (var file = activity.ContentResolver.OpenInputStream(uri))
{
string fileName = "Audio.mp3";
ICursor cursor = activity.ContentResolver.Query(uri, null, null, null, null);
try
{
if (cursor != null && cursor.MoveToFirst())
fileName = cursor.GetString(cursor.GetColumnIndex(OpenableColumns.DisplayName));
}
finally
{
cursor.Close();
}
response.SendChunked = false;
response.ContentType = "audio/mpeg";
response.AddHeader("Content-disposition", "attachment; filename=" + fileName);
byte[] buffer = new byte[64 * 1024];
int read;
using (BinaryWriter bw = new BinaryWriter(response.OutputStream))
{
while ((read = file.Read(buffer, 0, buffer.Length)) > 0)
{
bw.Write(buffer, 0, read);
bw.Flush();
}
bw.Close();
response.ContentLength64 = bw.BaseStream.Length;
}
response.StatusCode = (int)HttpStatusCode.OK;
response.StatusDescription = "OK";
response.OutputStream.Close();
}
I'm not sure how this code is not throwing a "cannot access a closed stream" exception:
bw.Close();
response.ContentLength64 = bw.BaseStream.Length;
But... retrieve the length before closing the stream:
response.ContentLength64 = bw.BaseStream.Length;
bw.Close();
Hi I am having issues in this code:
// Function will return the number of bytes processed
// to the caller. Initialize to 0 here.
int bytesProcessed = 0;
// Assign values to these objects here so that they can
// be referenced in the finally block
Stream remoteStream = null;
Stream localStream = null;
WebResponse response = null;
// Use a try/catch/finally block as both the WebRequest and Stream
// classes throw exceptions upon error
try
{
// Create a request for the specified remote file name
WebRequest request = WebRequest.Create(remoteFilename);
request.Method = "GET";
string credentials = Convert.ToBase64String(Encoding.ASCII.GetBytes(uName + ":" + pwd));
request.Headers[HttpRequestHeader.Authorization] = "Basic " + credentials;
if (request != null)
{
// Send the request to the server and retrieve the
// WebResponse object
response = request.GetResponse();
if (response != null)
{
// Once the WebResponse object has been retrieved,
// get the stream object associated with the response's data
remoteStream = response.GetResponseStream();
// Create the local file
localStream = File.Create(localFilename);
// Allocate a 1k buffer
byte[] buffer = new byte[1024];
int bytesRead;
long totalBytesToProcess = response.ContentLength;
// Simple do/while loop to read from stream until
// no bytes are returned
do
{
// Read data (up to 1k) from the stream
bytesRead = remoteStream.Read(buffer, 0, buffer.Length);
// Write the data to the local file
localStream.Write(buffer, 0, bytesRead);
// Increment total bytes processed
bytesProcessed += bytesRead;
log(resourcesPath + "/BytesRecieved.txt", bytesProcessed.ToString()+"/"+ totalBytesToProcess.ToString(), false);
} while (bytesRead > 0);
}
}
}
catch (Exception ex)
{
Response.Write(ex);
// log(resourcesPath +"/Logs.txt",);
}
finally
{
// Close the response and streams objects here
// to make sure they're closed even if an exception
// is thrown at some point
if (response != null) response.Close();
if (remoteStream != null) remoteStream.Close();
if (localStream != null) localStream.Close();
}
// Return total bytes processed to caller.
return bytesProcessed;
This was able to download small files ranging up to 200 mb of file unfortunately it's failing when the file size soar high like up to more than 1gb. I have tried downloadfileAsyc of web client but it's failing too. is there any other way to handle large file for this matter ?
Allocate buffer size bigger than expected file size .
byte[] byteBuffer = new byte[65536];
so that , if the file is 1GiB in size, you allocate a 1 GiB buffer, and then you try to fill the whole buffer in one call.
This filling may return fewer bytes but you've still allocated the whole buffer. Note that the maximum length of a single array in .NET is a 32-bit number which means that even if you recompile your program for 64bit and actually have enough memory available.
For your reference visit this link :
How to change this code to download file bigger than 2GB?
I have to upload a large file to the server with the following code snippet:
static async Task LordNoBugAsync(string token, string filePath, string uri)
{
HttpWebRequest fileWebRequest = (HttpWebRequest)WebRequest.Create(uri);
fileWebRequest.Method = "PATCH";
fileWebRequest.AllowWriteStreamBuffering = false; //this line tells to upload by chunks
fileWebRequest.ContentType = "application/x-www-form-urlencoded";
fileWebRequest.Headers["Authorization"] = "PHOENIX-TOKEN " + token;
fileWebRequest.KeepAlive = false;
fileWebRequest.Timeout = System.Threading.Timeout.Infinite;
fileWebRequest.Proxy = null;
using (FileStream fileStream = File.OpenRead(filePath) )
{
fileWebRequest.ContentLength = fileStream.Length; //have to provide length in order to upload by chunks
int bufferSize = 512000;
byte[] buffer = new byte[bufferSize];
int lastBytesRead = 0;
int byteCount = 0;
Stream requestStream = fileWebRequest.GetRequestStream();
requestStream.WriteTimeout = System.Threading.Timeout.Infinite;
while ((lastBytesRead = fileStream.Read(buffer, 0, bufferSize)) != 0)
{
if (lastBytesRead > 0)
{
await requestStream.WriteAsync(buffer, 0, lastBytesRead);
//for some reasons didnt really write to stream, but in fact buffer has content, >60MB
byteCount += bufferSize;
}
}
requestStream.Flush();
try
{
requestStream.Close();
requestStream.Dispose();
}
catch
{
Console.Write("Error");
}
try
{
fileStream.Close();
fileStream.Dispose();
}
catch
{
Console.Write("Error");
}
}
...getting response parts...
}
In the code, I made a HttpWebRequest and push the content to server with buffering. The code works perfectly for any files under 60MB.
I tried a 70MB pdf. The buffer array has different content for each buffering. Yet, the request stream does not seem to be getting written. The bytecount also reached 70M, showing the file is properly read.
Edit (more info): I set the break point at requestStream.Close(). It clearly takes ~2 mins for the request stream to write in 60MB files but only takes 2ms for 70MB files.
My calling:
Task magic = LordNoBugAsync(token, nameofFile, path);
magic.Wait();
I am sure my calling is correct (it works for 0B to 60MB files).
Any advice or suggestion is much appreciated.
My problem is unable to download file from sever
My code work fine for any Google image-url (eg.:-http://blogs.independent.co.uk/wp-content/uploads/2012/12/google-zip.jpg)
but it is not work in case of my server image-url("eg.:-[http://110.15.445.87/xyz/abc/123.jpg]")
i dont know where is problem
my code is :-
//Create a stream for the file
Stream stream = null;
//This controls how many bytes to read at a time and send to the client
int bytesToRead = 10000;
// Buffer to read bytes in chunk size specified above
byte[] buffer = new Byte[bytesToRead];
// The number of bytes read
try
{
String Url = "http://112.196.32.51/ll1/UploadFiles/13062402231250.jpg";
//String Url = "http://blogs.independent.co.uk/wp-content/uploads/2012/12/google-zip.jpg";
//Create a WebRequest to get the file
HttpWebRequest fileReq = (HttpWebRequest)HttpWebRequest.Create(Url);
//Create a response for this request
HttpWebResponse fileResp = (HttpWebResponse)fileReq.GetResponse();
if (fileReq.ContentLength > 0)
fileResp.ContentLength = fileReq.ContentLength;
//Get the Stream returned from the response
stream = fileResp.GetResponseStream();
// prepare the response to the client. resp is the client Response
var resp = HttpContext.Current.Response;
//Indicate the type of data being sent
resp.ContentType = "application/octet-stream";
String fileName = "Rock.jpg";
//Name the file
resp.AddHeader("Content-Disposition", "attachment; filename=\"" + fileName + "\"");
resp.AddHeader("Content-Length", fileResp.ContentLength.ToString());
int length;
do
{
// Verify that the client is connected.
if (resp.IsClientConnected)
{
// Read data into the buffer.
length = stream.Read(buffer, 0, bytesToRead);
// and write it out to the response's output stream
resp.OutputStream.Write(buffer, 0, length);
// Flush the data
resp.Flush();
//Clear the buffer
buffer = new Byte[bytesToRead];
}
else
{
// cancel the download if client has disconnected
length = -1;
}
} while (length > 0); //Repeat until no data is read
}
finally
{
if (stream != null)
{
//Close the input stream
stream.Close();
}
}
}