1. 程式人生 > >往MySQL中儲存圖片 longBlob型別

往MySQL中儲存圖片 longBlob型別

往MySQL中儲存圖片 1 介紹 在設計到資料庫的開發中,難免要將圖片或音訊檔案插入到資料庫中的情況。一般來說,我們可以同過插入圖片檔案相應的儲存位置,而不是檔案本身,來避免直接向資料庫裡插入的麻煩。但有些時候,向MySQL中插入圖片更加容易管理。那麼在MySQL中該怎麼儲存呢? 參考資料[1]中有個相當清晰的例子,不過是基於MySQL圖形介面的查詢工具Query Brower的,你的機子上沒有安裝的話,可能得不到很好的理解。我在這裡不在贅述,更詳細的資料請看給出的連結吧。 還有,[1]中的例子其實只是向我們說明了Query Brower的易用和強大,對我們在開發中實際應用不是很大。所以下面就讓我們用JAVA寫一個向MySQL中儲存的簡單例項。 2 建表 首先,先要在資料庫中建表。我在名為test的資料庫下建立了一個叫pic的表。該表包括3列,idpic, caption和img。其中idpic是主鍵,caption是對圖片的表述,img是影象檔案本身。建表的SQL語句如下: DROP TABLE IF EXISTS `test`.`pic`; CREATE TABLE `test`.`pic` (  `idpic` int(11) NOT NULL auto_increment,  `caption` varchar(45) NOT NULL default '',  `img` longblob NOT NULL,  PRIMARY KEY (`idpic`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8; 將上面的語句輸入到命令列中(如果安裝了Query Brower, 你可以按照參考[1]中的指示來建表,那樣會更加方便。),執行,表建立成功。 3 實現影象儲存類 表完成後,我們就開始寫個Java類,來完成向資料庫中插入圖片的操作。我們知道,Java與資料庫連線是通過JDBC driver來實現的。我用的是MySQL網站上提供的MySQL Connector/J,如果你用的是其他型別的driver, 在下面的實現過程中可能會有些許差別。 3.1 裝載JDBC驅動,建立連線 JDK中提供的DriverManager介面用來管理Java Application 和 JDBC Driver之間的連線。在使用這個介面之前, DriverManager需要知道要連線的JDBC 驅動。最簡單的方法就是用Class.forName()來向DriverManager註冊實現了java.sql.Driver 的介面類。對MySQL Connector/J來說,這個類的名字叫com.mysql.jdbc.Driver。 下面這個簡單的示例說明了怎樣來註冊Connector/J Driver。 import java.sql.Connection; import java.sql.DriverManager; import java.sql.SQLException; public class LoadDriver {     public static void main(String[] args) {
        try {             // The newInstance() call is a work around for some             // broken Java implementations             Class.forName("com.mysql.jdbc.Driver").newInstance();             // Connection con = DriverManager.getConnection(……)             // ……         } catch (Exception ex) {
            // handle the error         } } 向DriverManager註冊了驅動後,我們就可以通過呼叫 DriverManager.getConnection()方法來獲得和資料庫的連線。其實在上面的例子中就有這條語句,只不過被註釋掉了。在後面的實現中會有完整的例子。 3.2 PreparedStatement 完成上面的步驟後,我們就可以同過建立的連線建立Statement介面類,來執行一些SQL語句了。在下面的例子,我用的是PreparedStatement,還有CallableStatement,它可以執行一些儲存過程和函式,這裡不多講了。下面的程式碼片斷是向pic表中插入一條記錄。其中(1)處Connection介面的物件con通過呼叫prepareStatement 方法得到預編譯的SQL 語句(precompiled SQL statement);(2)處是為該insert語句的第一個問號賦值,(3)為第二個賦值,(4)為第三個,這步也是最該一提的,用的方法是setBinaryStream(),第一個引數3是指第三個問號,fis是一個二進位制檔案流,第三個引數是該檔案流的長度。 PreparedStatement ps; … ps = con.prepareStatement("insert into PIC values (?,?,?)"); // (1) ps.setInt(1, id); //(2) ps.setString(2, file.getName()); (3) ps.setBinaryStream(3, fis, (int)file.length()); (4) ps.executeUpdate(); … 3.3 完整程式碼 上面列出了完整的程式碼。 package com.forrest.storepic; import java.io.File; import java.io.FileInputStream; import java.sql.Connection; import java.sql.DriverManager; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; public class StorePictures {
 private String dbDriver;  private String dbURL;  private String dbUser;  private String dbPassword;  private Connection con;  private PreparedStatement ps;   public StorePictures() {  dbDriver = "com.mysql.jdbc.Driver";  dbURL = "jdbc:mysql://localhost:3306/test";  dbUser = "root";  dbPassword = "admin";  initDB();  }  public StorePictures(String strDriver, String strURL,  String strUser, String strPwd) {  dbDriver = strDriver;  dbURL = strURL;  dbUser = strUser;  dbPassword = strPwd;  initDB();  }  public void initDB() {  try {  // Load Driver  Class.forName(dbDriver).newInstance();  // Get connection  con = DriverManager.getConnection(dbURL,  dbUser, dbPassword);   } catch(ClassNotFoundException e) {  System.out.println(e.getMessage());  } catch(SQLException ex) {  // handle any errors  System.out.println("SQLException: " + ex.getMessage());  System.out.println("SQLState: " + ex.getSQLState());  System.out.println("VendorError: " + ex.getErrorCode());  } catch (Exception e) {  System.out.println(e.getMessage());  }  }  public boolean storeImg(String strFile) throws Exception {  boolean written = false;  if (con == null)  written = false;  else {  int id = 0;  File file = new File(strFile);  FileInputStream fis = new FileInputStream(file);  try {   ps = con.prepareStatement("SELECT MAX(idpic) FROM PIC");  ResultSet rs = ps.executeQuery();  if(rs != null) {  while(rs.next()) {  id = rs.getInt(1)+1;  }  } else {   return written;  }  ps = con.prepareStatement("insert "  + "into PIC values (?,?,?)");  ps.setInt(1, id);  ps.setString(2, file.getName());  ps.setBinaryStream(3, fis, (int) file.length());  ps.executeUpdate();  written = true;  } catch (SQLException e) {  written = false;  System.out.println("SQLException: "  + e.getMessage());  System.out.println("SQLState: "