`
log_cd
  • 浏览: 1098623 次
  • 性别: Icon_minigender_1
  • 来自: 成都
社区版块
存档分类
最新评论

oracle blob数据存取

阅读更多
    Oracle中的lob (Large Object)可以存储非常大的数据(可能是4GB),这样就可以通过将文件或其它任何对象序列化成字节输出流(OutputStream)后写入数据库,之后使用字节输入流(InputStream)将数据读出然后反序列化为原始文件或对象。操作时需要使用oracle的JDBC包,它扩展了sun的JDBC包中的Blob对象。
    以下是一个保存图片进数据库的例子:
1.servlet:用于保存图片并将图片输出
package com.logcd.servlet;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.sql.CallableStatement;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.sql.Types;
import java.util.Iterator;
import java.util.List;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import oracle.sql.BLOB;

import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;

public class ImageServlet extends HttpServlet {

	private static final long serialVersionUID = 1L;

	/**
	 * 处理请求
	 * @throws FileUploadException
	 */
	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {

		Iterator<FileItem> i = getFileItem(request);
		String title = "";
		byte[] data = null;

		while (i.hasNext()) {
			FileItem fi = (FileItem) i.next();
			if (fi.isFormField()) {// 取得表单域
				if(fi.getFieldName().equalsIgnoreCase("title")){
                              title = new String(fi.getString().getBytes("iso8859-1"),"gbk");
					}
			} else {// 取文件域
				data = fi.get();//文件二进制数据
			}
		}

		Integer id = saveImageUseProc(data,title);//saveImage(data, title);//存入 
		//outputImage(response, id);//读出
		outputImageUseProc(response,id);
	}

	public void doGet(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		doPost(request, response);
	}

	/**
	 * 通过SQL保存图片
	 * @param data
	 * @param title
	 */
	@SuppressWarnings("deprecation")
	public static Integer saveImage(byte[] data, String title) {
		Connection conn = getConnection();
		Integer id = (int) (Math.random() * 100000);
		String sql = "insert into t_image(id,title,image) values(" + id + ",'"
				+ title + "',empty_blob())";
		Statement stmt;
		OutputStream outStream = null;
		try {
			conn.setAutoCommit(false);// 如果不关闭会报-->"错误:读取违反顺序"

			stmt = conn.createStatement();
			stmt.execute(sql);

			String sqll = "select image from t_image where id=" + id
					+ " for update";

			ResultSet rs = stmt.executeQuery(sqll);
			if (rs.next()) {
				BLOB blob = (BLOB) rs.getBlob("image");
				outStream = blob.getBinaryOutputStream();
				// data是传入的byte数组,定义:byte[] data
				outStream.write(data, 0, data.length);

				outStream.flush();
				outStream.close();
				conn.commit();
			}
		} catch (Exception e) {
			try {
				conn.rollback();
			} catch (SQLException e1) {
				e1.printStackTrace();
			}
			e.printStackTrace();
		} finally {
			try {
				conn.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}
		}
		return id;

	}

	/**
	 * 调用存储过程保存图片
	 * @param data
	 * @param title
	 * @return
	 */
	@SuppressWarnings("deprecation")
	public static Integer saveImageUseProc(byte[] data, String title){
		Integer id = null;
		BLOB blob = null;
		OutputStream outStream;
		Connection conn = getConnection();
		try{
			conn.setAutoCommit(false);
			String call="{call OPERATE_BLOB.SAVE_BLOB_IMAGE(?,?,?)}";//调用语句
		    CallableStatement proc=conn.prepareCall(call);//调用存储过程
            proc.setString(1, title);
            proc.registerOutParameter(2, Types.BLOB);
		    proc.registerOutParameter(3, Types.INTEGER); 
            
            proc.execute();
            
            blob = (BLOB)proc.getBlob(2);
            id = proc.getInt(3);//返回结果

			outStream = blob.getBinaryOutputStream();
			outStream.write(data, 0, data.length);
			outStream.flush();
			outStream.close();
            
			proc.close();
            conn.commit();
		}catch(Exception e){
			e.printStackTrace();
		}finally{
			try {
				conn.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}
		}
		
		return id;
	}

	/**
	 * 输出保存的图片
	 * @param response
	 * @param id
	 */
	public static void outputImage(HttpServletResponse response, Integer id) {
		Connection con = getConnection();
		byte[] data = null;
		try{
			Statement st = con.createStatement();
			ResultSet rs = st.executeQuery("select image from t_image where id="
					+ id);
			if (rs.next()) {
				BLOB blob = (BLOB)rs.getBlob("image");
				InputStream inStream = blob.getBinaryStream();
				int bufferSize = blob.getBufferSize();
				data = new byte[bufferSize];
				int count = inStream.read(data, 0, bufferSize);
				while(count != -1){//读出字节数据
					response.getOutputStream().write(data,0,count);
					count = inStream.read(data, 0, bufferSize);
				}
				inStream.close();
			}
		}catch(Exception e){
			e.printStackTrace();
		}finally{
			try {
				con.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}

		}
	}

	/**
	 * 调用存储过程输出图片
	 * @param response
	 * @param id
	 */
	public static void outputImageUseProc(HttpServletResponse response, Integer id){
		Connection conn = getConnection();
        try{
        	String call = "{call OPERATE_BLOB.QUERY_BLOB_IMAGE(?,?)}";
		    CallableStatement proc=conn.prepareCall(call);//调用存储过程
            
		    proc.setInt(1, id);
		    proc.registerOutParameter(2, Types.BLOB);
		    
		    proc.execute();
		    
		    BLOB blob = (BLOB)proc.getBlob(2);
			
		    InputStream inStream = blob.getBinaryStream();
			int bufferSize = blob.getBufferSize();
			byte[] data = new byte[bufferSize];
			int count = inStream.read(data, 0, bufferSize);
			while(count != -1){//读出字节数据
				response.getOutputStream().write(data,0,count);
				count = inStream.read(data, 0, bufferSize);
			}
			inStream.close();
		    
        }catch(Exception e){
        	e.printStackTrace();
        }finally{
        	try {
				conn.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}
        }
	}
	
	/**
	 * 取得所有表单数据
	 * @param request
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public static Iterator<FileItem> getFileItem(HttpServletRequest request) {
		DiskFileItemFactory factory = new DiskFileItemFactory();
		factory.setSizeThreshold(4096); // 设置缓冲区大小,这里是4kb
		ServletFileUpload upload = new ServletFileUpload(factory);
		upload.setSizeMax(4194304); // 设置最大文件尺寸,这里是4MB

		List<FileItem> items = null;
		Iterator<FileItem> i = null;
		try {
			items = upload.parseRequest(request);
			i = items.iterator();
		} catch (FileUploadException e) {
			e.printStackTrace();
		}

		return i;
	}

	/**
	 * 取得数据库连接
	 * 
	 * @return
	 */
	public static Connection getConnection() {
		String driver = "oracle.jdbc.driver.OracleDriver";
		String url = "jdbc:oracle:thin:@195.2.199.6:1521:orcl";
		Connection conn = null;
		try {
			Class.forName(driver);
			conn = DriverManager.getConnection(url, "testdb", "logcd");
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		} catch (SQLException ex) {
			ex.printStackTrace();
		}
		return conn;
	}

}

2.所用到的存储过程
CREATE OR REPLACE PACKAGE BODY OPERATE_BLOB AS

  PROCEDURE  SAVE_BLOB_IMAGE(
      PC_TITLE  IN   VARCHAR2,
      PB_IMAGE  OUT   BLOB,
      PN_ID     OUT  INTEGER
    )AS
      v_id INTEGER;
  BEGIN   
       SELECT nvl(MAX(id),1000) + 1 INTO v_id FROM t_image; 
       PN_ID := v_id;
       INSERT INTO t_image(id,title,image) values(v_id,PC_TITLE,empty_blob())
       RETURNING image INTO PB_IMAGE;

  END;

  PROCEDURE QUERY_BLOB_IMAGE(
     PN_ID      IN   INTEGER,
     PB_IMAGE   OUT  BLOB
  )AS
  BEGIN
     SELECT image INTO PB_IMAGE FROM t_image WHERE id = PN_ID;  
  END;

END;


3.web.xml配置servlet
    <servlet>
        <servlet-name>ImageServlet</servlet-name>
        <servlet-class>com.logcd.servlet.ImageServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>ImageServlet</servlet-name>
        <url-pattern>/imageServlet</url-pattern>
    </servlet-mapping>

4.在image.html页面中调用下
<HTML>
	<HEAD>
		<TITLE>Image File</TITLE>
		<meta http-equiv="Content-Type" content="text/html; charset=gb2312">
	</HEAD>
	<FORM method="POST" encType="multipart/form-data" action="imageServlet">
		<INPUT type="text" name="title">
		<BR>
		<INPUT type="file" name="image">
		<BR>
		<INPUT type="submit" value="提交">
	</FORM>
	<BODY>
	</BODY>
</HTML>
分享到:
评论
1 楼 Larkin_chen 2012-05-29  
xiexie

相关推荐

    基于.NET的Oracle BLOB数据高效存取方法.pdf

    标题提到的“基于.NET的Oracle BLOB数据高效存取方法”是一种针对Oracle数据库中BLOB类型数据存储和读取的优化策略。BLOB(Binary Large Object)是Oracle数据库中用于存储大量二进制数据的对象,常用于保存图像、...

    Oracle,Clob,Blob数据存取的Java代码

    以下是对Oracle中Clob和Blob数据存取的Java代码示例及详细解释。 首先,确保你的项目已经引入了Oracle JDBC驱动(如ojdbc.jar)。然后,你需要创建一个与Oracle数据库的连接,这通常通过`DriverManager.get...

    BLOB数据存取

    在本主题中,我们将详细探讨如何使用ADO(ActiveX Data Objects)在VC++环境中对BLOB数据进行存取操作。 1. **什么是ADO?** ADO是微软开发的一种数据访问接口,它提供了与各种数据源(如SQL Server、Oracle等)...

    Oracle在PB中用OLE存取blob类型数据[归类].pdf

    "Oracle在PB中用OLE存取blob类型数据" Oracle是在PowerBuilder(PB)中使用OLE存取Blob类型数据的解决方案。该解决方案主要涉及到PB中使用OLE存取Blob类型数据的方法,包括建立数据库表、创建PB库、设置数据库连接...

    在Oracle数据表中存取BLOB数据的方法研究.pdf

    在Oracle数据库中,BLOB字段可以用来存储不规则的大数据文件,比如文档和图像等,它能以二进制的形式存储大量字符型数据。 BLOB的存储优势主要体现在两个方面:便于管理和高可用性。因为BLOB数据与其它数据库表数据...

    在C中存取Oracle数据库表中BLOB数据的方法研究.pdf

    在C中存取Oracle数据库表中BLOB数据的方法研究.pdf

    Struts2 Hibernate存取Oracle数据库中的BLOB数据.pdf

    - BLOB(二进制大对象):用于存储大型二进制数据,如影像、图片等,其长度可达4GB,支持随机存取。 - BFILE:虽然用于存储大型二进制数据,但数据实际存储在文件系统中,数据库中仅存储指向文件的指针,Oracle对...

    Java存取OracleBlob字段,图片存储,Blob和BLOB的问题,Clob,oracle.docx

    ### Java存取Oracle Blob 字段详解 #### 一、Blob 和 BLOB 的区别 在处理 Oracle 数据库中的二进制大型对象(Binary Large Object,简称 Blob)时,开发者经常会遇到两个相似但不同的概念:`java.sql.Blob` 和 `...

    oracle存取图片blob字段

    oracle 存读数据库的blob字段 .net有两种方式向Oracle的blob字段中存储图片:

    在Oracle中存取BLOB对象实现文件的上传和下载.txt

    ### 在Oracle中存取BLOB对象实现文件的上传和下载 #### 核心知识点解析: **一、BLOB数据类型简介** BLOB(Binary Large Object)是数据库中的二进制大对象类型,主要用于存储大量二进制数据,如图像、音频、视频等...

    图片存入Oracle中,用clob和blob两种方式

    在数据库管理中,存储非结构化数据如图片、音频或视频文件时,通常会使用`CLOB`(Character Large Object)和`BLOB`(Binary Large Object)这两种数据类型。Oracle数据库系统支持这两种数据类型,用于存储大量文本...

    oracle,weblogic读写blob

    Oracle 和 WebLogic 服务器在处理 BLOB(Binary Large Object)数据类型时,涉及的是数据库管理和Web应用程序中的数据存储与检索。BLOB 类型通常用于存储大量二进制数据,如图片、音频或视频文件。本篇文章将深入...

    绝对好用!extjs中本地照片预览、blob数据在oracle中存取.zip

    并且此资料夹最后的版本可以将文件从extjs以数据流的形式传输到servlet,在后台存储blob数据,并且将blob数据从oracle数据库展示在extjs页面。没有完全实现的是extjs用uploadfild控件实现的blob数据上传预览,并且...

    extjs中本地照片预览、blob数据在oracle中存取

    此压缩包中完全能实现的功能是在extjs中让本地照片预览,并且将地址传递给java后台,将图片文件以blob的形式存储到oracle数据库,并且可以默认将数据库中的数据第一次加载在预览框里(也就是从数据库中读出blob数据...

    DELPHI的CLOB和BLOB存取处理.zip_DELPHI的CLOB和BLOB存取处理_hallzgz

    本篇文章将深入探讨DELPHI中如何有效地进行CLOB和BLOB的存取处理。 CLOB主要用来存储大文本数据,如长篇文章、XML文档或JSON字符串,而BLOB则用于存储大量的二进制数据,如图像、音频、视频文件或者任何非文本的...

    c#Blob图片在oracle上读取、保存、上传

    c#-操作数据库oracle的小代码,提供用于学习。代码主要实现从oracle读取、保存、上传图片等功能,使用了Oracle.DataAccess.dll,想了解相关知识的欢迎下载,有问题的请给我留言,谢谢。

    Excel文件在Oracle上的存取技术.pdf

    总之,《Excel文件在Oracle上的存取技术》一文详细阐述了如何利用Oracle数据库的BLOB类型和ADO技术,实现Excel文件的高效存储和检索,对于需要处理大量Excel数据的系统设计具有重要的参考价值。这种技术的应用可以...

    Oracle数据库大对象数据存取的两种实现方法及时间性能比较.pdf

    部分内容中,作者首先介绍了Oracle中的大对象数据分类,包括字符类型(CLOB和NCLOB)和二进制类型(BLOB),以及BFILE类型,后者存储在操作系统文件中。接着,讨论了两种存取方式:数据存储在内部表空间和指向操作...

    Oracle数据库图像存取技术.pdf

    Oracle数据库提供了一种处理大型二进制数据对象的数据类型——Blob(Binary Large Object,二进制大对象),这对于处理图像数据显得尤为重要。 在Oracle数据库中,图像数据通常采用lob型字段进行存取。lob型数据是...

    Oracle,SQL2000,MYSQL存取图片或二进制数据的功能文件

    Oracle数据库使用BLOB(Binary Large Object)数据类型来存储图片或任何其他二进制数据。BLOB类型可以存储最大4GB的数据,足以容纳大多数图像文件。`OracleUploader.java`可能是一个Java程序,用于上传图片或二进制...

Global site tag (gtag.js) - Google Analytics