spring,hibernate處理Lob類型數據

Lob代表大對象數據,包括BLOB和CLOB兩種類型數據,前者用於存儲大塊的二進制數據,如圖片和視頻數據等,而後者用於存儲長文本數據,如論壇帖子內容,產品詳細描述等。在不同的數據庫中,大對象對應的字段類型往往不一樣,如oracle對應的是BLOB/CLOB;Mysql對應的BLOB/LONGTEXT;SQLSERER對應IMAGE/TEXT,有些數據庫對大對象類型可以像簡單類型一樣訪問,如mysql的LONGTEXT的操作方式和VARCHAR類型一樣,在一半情況下,LOB類型數據的訪問不同於其他簡單類型的數據,用戶可能會以流的方式操作LOB類型的書。此外,LOB類型的數據訪問並不是線程安全的,需要分配相應的數據庫資源,並在操作後完成釋放。最後oracle非常有個性地採用非jdbc標準的api操作lob數據,spring爲此在org.springframework.jdbc.support.lob包中提供幫助類


LobCreator

雖然jdbc定義了兩個操作LOB類型的接口:java.sql.BLOB,java.sql.CLOB,但是有些廠商的jdbc驅動程序並不支持這兩個接口。爲此,spring定義了一個獨立於java.sql.blob/java.sql.clob接口,以統一的方式操作各種數據庫LOB類型的lobCreator接口,因爲LobCreator本身執有Lob所對應的數據庫資源,所以它不是線程安全,一個LOBcREATOR只能操作一個Lob數據


LobCreator接口對應的方法

void close();關閉會話,並釋放Lob資源

void setBlobAsBinaryStream(PreparedStatement ps,int paramIndex,InputStream,int contentLength)通過流填充Blob數據

void setBlobAsBytes(PreparedStatement ps,int paramIndex,byte[] content);通過二進制填充Blob數據

void setClobAsCharacterStream(PreparedStatement ps,int paramIndex,Reader characterStream,int contentLength);通過Unicode字符流填充clob數據

void setClobAsAsciiStream(PreparedStatement ps,int paramIndex,InputStream asciiStream,int contentLength);通過Ascii字符流填充clob數據

void setClobAsStream(PreparedStatement ps,int paramIndex,String content)  通過字符串填充clob數據


LobHandler

lobhandler接口爲操作大二進制字段和大文本字段提供統一的訪問接口訪問,不管底層數據庫是以大對象的方式還是一般數據類型進行操作,lobhandler還充當了lobcreator的工廠類

InputStream getBlobAsBinaryStream(ResultSet rs,int columnIndex)從結果集中返回InputStream,通過InputStream讀取Blob數據

byte[] getBlobAsBytes(ResultSet rs,int columnIndex);以二進制數據的方式讀取結果集中的Blobshuju

InputStream getClobAsAssciiStream(ResultSet rs,int columnIndex)從結果集中返回InputStream,通過InputStream 以Asscii字符流方式讀取Blob數據

Reader getClobAsCharacterStream(ResultSet rs,int columnIndex);從結果集中獲取Unicode字符流Reader,並通過Reader以Unicode字符流方式讀取Clob數據

getClobAsStream(ResultSet rs,int columnIndex)會從結果集中以字符串的方式獲取clob數據


xml配置文件

<bean id="lobHandler" class="org.springframework.jdbc.support.lob.DefaultLobHandler" lazy-init="true"/>

測試類

@Test
	public void handle14() throws IOException{
		File file = new File("F:\\e.png");
		
		final byte[] mockImg = FileCopyUtils.copyToByteArray(file);
		
		String sql = "insert into tb_content(image)values(?)";
		jdbcTemplate.execute(sql, new AbstractLobCreatingPreparedStatementCallback(lobHandler) {
			
			@Override
			protected void setValues(PreparedStatement ps, LobCreator lobCreator)
					throws SQLException, DataAccessException {
				
				lobCreator.setBlobAsBytes(ps, 1, mockImg);
			}
		});
	} 


@Test
	public void handle15() throws IOException{
		final File file = new File("F:\\d.png");
		
		
		String sql = "select * from tb_content where id=3";
		jdbcTemplate.query(sql, new RowMapper(){

			@Override
			public Object mapRow(ResultSet rs, int arg1) throws SQLException {
				byte[] attach = lobHandler.getBlobAsBytes(rs, 1);
				try {
					FileOutputStream outputStream = new FileOutputStream(file);
					try {
						outputStream.write(attach, 0, attach.length);
					} catch (IOException e) {
					
						e.printStackTrace();
					}
				} catch (FileNotFoundException e) {
				
					e.printStackTrace();
				}
				
				return null;
			}
			
		});
	} 
}


spring+hibernate處理Blob類型的數據

實體類

@Entity(name = "tb_news")
public class NewsContent {
	
	private Integer id;
	private byte[] photo;
	public NewsContent(){}
	public NewsContent(Integer id){
		this.id = id;
	}
	
	@Id
	@GeneratedValue(strategy=GenerationType.IDENTITY)
	@Column(name = "id")
	public Integer getId() {
		return id;
	}
	public void setId(Integer id) {
		this.id = id;
	}
	
	@Column(name ="photo",columnDefinition="longblob")
	public byte[] getPhoto() {
		return photo;
	}
	public void setPhoto(byte[] photo) {
		this.photo = photo;
	}
	
	
	
	
}

測試:

@Test
	public void handle2() throws IOException{
		NewsContent content = new NewsContent();
		File file = new File("F:\\e.png");
		byte[] bytes = FileUtils.readFileToByteArray(file);
		content.setPhoto(bytes);
		Session session = sessionFactory.openSession();
		session.save(content);
	}
	
	@Test
	public void handle3() throws IOException{
		
		File file = new File("F:\\e.png");
		
		FileOutputStream out = new FileOutputStream(file);
		Session session = sessionFactory.openSession();
		NewsContent content = (NewsContent)session.get(NewsContent.class, 1);
		byte[] bytes = content.getPhoto();
		out.write(bytes, 0, bytes.length);
		
	
	}


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章