preview image function causing FileUpload control to reset - asp.net

code snippet for my image upload:
'Read the file and convert it to Byte Array
Dim filePath As String = FileUpload1.PostedFile.FileName
Dim filename As String = Path.GetFileName(filePath)
Dim ext As String = Path.GetExtension(filename)
Dim contenttype As String = String.Empty
'Set the contenttype based on File Extension
Select Case ext
Case ".jpg"
contenttype = "image/jpg"
Exit Select
Case ".png"
contenttype = "image/png"
Exit Select
End Select
If Not contenttype Is String.Empty Then
Dim fs As Stream = FileUpload1.PostedFile.InputStream
Dim br As New BinaryReader(fs)
Dim bytes As Byte() = br.ReadBytes(fs.Length)
'insert the file into database
cmd.Parameters.Add("#imgName", SqlDbType.VarChar).Value = filename
cmd.Parameters.Add("#contentType", SqlDbType.VarChar).Value = contenttype
cmd.Parameters.Add("#data", SqlDbType.Binary).Value = bytes
Else
cmd.Parameters.Add("#imgName", SqlDbType.VarChar).Value = DBNull.Value
cmd.Parameters.Add("#contentType", SqlDbType.VarChar).Value = DBNull.Value
cmd.Parameters.Add("#data", SqlDbType.Binary).Value = DBNull.Value
End If
con.Open()
cmd.ExecuteNonQuery()
con.Close()
preview image:
Protected Sub preview_btn_Click(sender As Object, e As EventArgs) Handles preview_btn.Click
Session("ImageBytes") = FileUpload1.FileBytes
Image1.ImageUrl = "~/Handler1.ashx"
preview_btn.BackColor = Drawing.Color.Lime
preview_btn.ForeColor = Drawing.Color.White
Image1.BorderColor = Drawing.Color.Lime
End Sub
Handler1.ashx
<%# WebHandler Language="VB" Class="Handler1" %>
Imports System
Imports System.Web
Public Class Handler1 : Implements System.Web.IHttpHandler, System.Web.SessionState.IRequiresSessionState
Public Sub ProcessRequest(ByVal context As HttpContext) Implements IHttpHandler.ProcessRequest
If (context.Session("ImageBytes")) IsNot Nothing Then
Dim image As Byte() = DirectCast(context.Session("ImageBytes"), Byte())
context.Response.ContentType = "image/jpeg"
context.Response.BinaryWrite(image)
End If
End Sub
Public ReadOnly Property IsReusable() As Boolean Implements IHttpHandler.IsReusable
Get
Return False
End Get
End Property
End Class
The preview image works but whenever I invoke the preview image button, the FileUpload control get reset.
So from the FileUpload control's point of view, it is as if the user did not select any image in the first place.
I tried storing the value of FileUpload1.PostedFile.FileName in some variable first and then manually set back its value but FileUpload1.PostedFile.FileName appears to be read-only, which makes sense from a security perspective.
So workaround for this?

For a quick solution, I would do the following:
Preview - Save the posted file in session. Set the Image1 image url to handler.
Handler - Get the posted file from session. Write image to response.
Upload - Check if file exists in FileUpload1, get it. If not, get it
from session. Save image. Clear session.
Here's the code I would use:
EDIT : Changed the code to fix issue with larger (> 50kb) images
aspx.vb
Protected Sub btnUpload_Click(sender As Object, e As EventArgs) Handles btnUpload.Click
'Disabled DB operations for test
'Read the file and convert it to Byte Array
Dim filePath As String = String.Empty
Dim filename As String = String.Empty
Dim ext As String = String.Empty
Dim contenttype As String = String.Empty
Dim bytes As Byte()
If FileUpload1.HasFile Then
filePath = FileUpload1.PostedFile.FileName
Else
If (Session("MyFile") IsNot Nothing AndAlso Session("MyFileName") IsNot Nothing) Then
filePath = Session("MyFileName").ToString()
bytes = DirectCast(Session("MyFile"), Byte())
End If
End If
filename = Path.GetFileName(filePath)
ext = Path.GetExtension(filename)
'Set the contenttype based on File Extension
Select Case ext
Case ".jpg"
contenttype = "image/jpg"
Exit Select
Case ".png"
contenttype = "image/png"
Exit Select
End Select
If Not contenttype Is String.Empty Then
If FileUpload1.HasFile Then
Dim fs As Stream = FileUpload1.PostedFile.InputStream
Dim br As New BinaryReader(fs)
bytes = br.ReadBytes(fs.Length)
End If
'insert the file into database
cmd.Parameters.Add("#imgName", SqlDbType.VarChar).Value = filename
cmd.Parameters.Add("#contentType", SqlDbType.VarChar).Value = contenttype
cmd.Parameters.Add("#data", SqlDbType.Binary).Value = bytes
Else
cmd.Parameters.Add("#imgName", SqlDbType.VarChar).Value = DBNull.Value
cmd.Parameters.Add("#contentType", SqlDbType.VarChar).Value = DBNull.Value
cmd.Parameters.Add("#data", SqlDbType.Binary).Value = DBNull.Value
End If
con.Open()
cmd.ExecuteNonQuery()
con.Close()
'Cleanup
Session("MyFile") = Nothing
Session("MyFileName") = Nothing
End Sub
Protected Sub preview_btn_Click(sender As Object, e As EventArgs) Handles preview_btn.Click
If FileUpload1.PostedFile IsNot Nothing Then
Dim file As HttpPostedFile = FileUpload1.PostedFile
Dim data As Byte() = New [Byte](file.ContentLength - 1) {}
file.InputStream.Read(data, 0, file.ContentLength)
Session("MyFile") = data
Session("MyFileName") = FileUpload1.PostedFile.FileName
Image1.ImageUrl = "~/Handler1.ashx"
preview_btn.BackColor = Drawing.Color.Lime
preview_btn.ForeColor = Drawing.Color.White
Image1.BorderColor = Drawing.Color.Lime
End If
End Sub
Handler1.ashx
Sub ProcessRequest(ByVal context As HttpContext) Implements IHttpHandler.ProcessRequest
If (context.Session("MyFile")) IsNot Nothing Then
Dim storedImage = TryCast(context.Session("MyFile"), Byte())
If storedImage IsNot Nothing Then
context.Response.ContentType = "image/jpeg"
context.Response.BinaryWrite(storedImage)
End If
End If
End Sub
Hope it helps!

Related

Exceptional handling in ASP.NET file handler

I am processing PDF/JPG/GIF files using HTTP Handler.
A popup receives a btnId in query string and detects the file extension then calls the handler with btnId and processes the request.
Files are physical stored on server with file names in DB.
When there is an issue with the file like file not found or some error I want an alert to be displayed and opened window to be closed which is not working right now.
I know the reason and that is I am writing the alert into response which will eventually land in either object tag or Image tag.
Can some one please suggest how can this be achieved. Help will be appreciated. Thanks!!!
Public Class ViewHelpContent
Inherits System.Web.UI.Page
'Method that dynamically decides based on file extension which file viewer to render
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Dim embed As String = String.Empty
Dim count As Integer
Dim fileName As String = String.Empty
Dim extension As String = String.Empty
Try
If Not IsPostBack Then
If Not Request.QueryString("btnId") Is Nothing Then
Dim btnId As String = Request.QueryString("btnId").ToString()
count = GetFileAttachedToButton(btnId, fileName)
extension = Path.GetExtension(fileName)
If extension.ToLower() = ".pdf" Then
embed = "<object id=""objPDFViewer"" data=""{0}{1}"" type=""application/pdf"">"
embed &= "If you are unable to view file, you can download from here"
embed &= " or there is no file available to be viewed."
embed &= "</object>"
ElseIf extension.ToLower() = ".jpeg" OrElse extension.ToLower() = ".jpg" OrElse extension.ToLower() = ".gif" Then
embed = "<img id=""objImgViewer"" src=""{0}{1}"" alt=""No file is available to be viewed."" />"
Else
ClientScript.RegisterStartupScript(Me.GetType(), "alert", "alert('No help content uploaded for this button.');", True)
Return
End If
helpContent.Text = String.Format(embed, ResolveUrl("~/ProcessHelpContent.ashx?btnId="), btnId)
End If
End If
Catch ex As Exception
ExceptionHandler.LogError(ex)
JSHelper.ShowSystemError(Me)
End Try
End Sub
End Class
Public Class ProcessHelpContent
Implements System.Web.IHttpHandler
'Sub that processes the help request and generates the requested content based on button Id
Sub ProcessRequest(ByVal context As HttpContext) Implements IHttpHandler.ProcessRequest
Dim btnId As String = String.Empty
Dim fileName As String = String.Empty
Dim contentType As String = String.Empty
Dim outputDir As String = String.Empty
Dim count As Integer
Dim strPath As FileInfo = Nothing
Dim extension As String = String.Empty
Try
If Not context.Request.QueryString("btnId") Is Nothing Then
btnId = context.Request.QueryString("btnId").ToString()
outputDir = ConfigurationManager.AppSettings("HelpContentFilesFolder")
count = GetFileAttachedToButton(btnId, fileName)
strPath = New FileInfo(outputDir & fileName)
If Not String.IsNullOrWhiteSpace(fileName) Then
If File.Exists(strPath.FullName) Then
extension = Path.GetExtension(strPath.FullName)
If context.Request.QueryString("download") = "1" Then
context.Response.AppendHeader("Content-Disposition", Convert.ToString("attachment; filename=") & fileName)
End If
context.Response.Cache.SetCacheability(HttpCacheability.NoCache)
If extension.ToLower() = ".pdf" Then
context.Response.ContentType = "application/pdf"
ElseIf extension.ToLower() = ".jpg" OrElse extension.ToLower() = ".jpeg" Then
context.Response.ContentType = "image/jpeg"
ElseIf extension.ToLower() = ".gif" Then
context.Response.ContentType = "image/gif"
End If
context.Response.TransmitFile(strPath.FullName)
context.Response.Flush()
Else
context.Response.Write("<script>alert('Uploaded help file is missing. Please re-upload or contact administrator.'); window.close();</script>")
End If
Else
context.Response.Write("<script>alert('Uploaded help file is missing. Please re-upload or contact administrator.'); window.close();</script>")
End If
End If
Catch ex As Exception
ExceptionHandler.LogError(ex)
context.Response.Write("<script>alert('Uploaded help file is missing. Please re-upload or contact administrator.'); window.close();</script>")
End Try
End Sub
ReadOnly Property IsReusable() As Boolean Implements IHttpHandler.IsReusable
Get
Return False
End Get
End Property
End Class

Cross communication between two web applications using web requests: is this close to viable?

I am using the following code to try and learn how pages post, listen and respond between one another using web requests. I begin the process by issuing a request in the first of the two procedures, intending to have the second process retrieve the request and respond back to the calling process. My calling process is receiving a blank response.
Question: Why, and how close to viable is this test?
Here's my two page load events, located in two separate web applications.
Both apps are hosted on IIS:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Dim sPostURL As String = "http://localhost/DDI_TXListener_Test/Listener_Page.aspx"
Dim dataToPost As String = String.Empty ' //This is the data for form posting
Dim HttpWebResponse As System.Net.WebResponse = Nothing
Dim StreamReader As System.IO.StreamReader = Nothing
Dim respString As String = String.Empty
Dim stOut As System.IO.Stream = Nothing
dataToPost = "Name"
Try
Dim httpReq As System.Net.WebRequest = System.Net.WebRequest.Create(sPostURL)
httpReq.Method = "POST"
httpReq.ContentType = "application/x-www-form-urlencoded"
Dim byte1 As Byte() = System.Text.Encoding.ASCII.GetBytes(dataToPost)
httpReq.ContentLength = byte1.Length
httpReq.Timeout = 10000
stOut = httpReq.GetRequestStream()
stOut.Write(byte1, 0, byte1.Length)
stOut.Dispose()
stOut = Nothing
HttpWebResponse = httpReq.GetResponse()
StreamReader = New System.IO.StreamReader(HttpWebResponse.GetResponseStream(), System.Text.Encoding.GetEncoding("utf-8"))
respString = StreamReader.ReadToEnd()
Catch ex As Exception
Finally
If Not StreamReader Is Nothing Then
StreamReader.Dispose()
StreamReader = Nothing
End If
If Not HttpWebResponse Is Nothing Then
HttpWebResponse.Close()
HttpWebResponse = Nothing
End If
End Try
' <asp:label> control on the html form in front of this code page
returnedhit.Text = respString
End Sub
And I have this as what I hope to use as the receiving/fulfilling end of the above request at:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Dim sPostURL As String = "http://localhost/DDI_TXRequester_Test/RequesterPage.aspx"
Dim dataToPost As String = String.Empty ' //This is the data for form posting
Dim HttpWebResponse As System.Net.WebResponse = Nothing
Dim StreamReader As System.IO.StreamReader = Nothing
Dim respString As String = String.Empty
Dim stOut As System.IO.Stream = Nothing
Try
Dim httpReq As System.Net.WebRequest = System.Net.WebRequest.Create(sPostURL)
HttpWebResponse = httpReq.GetResponse()
StreamReader = New System.IO.StreamReader(HttpWebResponse.GetResponseStream(), System.Text.Encoding.GetEncoding("utf-8"))
respString = StreamReader.ReadToEnd()
If respString <> "" Then
Dim cnt As Integer = 0
Dim delim As Char() = {"&"c}
Dim bodpos As Integer = InStr(respString, "<body>") + 6
Dim respstr As String = Right$(respString, (Len(respString) - bodpos))
Dim strArr As String() = respstr.Split(delim)
For Each s As String In strArr
cnt += 1
Select Case cnt
Case 1
Session.Add("opRequested", Right$(Trim(s), (Len(Trim(s)) - 18)))
Case Else '
End Select
Next s
If CStr(Session("opRequested")) = "Name" Then dataToPost = "Name=Jones" Else dataToPost = "Error=Unknown Request"
httpReq.Method = "POST"
httpReq.ContentType = "application/x-www-form-urlencoded"
Dim byte1 As Byte() = System.Text.Encoding.ASCII.GetBytes(dataToPost)
httpReq.ContentLength = byte1.Length
httpReq.Timeout = 10000
stOut = httpReq.GetRequestStream()
stOut.Write(byte1, 0, byte1.Length)
stOut.Dispose()
stOut = Nothing
End If
Catch ex As Exception
Finally
If Not stOut Is Nothing Then
stOut.Dispose()
stOut = Nothing
End If
If Not StreamReader Is Nothing Then
StreamReader.Dispose()
StreamReader = Nothing
End If
If Not HttpWebResponse Is Nothing Then
HttpWebResponse.Close()
HttpWebResponse = Nothing
End If
End Try
End Sub

how to use fileupload insert to database sql server this

Protected Sub btnUpload_Click(ByVal sender As Object, e As EventArgs) Handles btnUpload.Click
Dim filePath As String = FileUpload.PostedFile.FileName
Dim filePath2 As String = FileUploadImage.PostedFile.FileName
Dim fileName As String = Path.GetFileName(filePath)
Dim ext As String = Path.GetExtension(fileName)
Dim contenttyppe As String = String.Empty
Select Case ext
Case ".pdf"
ContentType = "application/pdf"
Exit Select
Case ".jpg"
ContentType = "image/jpg"
Exit Select
Case ".pfx"
ContentType = "image/pfx"
Exit Select
Case ".png"
ContentType = "image/png"
Exit Select
Case ".gif"
ContentType = "image/gif"
Exit Select
Case ".doc"
ContentType = "application/vnd.ms-word"
Exit Select
Case ".docx"
ContentType = "application/vnd.ms-word"
Exit Select
Case ".xls"
ContentType = "application/vnd.ms-excel"
Exit Select
Case ".xlsx"
ContentType = "application/vnd.ms-excel"
Exit Select
Case ".pfx"
ContentType = "image/pfx"
Exit Select
End Select
If contenttyppe <> String.Empty Then
Dim fs As Stream = FileUpload.PostedFile.InputStream
Dim fi As Stream = FileUploadImage.PostedFile.InputStream
Dim br As New BinaryReader(fs)
Dim br2 As New BinaryReader(fi)
Dim bytes As Byte() = br.ReadBytes(fs.Length)
Dim bytes2 As Byte() = br2.ReadBytes(fi.Length)
Dim strQuery As String = "insert into APPUSERDTL (UID,APPCODE,APPEXPIRED,SIGNIMAGE, PFKFILE,HEADUID,PRINCIPALFROM,PRINCIPALTO,EXCEPTIONUSER,LastUpdate)" _
& "VALUES('',' ','',' #FileUpload ',' #FileUploadImage','','','','','')"
Dim cmd As New SqlCommand(strQuery)
cmd.Parameters.Add("#UID", Data.SqlDbType.Int).Value = bytes
cmd.Parameters.Add("#APPCODE", Data.SqlDbType.VarChar, 50).Value = bytes
cmd.Parameters.Add("#APPEXPIRED", Data.SqlDbType.DateTime).Value = bytes
cmd.Parameters.Add("#FileUpload", Data.SqlDbType.Image).Value = FileUpload
cmd.Parameters.Add("#FileUploadImage", Data.SqlDbType.VarBinary).Value = FileUploadImage
cmd.Parameters.Add("#HEADUID", Data.SqlDbType.Int).Value = bytes
cmd.Parameters.Add("#PRINCIPALFROM", Data.SqlDbType.Money).Value = bytes
cmd.Parameters.Add("#PRINCIPALTO", Data.SqlDbType.Money).Value = bytes
cmd.Parameters.Add("#EXCEPTIONUSER", Data.SqlDbType.Bit).Value = bytes
cmd.Parameters.Add("#LastUpdate", Data.SqlDbType.DateTime).Value = bytes
InsertUpdateData(cmd)
lblMsgUpload.ForeColor = System.Drawing.Color.Green
lblMesgImage.ForeColor = System.Drawing.Color.Green
lblMsgUpload.Text = "File Upload Successfully"
lblMesgImage.Text = "File Upload Successfuly"
Else
lblMesgImage.ForeColor = System.Drawing.Color.Red
lblMesgImage.Text = "File format not recognised." _
& " Upload Image/Word/PDF/Excel formats"
End If
' delete file upload
Dim fullPath = MapPath("~/upload/") + fileName
If System.IO.File.Exists(fullPath) Then
System.IO.File.Delete(fullPath)
End If
End Sub
==================================================
Public Function InsertUpdateData(ByVal cmd As SqlCommand) As Boolean
' Dim strConnString As New DBX
Dim strConnString As String = System.Configuration.ConfigurationManager.ConnectionStrings("connection").ConnectionString
Dim conn As New SqlConnection(strConnString)
cmd.CommandType = CommandType.Text
cmd.Connection = conn
Try
conn.Open()
cmd.ExecuteNonQuery()
Return True
Catch ex As Exception
Response.Write(ex.Message)
Return False
Finally
conn.Close()
conn.Dispose()
End Try
End Function
End Class
You have only two parameters placeholders in the query text (#FileUpload and #FileUploadImage). Then you define parameters for every field with various datatype, but then set them all with the same value (bytes). Finally the commas that should separe the values are placed wrongly in the query text. No wonder that you ExecuteNonQuery doesn't work
If you don't know the other values and your record could be inserted leaving that fields to their default value you could try with this trimmed down version of your query above. Otherwise you need to know the actual values to insert in the other fields and initialize the parameters value with the appropriate variables.
Dim strQuery As String = "insert into APPUSERDTL (SIGNIMAGE,PKFILE,LastUpdate) " & _
"VALUES(#FileUpload,#FileUploadImage, GetDate())"
Dim cmd As New SqlCommand(strQuery)
cmd.Parameters.Add("#FileUpload", Data.SqlDbType.Image).Value = FileUpload
cmd.Parameters.Add("#FileUploadImage", Data.SqlDbType.VarBinary).Value = FileUploadImage
InsertUpdateData(cmd)
As a last note, when you have errors it is always good to add the error message to your question. It is very helpfull to understand what happens in your code.

Downloading a file from SQL Server - ArgumentOutOfRangeException

I'm trying to download files from an SQL Server 2012 database using GridView. I am getting an ArgumentOutOfRangeException giving me this error:
Index was out of range. Must be non-negative and less than the size of the collection.
on:
Dim fileid As Integer = Convert.ToInt32(GridView1.DataKeys(gvrow.RowIndex).Value.ToString())
Code concerned:
Protected Sub lnkDownload_Click(ByVal sender As Object, ByVal e As EventArgs)
Dim lnkbtn As LinkButton = TryCast(sender, LinkButton)
Dim gvrow As GridViewRow = TryCast(lnkbtn.NamingContainer, GridViewRow)
Dim fileid As Integer = Convert.ToInt32(GridView1.DataKeys(gvrow.RowIndex).Value.ToString())
Dim name As String, type As String
Dim con As New SqlConnection("Data Source=BRIAN-PC\SQLEXPRESS;Initial Catalog=master_db;Integrated Security=True;")
con.Open()
Using cmd As New SqlCommand()
cmd.CommandText = "Select content_name, content_type, content_file from content where content_id=#Id"
cmd.Parameters.AddWithValue("#Id", fileid)
cmd.Connection = con
con.Open()
Dim dt As DataTable = GetData(cmd)
If dt IsNot Nothing Then
download(dt)
End If
End Using
End Sub
Public Function GetData(ByVal cmd As SqlCommand) As DataTable
Dim dt As New DataTable
Dim strConnString As String = System.Configuration.ConfigurationManager.ConnectionStrings("ConnStringDb1").ConnectionString()
Dim con As New SqlConnection(strConnString)
Dim sda As New SqlDataAdapter
cmd.CommandType = CommandType.Text
cmd.Connection = con
Try
con.Open()
sda.SelectCommand = cmd
sda.Fill(dt)
Return dt
Catch ex As Exception
Response.Write(ex.Message)
Return Nothing
Finally
con.Close()
sda.Dispose()
con.Dispose()
End Try
End Function
Protected Sub download(ByVal dt As DataTable)
Dim bytes() As Byte = CType(dt.Rows(0)("Data"), Byte())
Response.Buffer = True
Response.Charset = ""
Response.Cache.SetCacheability(HttpCacheability.NoCache)
Response.ContentType = dt.Rows(0)("ContentType").ToString()
Response.AddHeader("content-disposition", "attachment;filename=" & dt.Rows(0)("Name").ToString())
Response.BinaryWrite(bytes)
Response.Flush()
Response.End()
End Sub
gvrow.RowIndex at time of debugging is 0.
Full Code:
Imports System.Data.SqlClient
Imports System.Data
Imports System.IO
Partial Class Documents
Inherits System.Web.UI.Page
Protected Sub btnUploadContent_Click(sender As Object, e As EventArgs) Handles btnUploadContent.Click
Dim filePath As String = FileUpload.PostedFile.FileName
Dim filename As String = Path.GetFileName(filePath)
Dim ext As String = Path.GetExtension(filename)
Dim contenttype As String = String.Empty
Select Case ext
Case ".doc"
contenttype = "application/vnd.ms-word"
Exit Select
Case ".docx"
contenttype = "application/vnd.ms-word"
Exit Select
Case ".xls"
contenttype = "application/vnd.ms-excel"
Exit Select
Case ".xlsx"
contenttype = "application/vnd.ms-excel"
Exit Select
Case ".jpg"
contenttype = "image/jpg"
Exit Select
Case ".png"
contenttype = "image/png"
Exit Select
Case ".gif"
contenttype = "image/gif"
Exit Select
Case ".pdf"
contenttype = "application/pdf"
Exit Select
End Select
If contenttype <> String.Empty Then
Dim fs As Stream = FileUpload.PostedFile.InputStream
Dim br As New BinaryReader(fs)
Dim bytes As Byte() = br.ReadBytes(fs.Length)
'insert the file into database
Dim strQuery As String = "INSERT INTO [master_db].[dbo].[content] ([content_name],[content_type],[content_file]) VALUES (#Name, #ContentType, #Data)"
Dim cmd As New SqlCommand(strQuery)
cmd.Parameters.Add("#Name", SqlDbType.VarChar).Value = filename
cmd.Parameters.Add("#ContentType", SqlDbType.VarChar).Value() = contenttype
cmd.Parameters.Add("#Data", SqlDbType.Binary).Value = bytes
InsertUpdateData(cmd)
lblMessage.ForeColor = System.Drawing.Color.Green
lblMessage.Text = "File Uploaded Successfully"
Else
lblMessage.ForeColor = System.Drawing.Color.Red
lblMessage.Text = "File format not recognised." + " Upload Image/Word/PDF/Excel formats"
End If
End Sub
Protected Sub lnkDownload_Click(ByVal sender As Object, ByVal e As EventArgs)
Dim lnkbtn As LinkButton = TryCast(sender, LinkButton)
Dim gvrow As GridViewRow = TryCast(lnkbtn.NamingContainer, GridViewRow)
Dim fileid As Integer = Convert.ToInt32(GridView1.DataKeys(gvrow.RowIndex).Value.ToString())
Dim name As String, type As String
Dim con As New SqlConnection("Data Source=BRIAN-PC\SQLEXPRESS;Initial Catalog=master_db;Integrated Security=True;")
con.Open()
Using cmd As New SqlCommand()
cmd.CommandText = "Select content_name, content_type, content_file from content where content_id=#Id"
cmd.Parameters.AddWithValue("#Id", fileid)
cmd.Connection = con
con.Open()
Dim dt As DataTable = GetData(cmd)
If dt IsNot Nothing Then
download(dt)
End If
End Using
End Sub
Public Function GetData(ByVal cmd As SqlCommand) As DataTable
Dim dt As New DataTable
Dim strConnString As String = System.Configuration.ConfigurationManager.ConnectionStrings("ConnStringDb1").ConnectionString()
Dim con As New SqlConnection(strConnString)
Dim sda As New SqlDataAdapter
cmd.CommandType = CommandType.Text
cmd.Connection = con
Try
con.Open()
sda.SelectCommand = cmd
sda.Fill(dt)
Return dt
Catch ex As Exception
Response.Write(ex.Message)
Return Nothing
Finally
con.Close()
sda.Dispose()
con.Dispose()
End Try
End Function
Protected Sub download(ByVal dt As DataTable)
Dim bytes() As Byte = CType(dt.Rows(0)("Data"), Byte())
Response.Buffer = True
Response.Charset = ""
Response.Cache.SetCacheability(HttpCacheability.NoCache)
Response.ContentType = dt.Rows(0)("ContentType").ToString()
Response.AddHeader("content-disposition", "attachment;filename=" & dt.Rows(0)("Name").ToString())
Response.BinaryWrite(bytes)
Response.Flush()
Response.End()
End Sub
Public Function InsertUpdateData(ByVal cmd As SqlCommand) As Boolean
Dim strConnString As String = System.Configuration.ConfigurationManager.ConnectionStrings("ConnStringDb1").ConnectionString()
Dim conn As New SqlConnection("Data Source=BRIAN-PC\SQLEXPRESS;Initial Catalog=master_db;Integrated Security=True;")
cmd.CommandType = CommandType.Text
cmd.Connection = conn
Try
conn.Open()
cmd.ExecuteNonQuery()
Return True
Catch ex As Exception
Response.Write(ex.Message)
Return False
Finally
conn.Close()
conn.Dispose()
End Try
End Function
End Class
What is happening and why?
replace the error line with this:
Dim selectedRow As Integer = Me.GridView1.CurrentRow.Index
Dim fileid As Integer = Convert.ToInt32(Me.GridView1.Item(1,gvrow.RowIndex).Value.ToString())
Replace the number 1 with the index of the cell that contains the fileid (ie if its the 0 for the first cell, 1 for the second and so on)
Let me know if this works. Am a C# developer so conversions may differ.
pass the RowIndex via CommandArgument and use it to retrieve the DataKey value
add the below line on Button
CommandArgument='<%# DataBinder.Eval(Container, "RowIndex") %>'
and add the below line on Server Event
Dim Index As Integer = Integer.Parse(e.CommandArgument.ToString())
Dim val As String = DirectCast(Me.grid.DataKeys(Index)("YourDataKeyName"), String)
Update:
See this samples :
sample1
sample 2
I ran into this a while ago myself replacing a predecessors data adapter's with data readers for obvious reasons.
My fix was simple:
if (dt.Rows.Count == 0)
//do stuff
else
//do nothing
GV.DataSource = new DataTable();
you're also loading with a datatable, so that should make deploying it easier.
The reason in your specific case is the exception is thrown when no data is passed to the GV.

Uploading files to SQL Server 2012 with ASP.NET/VB.NET

I followed a tutorial an ran the below code without any errors. The file "uploads", however no data is inserted into my SQL Server table.
Data should be inserted into the content table.
Content Table:
Document.aspx
Imports System.Data.SqlClient
Imports System.Data
Imports System.IO
Partial Class Documents
Inherits System.Web.UI.Page
Protected Sub btnUploadContent_Click(sender As Object, e As EventArgs) Handles btnUploadContent.Click
Dim filePath As String = FileUpload.PostedFile.FileName
Dim filename As String = Path.GetFileName(filePath)
Dim ext As String = Path.GetExtension(filename)
Dim contenttype As String = String.Empty
Select Case ext
Case ".doc"
contenttype = "application/vnd.ms-word"
Exit Select
Case ".docx"
contenttype = "application/vnd.ms-word"
Exit Select
Case ".xls"
contenttype = "application/vnd.ms-excel"
Exit Select
Case ".xlsx"
contenttype = "application/vnd.ms-excel"
Exit Select
Case ".jpg"
contenttype = "image/jpg"
Exit Select
Case ".png"
contenttype = "image/png"
Exit Select
Case ".gif"
contenttype = "image/gif"
Exit Select
Case ".pdf"
contenttype = "application/pdf"
Exit Select
End Select
If contenttype <> String.Empty Then
Dim fs As Stream = FileUpload.PostedFile.InputStream
Dim br As New BinaryReader(fs)
Dim bytes As Byte() = br.ReadBytes(fs.Length)
'insert the file into database
Dim strQuery As String = "INSERT INTO content (content_name, content_type, content_file) VALUES (#Name, #ContentType, #Data)"
Dim cmd As New SqlCommand(strQuery)
cmd.Parameters.Add("#Name", SqlDbType.VarChar).Value = filename
cmd.Parameters.Add("#ContentType", SqlDbType.VarChar).Value() = contenttype
cmd.Parameters.Add("#Data", SqlDbType.Binary).Value = bytes
InsertUpdateData(cmd)
lblMessage.ForeColor = System.Drawing.Color.Green
lblMessage.Text = "File Uploaded Successfully"
Else
lblMessage.ForeColor = System.Drawing.Color.Red
lblMessage.Text = "File format not recognised." + " Upload Image/Word/PDF/Excel formats"
End If
End Sub
Public Function InsertUpdateData(ByVal cmd As SqlCommand) As Boolean
Dim strConnString As String = System.Configuration.ConfigurationManager.ConnectionStrings("ConnStringDb1").ConnectionString()
Dim conn As New SqlConnection("Data Source=BRIAN-PC\SQLEXPRESS;Initial Catalog=master_db;Integrated Security=True;")
cmd.CommandType = CommandType.Text
cmd.Connection = conn
Try
conn.Open()
cmd.ExecuteNonQuery()
Return True
Catch ex As Exception
Response.Write(ex.Message)
Return False
Finally
conn.Close()
conn.Dispose()
End Try
End Function
End Class
Can anyone tell me what's going on ?
EDIT: Debug Breakpoint # InsertUpdateData(cmd) :
SqlDbType.Binary Binary {1} System.Data.SqlDbType
+ bytes {Length=4136752} Byte()
+ cmd {System.Data.SqlClient.SqlCommand} System.Data.SqlClient.SqlCommand
+ cmd.Parameters {System.Data.SqlClient.SqlParameterCollection} System.Data.SqlClient.SqlParameterCollection
I have created empty database and added table content just like you have and I used code almost the same as you and it worked fine.
Again, if no exception occurs, please check your connection string and see whether the rows been added to the table in the db specified in connection string.
Here is my code (which is working fine), a bit modified from yours:
Imports System.Data.SqlClient
Imports System.IO
Public Class _Default
Inherits System.Web.UI.Page
Protected Sub btnUploadContent_Click(sender As Object, e As EventArgs) Handles btnTest1.Click
Dim fs As Stream = FileUpload.PostedFile.InputStream
Dim br As New BinaryReader(fs)
Dim bytes As Byte() = br.ReadBytes(fs.Length)
'insert the file into database
Dim strQuery As String = "INSERT INTO content (content_name, content_type, content_file) VALUES (#Name, #ContentType, #Data)"
Dim cmd As New SqlCommand(strQuery)
cmd.Parameters.Add("#Name", SqlDbType.VarChar).Value = "filename"
cmd.Parameters.Add("#ContentType", SqlDbType.VarChar).Value() = "jpg"
cmd.Parameters.Add("#Data", SqlDbType.Binary).Value = bytes
InsertUpdateData(cmd)
End Sub
Public Function InsertUpdateData(ByVal cmd As SqlCommand) As Boolean
Dim conn As New SqlConnection("Data Source=(local);Initial Catalog=test;Integrated Security=True;")
cmd.CommandType = CommandType.Text
cmd.Connection = conn
Try
conn.Open()
cmd.ExecuteNonQuery()
Return True
Catch ex As Exception
Response.Write(ex.Message)
Return False
Finally
conn.Close()
conn.Dispose()
End Try
End Function
End Class
I add sample of SQL to test on DB:
INSERT INTO [master_db].[dbo].[content]
([content_name]
,[content_type]
,[content_file])
VALUES
('test'
,'png'
,0x111111111111111)
SELECT * FROM [master_db].[dbo].[content]
I came across this post looking looking for an example. I used the example code you posted and had the same problem. I found and resolved the following issues and got it working:
I created the db table as pictured. content_type of nchar(5) was the first problem since you were inserting something like "application/vnd.ms-word" which was too big.
The next error was because I had not defined the content_id to be an identity column and since it wasn't listed in the insert statement it failed.
Next I had an error as my db user didn't have insert privileges.
The biggest problem is that the return message was always a success message because even though the InsertUpdateData function was catching errors it was not notifying the calling code. This made me think things were okay. doh! Using a breakpoint on the ExecuteNonQuery allowed me to see the errors.
Hope that helps the next person that stops by....

Resources