0

我来这里已经有一段时间了。我一直在研究附件存储到数据库的 ASP 项目。我正在尝试将存储在表中的字节存储到文件中。我能够制作文件,但是,我无法从表中获取字节。

这是将文件输入到表中的代码:

'Saves the upload file data to database for the using Request_ID after the request has been created
    strFileName = FileUploadReqDtl.FileName
    strFileExt = strFileName.Substring(strFileName.IndexOf(".") + 1)
    intFileSize = FileUploadReqDtl.PostedFile.ContentLength()

    Dim theDataSize As Byte() = New Byte(FileUploadReqDtl.PostedFile.ContentLength - 1) {}
    Dim uploadedFile As HttpPostedFile = FileUploadReqDtl.PostedFile
    Dim theData = uploadedFile.InputStream.Read(theDataSize, 0, CInt(FileUploadReqDtl.PostedFile.ContentLength))

我能够在一个页面上创建一个链接到另一个 ASP 页面并尝试使文件可下载。我知道 SQL 可以正常工作以从表中获取记录,但是,我无法正确获取字节:

        If (dr.HasRows = True) Then
            While dr.Read()
                ' Casting the value returned by the datareader to the byte[] data type.
                result = CType(dr.GetValue(0), Byte())
                strFileName = dr.GetString(1)
                Debug.Write("strFileName: " & strFileName & vbCrLf)
            End While
        End If
        dr.Close()
        cnToDb.Close()
        ShowFile(strFileName, result, MimeType)
    Catch ex As Exception
        MsgBox("Uh oh, I couldn't get the attachment!")
        Debug.Write("Uh oh, I couldn't get the attachment!")
        Debug.Write(ex.Message & " - " & ex.StackTrace & vbCrLf & vbCrLf)
        result = Nothing
    End Try

这是 ShowFile 函数,它最终使用数据库中的字节“创建文件”:

    Dim fileData() As Byte
    fileData = byteFileData

    Response.Clear()
    Response.AddHeader("Content-Disposition", "attachment; filename=" + strFileName)
    Response.ContentType = MimeType
    Response.BinaryWrite(fileData)
    Response.End()
    Response.Flush()

我遇到的一个例外是:

    SQL: SELECT Data, FileName FROM tblFileUploadData WHERE Report_ID =
116

strFileName: TheAwesomeAttachment.txt A first chance exception of type
'System.Threading.ThreadAbortException' occurred in mscorlib.dll Uh
oh, I couldn't get the attachment!Thread was being aborted. -    at
System.Threading.Thread.AbortInternal()    at
System.Threading.Thread.Abort(Object stateInfo)    at
System.Web.HttpResponse.End()    at
WebApplication3.WebForm2.ShowFile(String strFileName, Byte[]
byteFileData, String MimeType) in C:\Users\Mike\documents\visual
studio
2010\Projects\WebApplication3\WebApplication3\Attachment.aspx.vb:line
81    at WebApplication3.WebForm2.getAttachment(Int32 RequestID,
String MimeType) in C:\Users\Mike\documents\visual studio
2010\Projects\WebApplication3\WebApplication3\Attachment.aspx.vb:line
56

A first chance exception of type
'System.Threading.ThreadAbortException' occurred in
WebApplication3.DLL An exception of type
'System.Threading.ThreadAbortException' occurred in
WebApplication3.DLL but was not handled in user code The thread '<No
Name>' (0x728) has exited with code 0 (0x0). The program '[13512]
WebDev.WebServer40.EXE: Managed (v4.0.30319)' has exited with code 0
(0x0). The program '[13512] WebDev.WebServer40.EXE: Program Trace' has
exited with code 0 (0x0).
4

1 回答 1

1

看一眼:

http://support.microsoft.com/kb/312629

“对于 Response.End,调用 HttpContext.Current.ApplicationInstance.CompleteRequest 方法而不是 Response.End 以绕过对 Application_EndRequest 事件的代码执行”

我喜欢为这种情况创建一个 .ashx 文件。您可以链接到它,它会下载文件而不显示页面。

Public Class DownloadFile
Implements System.Web.IHttpHandler

Public Sub ProcessRequest(context As HttpContext) Implements IHttpHandler.ProcessRequest

    Try

        Dim id As String = context.Request.QueryString("id")

        Dim filename As String = ""

        Dim output As Byte()

        filename = ServiceHelper.GetFilenameByID(id)

        output = ServiceHelper.GetFileBytesByID(id)

        Dim ext As String = System.IO.Path.GetExtension(filename)
        Dim contenttype As String

        'clear the current output content from the buffer
        context.Response.Clear()
        'add the header that specifies the default filename for the
        'Download/SaveAs dialog

        context.Response.AddHeader("Content-Disposition", "attachment; filename=" & filename)

        'add the header that specifies the file size, so that the browser
        'can show the download progress
        context.Response.AddHeader("Content-Length", output.Length.ToString())
        'specify that the response is a stream that cannot be read by the
        'client and must be downloaded
        'Response.ContentType = "application/octet-stream"

        context.Response.Buffer = True

        Select Case ext
            Case ".doc"
                contenttype = "msword"
            Case ".pdf"
                contenttype = "pdf"
            Case ".xls"
                contenttype = "x-excel"
            Case ".ppt"
                contenttype = "ms-powerpoint"
            Case Else
                contenttype = "octet-stream"
        End Select

        context.Response.ContentType = "application/" & contenttype
        context.Response.BinaryWrite(output)

        'http://support.microsoft.com/kb/312629
        'context.Response.End()
        context.ApplicationInstance.CompleteRequest()

    Catch
    End Try

End Sub

Public ReadOnly Property IsReusable() As Boolean Implements IHttpHandler.IsReusable
    Get
        Return False
    End Get
End Property

End Class
于 2012-12-09T15:20:08.517 回答