0

So, I have the following script to convert images into binaries (so I can put it on a blob):

public static byte[] ImagemBin(string imagePath, int imagem_comp)
    {

        FileStream fileStream = new FileStream(imagePath, FileMode.Open, FileAccess.Read);
        byte[] buffer = new byte[imagem_comp];

        int numBytesToRead = imagem_comp;
        int numBytesRead = 0;
        while (numBytesToRead > 0)
        {
            // Read may return anything from 0 to numBytesToRead.
            int n = fileStream.Read(buffer, numBytesRead, numBytesToRead);

            // Break when the end of the file is reached.
            if (n == 0)
                break;

            numBytesRead += n;
            numBytesToRead -= n;
        }
        numBytesToRead = buffer.Length;

       fileStream.Read(buffer, 0, numBytesToRead);

        fileStream.Close();
        return buffer;
    }

Where imagePath is the location of the image in the computer, and imagem_comp is the size of the image. However, the image convertion is incomplete, and after a few bytes, it returns uniquely 0's...

So, any help on this?

Thank you in advance.

Gabe
  • 84,912
  • 12
  • 139
  • 238
João Borrego
  • 95
  • 2
  • 12

2 Answers2

0

You should explain what you are trying to accomplish. like what is imagem_comp supposed to be? I find the following wrong with your logic.

  1. You overwrite the buffer in each iteration without doing anything with it.
  2. You are subtracting the numbers of bytes read from the number of bytes to read on this line numBytesToRead -= n;. After one read you will then only be asking to read 0 bytes.
  3. You overwrite the buffer again with essentially the same data as the first iteration outside of the loop.
  4. Assuming all of the above are fixed, you are returning a buffer that does not contain all of the data if the file contains more bytes than imagem_comp.

As @bmm6o stated in the comments above, you should be able to replace this with File.ReadAllBytes.

Joe
  • 56,979
  • 9
  • 128
  • 135
  • Tried the File.ReadAllBytes and somehow, this is what gets stored in my blob field: "System.Byte[]". Still I must do a function that transforms an image to binary. – João Borrego Apr 11 '12 at 21:23
  • `ReadAllBytes` does create an in memory binary representation of the image. If `FindAllBytes` did not work you are doing something incorrectly elsewhere. – Joe Apr 12 '12 at 00:57
  • Here's how I'm creating it: Binary imagem = File.ReadAllBytes(file); Anything before is getting more info from the form, and after it's a mySql query. – João Borrego Apr 12 '12 at 17:24
  • If you get `System.Byte[]` in the database it is because you are inserting the description (`ToString()`) of object and not the data itself. Therefore you are incorrectly inserting the binary into your query. – Joe Apr 12 '12 at 17:31
  • Here's the query: string myQuery = "INSERT INTO livros (tituloLivros, dataedicaoLivros, isbnLivros, autoresLivros, generoLivros, editorasLivros, imagemLivros, nomeImagemLivros, elazerLivros, resumoLivros, pedidoLivros, disponivelLivros, sizeImagemLivros) VALUES ('" + titulo + "','" + data_string + "','" + isbn + "','" + autor + "','" + genero + "','" + editora + "','" + imagem + "','" + nomeimagem + "','" + lazer + "','" + resumo + "','" + pedidos + "','" + disponivel + "','" + imagem_comp + "')"; Do I need to change anything in it to make it work? – João Borrego Apr 12 '12 at 17:54
  • The only one you need to focus is the "imagemLivros" db field, and the imagem var. The remaining fields are about "other stuff". – João Borrego Apr 12 '12 at 17:56
  • There is your problem!! 1) [Use parameterized queries](http://www.codinghorror.com/blog/2005/04/give-me-parameterized-sql-or-give-me-death.html) 2) USE PARAMETERIZED QUERIES, and 3) Once you've parameterized your query set the `imagem` as [`SqlDbType.VarBinary`](http://stackoverflow.com/questions/1064121/how-do-i-insert-a-byte-into-an-sql-server-varbinary-column). – Joe Apr 12 '12 at 18:17
  • Yup, it worked! :D Thank you, and that's something I'll take care in the future ;) – João Borrego Apr 12 '12 at 18:49
0

It appears to work with this version:

public static byte[] ImagemBin(string imagePath, int imagem_comp)
{

    FileStream fileStream = new FileStream(imagePath, FileMode.Open, FileAccess.Read);
    byte[] buffer = new byte[imagem_comp];

    int numBytesToRead = imagem_comp;
    int numBytesRead = 0;
    while (numBytesToRead > 0)
    {
        // Read may return anything from 0 to numBytesToRead.
        int n = fileStream.Read(buffer, numBytesRead, numBytesToRead);

        // Break when the end of the file is reached.
        if (n == 0)
            break;

        numBytesRead += n;
        numBytesToRead -= n;
    }

    fileStream.Close();
    return buffer;
}

I.e. remove the lines:

numBytesToRead = buffer.Length;

and

fileStream.Read(buffer, 0, numBytesToRead);

That said, I agree with what others have mentioned; consider using ReadAllBytes. :-)

dharmatech
  • 8,979
  • 8
  • 42
  • 88
  • While that would work if you knew the exact file size when calling the function, the logic is still essentially wrong because `imagem_comp` is treated as a buffer size. – Joe Apr 11 '12 at 20:10
  • 1. ReadAllBytes does the exact same thing as my function, it doesn't upload the complete file. 2. I'm supposed to make my own function to do that. 3. imagem_comp is the exact size of the image. – João Borrego Apr 11 '12 at 20:52