2012-07-17 77 views
6

我在讀取MySQL數據庫中的BLOB時遇到了一些麻煩。我已經成功地將它插入數據庫,但似乎無法讓它回讀。我知道你們中的一些人可能會想「爲什麼他使用數據庫來存儲圖像的斑點,而不僅僅是文件路徑/文件名」,但我想要有靈活性,因爲很多這些圖像將存儲在服務器而不是本地的,這樣可以優化效率,並且允許我在需要時將圖像移動到本地。我遵循了一個(簡短的)教程,並且寫下了以下用於接收blob的方法;讀取MySQL數據庫中的BLOB圖像

public void getBlob(string query, string fileOut) 
    { 
     if (this.OpenConnection() == true) 
     { 
      MySqlCommand cmd = new MySqlCommand(query, mConnection); 

      //the index number to write bytes to 
      long CurrentIndex = 0; 

      //the number of bytes to store in the array 
      int BufferSize = 100; 

      //The Number of bytes returned from GetBytes() method 
      long BytesReturned; 

      //A byte array to hold the buffer 
      byte[] Blob = new byte[BufferSize]; 


      //We set the CommandBehavior to SequentialAccess 
      //so we can use the SqlDataReader.GerBytes() method. 

      MySqlDataReader reader = cmd.ExecuteReader(CommandBehavior.SequentialAccess); 

      while (reader.Read()) 
      { 
       FileStream fs = new FileStream(DeviceManager.picPath + "\\" + reader["siteBlobFileName"].ToString(), FileMode.OpenOrCreate, FileAccess.Write); 
       BinaryWriter writer = new BinaryWriter(fs); 
       CurrentIndex = 0; 
       BytesReturned = reader.GetBytes(1, CurrentIndex, Blob, 0,BufferSize); 

       while (BytesReturned == BufferSize) 
       { 
        writer.Write(Blob); 
        writer.Flush(); 
        CurrentIndex += BufferSize; 
        BytesReturned = reader.GetBytes(1, CurrentIndex, Blob, 0, BufferSize); 
       } 

       writer.Write(Blob, 0, (int)BytesReturned); 
       writer.Flush(); 
       writer.Close(); 
       fs.Close(); 
      } 
      reader.Close(); 

      this.CloseConnection(); 
     } 
    } 

和我很喜歡這樣稱它..

mDBConnector.getBlob("SELECT siteMapPicture, siteBlobFilename FROM sites WHERE siteID = '" + DeviceManager.lastSite + "'", DeviceManager.picPath + "mappicsite" + DeviceManager.lastSite); 


PBSite.BackgroundImage = Image.FromFile(DeviceManager.picPath + "mappicsite" + DeviceManager.lastSite); 

但是它示數在BytesReturned = reader.GetBytes(1,CURRENTINDEX,斑點,0,緩衝區大小);錯誤「GetBytes只能在二進制或guid列上調用」。我假設這是與我的數據庫中的字段類型有關,但將列更改爲鍵入二進制意味着我必須將其存儲爲blob類型,但我希望將文件名保留爲常規字符串。有什麼我失蹤?或另一種方式做到這一點?

編輯1:我認爲字節返回的第一個參數是在讀取器中的列,將其設置爲0會給出錯誤「無效嘗試使用SequentialAccess讀取先前列」,否則請仔細觀察一下。

edit2:刪除順序訪問給我一個大小爲13字節的文件(這可能只是第一行,這就是爲什麼順序訪問讀取所有行?),所以也許我按照錯誤的順序讀取列。

編輯3:我相信這個錯誤的原因是由於我輸入數據庫的方式。已經改變這個方法,我saveBlob現在看起來像這樣:

public void saveBlob(string filePath, string fileName, string siteID) 
    { 
     if (this.OpenConnection() == true) 
     { 

      //A stream of bytes that represnts the binary file 
      FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Read); 

      //The reader reads the binary data from the file stream 
      BinaryReader reader = new BinaryReader(fs); 

      //Bytes from the binary reader stored in BlobValue array 
      byte[] BlobValue = reader.ReadBytes((int)fs.Length); 

      fs.Close(); 
      reader.Close(); 


      MySqlCommand cmd = new MySqlCommand(); 
      cmd.Connection = mConnection; 
      cmd.CommandType = CommandType.Text; 
      cmd.CommandText = "INSERT INTO x (y, z) VALUES (@BlobFile, @BlobFileName)"; 

      MySqlParameter BlobFileNameParam = new MySqlParameter("@BlobFileName", SqlDbType.NChar); 
      MySqlParameter BlobFileParam = new MySqlParameter("@BlobFile", SqlDbType.Binary); 
      cmd.Parameters.Add(BlobFileNameParam); 
      cmd.Parameters.Add(BlobFileParam); 
      BlobFileNameParam.Value = fileName; 
      BlobFileParam.Value = BlobValue; 



       cmd.ExecuteNonQuery(); 

      this.CloseConnection(); 
     } 
    } 

我已經通過調試運行,都blobvalue和blobfileparam(@blobfile)具有全尺寸(約15萬),但它的示數在執行該查詢,給出以下錯誤;

​​

我已經看到了入代碼,並試圖改變類型的二進制圖像,允許更大的文件,但給出了同樣的錯誤。任何人都對這個新信息有所瞭解?

編輯4:固定一切。注意到,在我的代碼我使用:

("@BlobFile", SqlDbType.Binary); 

改變了這些類型的「MySQLDbType的」(DERP),它讓我選擇類型的斑點。事情終於按預期工作:)

+1

我不是C#專家,但你選擇2列 - 'siteMapPicture'和'siteBlobFilename' - 都是斑點或者是一個VARCHAR /炭/文本? – 2012-07-17 15:54:07

+0

siteMapPicture是一個BLOB,siteBlobFilename是一個varchar – 2012-07-17 15:56:39

+0

不是c#開發人員,但不會是你的blob字段是列#0,而你想要在第1列getbybytes,這是路徑字段? – 2012-07-17 16:39:17

回答