0

I am working on WinForms using C#. I made a class video that has method yourvideos(). This method reads data from SQL database and add it in imagelist and listview.

First I have uploaded the image and then take the location of image using:

var=open.FileName.ToString();

Then in a function uploadvideo(), I converted image to bytearray and inserted it to database:

public void uploadvideo(string url, string path, string name,string title, DateTime date, string imgloc, string user)
{
    con.Open();
    FileStream file = new FileStream(imgloc,FileMode.Open,FileAccess.Read);
        BinaryReader br = new BinaryReader(file);
        byte[] img = br.ReadBytes((int)file.Length);
   cmd = new SqlCommand($"insert into RecipeInfo (RecipeName, [Recipe Link],Thumbnail,Username, Date, Title) values (@Name,@Path,@img,@Username,@Date,@Title)", con);
                cmd.Parameters.AddWithValue("Name", name);
                cmd.Parameters.AddWithValue("Path", path);
                cmd.Parameters.AddWithValue("Img", img);
                cmd.Parameters.AddWithValue("Username", user);
                cmd.Parameters.AddWithValue("Date", date);
                cmd.Parameters.AddWithValue("Title", title);
                cmd.ExecuteNonQuery();
}

and then the function yourvideos() where I am retrieving data comes.

public void yourvideos(string user, ImageList imglist, ListView list, Label l)
{
     cmd = new SqlCommand("select Title, Thumbnail from RecipeInfo where Username=@username", con);
            cmd.Parameters.AddWithValue("username", user);
    con.Open();
    SqlDataReader reader = cmd.ExecuteReader();
    if (reader.HasRows)
    {
        while (reader.Read())
        {
            byte[] img = (byte[])(reader["Thumbnail"]);
            MemoryStream ms = new MemoryStream(img);
            imglist.Images.Add(Image.FromStream(ms));
            list.Items.Add(reader["Title"].ToString());
            //MessageBox.Show("Data presesnt");
        }
    }
    else
    {

        l.Visible = true;
        l.Text = "Upload videos and share your recipes with others";
    }
    reader.Close();
    con.Close();
}

This function is called in the Form under the button click event

v1.yourvideos(Form2.setname, imageList1, yourvideoslistview, messagelabel);

It is giving me the error when I call yourvideos() that 'parameter is not valid' error details are:

System.ArgumentException
  HResult=0x80070057
  Message=Parameter is not valid.
  Source=System.Drawing
  StackTrace:
   at System.Drawing.Image.FromStream(Stream stream, Boolean useEmbeddedColorManagement, Boolean validateImageData)
   at System.Drawing.Image.FromStream(Stream stream)
   at loginpage.video.yourvideos(String user, ImageList imglist, ListView list, Label l) in C:\Users\maha javed\source\repos\loginpage\Recipe.cs:line 115
   at loginpage.Form3.xuiSuperButton2_Click(Object sender, EventArgs e) in C:\Users\maha javed\source\repos\loginpage\Form3.cs:line 118
   at System.Windows.Forms.Control.OnClick(EventArgs e)
   at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
   at System.Windows.Forms.Control.WndProc(Message& m)
   at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m)
   at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
   at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
   at System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg)
   at System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(IntPtr dwComponentID, Int32 reason, Int32 pvLoopData)
   at System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context)
   at System.Windows.Forms.Application.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context)
   at System.Windows.Forms.Application.Run(Form mainForm)
   at loginpage.Program.Main() in C:\Users\maha javed\source\repos\loginpage\Program.cs:line 19

  This exception was originally thrown at this call stack:
    [External Code]
    loginpage.video.yourvideos(string, System.Windows.Forms.ImageList, System.Windows.Forms.ListView, System.Windows.Forms.Label) in Recipe.cs
    loginpage.Form3.xuiSuperButton2_Click(object, System.EventArgs) in Form3.cs
    [External Code]
    loginpage.Program.Main() in Program.cs
  • Can you provide exception details as well? It should have given you error line information. – WaqarAli Sep 02 '20 at 04:16
  • try `cmd.Parameters.AddWithValue("@Name", name);` adding `@` before parameter name that is . – TheVillageIdiot Sep 02 '20 at 04:22
  • I have editted the error details. and using @ makes no diffference –  Sep 02 '20 at 04:25
  • 1
    To get the byte array of an Image, use `byte[] imageBytes = File.ReadAllBytes(imgloc)` => No Stream and **No BinaryReader**. To get the Image from that Column, `var image = Image.FromStream(new MemoryStream(reader["Thumbnail"]))`. Try to avoid `AddWithValue()` when the you're not using stored procedures. Use `Parameters.Add()` instead. E.g., `cmd.Parameters.Add(@img, SqlDbType.VarBinary).Value = imageBytes;` – Jimi Sep 02 '20 at 05:03
  • Note that [you're still indexing your DataReader](https://stackoverflow.com/q/63695972/7444103) as, e.g., `reader[5]`, when you're querying just 2 Columns. You can have only `reader[0]` and `reader[1]`. Or `reader["Title"]` and `reader["Thumbnail"]`. – Jimi Sep 02 '20 at 05:09
  • @Jimi oh that wass a mistake while posting it here –  Sep 02 '20 at 05:19
  • @Jimi I used the above method u told but if I write `(reader("Thumbnail")` it says `can't convert from object to int` and if I write `(byte[]) reader("Thumbnail")` then again `parameter is not valid` –  Sep 02 '20 at 05:21
  • Check the size of the image as stored in the database against the original file size. It's possible that ReadBytes reads *at most* the suggested size – Hans Kesting Sep 02 '20 at 05:26
  • Yes, I forgot to cast the value returned by the DataReader in that comment. The point is, did you store the Image as `Image` or `VarBinary` data type (and, if the latter, how did you define it)? Also, are you sure you stored it correctly? From the code you're showing here, probably not. Please, update the code with corrections to, at least, `while (reader.HasRows)` and `reader[5]`. Your code is not working. – Jimi Sep 02 '20 at 05:35
  • I stored it as Image –  Sep 02 '20 at 05:43
  • Is the Field's Data Type `Image`? If so, change it to `VARBINARY(max)`, then you can store your byte arrays correctly. The `Image` data type is deprecated, it's still there for backwards compatibility. New implementations are not supposed to use it. – Jimi Sep 02 '20 at 06:05
  • Don't use [addwithvalue](http://www.dbdelta.com/addwithvalue-is-evil/). – SMor Sep 02 '20 at 11:35

2 Answers2

1

From documentation on [this page][1]. This is example of how you should add parameters to SqlCommand object:

string demoXml, string connectionString)
{
    // Update the demographics for a store, which is stored
    // in an xml column.
    string commandText = "UPDATE Sales.Store SET Demographics = @demographics "
        + "WHERE CustomerID = @ID;";
using (SqlConnection connection = new SqlConnection(connectionString))
{
    SqlCommand command = new SqlCommand(commandText, connection);
    command.Parameters.Add("@ID", SqlDbType.Int);
    command.Parameters["@ID"].Value = customerID;

    // Use AddWithValue to assign Demographics.
    // SQL Server will implicitly convert strings into XML.
    command.Parameters.AddWithValue("@demographics", demoXml);

    try
    {
        connection.Open();
        Int32 rowsAffected = command.ExecuteNonQuery();
        Console.WriteLine("RowsAffected: {0}", rowsAffected);
    }
    catch (Exception ex)
    {
        Console.WriteLine(ex.Message);
    }
}

}

TheVillageIdiot
  • 40,053
  • 20
  • 133
  • 188
0

In the while loop you need to call

while(reader.read()){
  .....
}

I'm suggesting using block to dispose your connection , command and reader object.

Also you can see some valuable input from the below link , if the size of the image data is big.

What 'length' parameter should I pass to SqlDataReader.GetBytes()

Biju Kalanjoor
  • 532
  • 1
  • 6
  • 12