我們有很多文件,在我們的SQL Server數據庫中保存爲二進制文件。 我製作了一個.ashx文件,將這些文件傳遞給用戶。 不幸的是,當文件變得相當大,它會失敗,並出現以下錯誤:正在下載大文件,保存在數據庫中
Overflow or underflow in the arithmetic operation
我認爲它運行的內存,因爲我的二進制加載到一個byte []。
所以,我的問題是,當它是從數據庫表中讀取數據塊(也許?)時,如何使這個功能成爲可能?它也好像Response.TransmitFile()是一個很好的選擇,但是,這又如何與數據庫一起工作?
DB.GetReposFile()在下面的代碼中從數據庫獲取文件。有很多字段,用於條目: Filename,ContentType,datestamps和FileContent as varbinary。
這是我的職責,爲客戶提供文件:
context.Response.Clear();
try
{
if (!String.IsNullOrEmpty(context.Request.QueryString["id"]))
{
int id = Int32.Parse(context.Request.QueryString["id"]);
DataTable dtbl = DB.GetReposFile(id);
string FileName = dtbl.Rows[0]["FileName"].ToString();
string Extension = FileName.Substring(FileName.LastIndexOf('.')).ToLower();
context.Response.ContentType = ReturnExtension(Extension);
context.Response.AddHeader("Content-Disposition", "attachment; filename=" + FileName);
byte[] buffer = (byte[])dtbl.Rows[0]["FileContent"];
context.Response.OutputStream.Write(buffer, 0, buffer.Length);
}
else
{
context.Response.ContentType = "text/html";
context.Response.Write("<p>Need a valid id</p>");
}
}
catch (Exception ex)
{
context.Response.ContentType = "text/html";
context.Response.Write("<p>" + ex.ToString() + "</p>");
}
更新: 我結束了該功能,是下面列出的一個。如Tim所說,DB.GetReposFileSize()只是獲取內容Datalength。 我調用這個函數,在原有的代碼,而不是兩行:
byte[] buffer = (byte[])dtbl.Rows[0]["FileContent"];
context.Response.OutputStream.Write(buffer, 0, buffer.Length);
新的下載功能:
private void GetFileInChunks(HttpContext context, int ID)
{
//string path = @"c:\somefile.txt";
//FileInfo file = new FileInfo(path);
int len = DB.GetReposFileSize(ID);
context.Response.AppendHeader("content-length", len.ToString());
context.Response.Buffer = false;
//Stream outStream = (Stream)context.Response.OutputStream;
SqlConnection conn = null;
string strSQL = "select FileContent from LM_FileUploads where [email protected]";
try
{
DB.OpenDB(ref conn, DB.DatabaseConnection.PDM);
SqlCommand cmd = new SqlCommand(strSQL, conn);
cmd.Parameters.AddWithValue("@ID", ID);
SqlDataReader reader = cmd.ExecuteReader(CommandBehavior.SequentialAccess);
reader.Read();
byte[] buffer = new byte[1024];
int bytes;
long offset = 0;
while ((bytes = (int)reader.GetBytes(0, offset, buffer, 0, buffer.Length)) > 0)
{
// TODO: do something with `bytes` bytes from `buffer`
context.Response.OutputStream.Write(buffer, 0, buffer.Length);
offset += bytes;
}
}
catch (Exception ex)
{
throw ex;
}
finally
{
DB.CloseDB(ref conn);
}
}
看一看這個答案:http://stackoverflow.com/a/609151/284240 –
@TimSchmelter,我將如何得到這個閱讀,從我的數據庫字段塊?我沒有要讀取的文件路徑,而是varbinary字段。 – Nicolai
您可以使用['SqlFileStream'](http://msdn.microsoft.com/zh-cn/library/cc716724.aspx) –