简体   繁体   English

如何将BLOB数组传递给存储的oracle过程?

[英]How to pass an array of BLOB to a stored oracle procedure?

I am allowing user to upload multiple files to my database. 我允许用户将多个文件上传到我的数据库。 These file contents must be stored in my oracle database as BLOB. 这些文件内容必须作为BLOB存储在我的oracle数据库中。

How can i write a oracle procedure to do this ? 我如何编写一个oracle过程来做到这一点? (I have a little knowledge of Oracle stored procedures) ? (我对Oracle存储过程有一点了解)?

Once this is done how can i use the stored procedure in java using jdbc's CallableStatement ? 完成此操作后,如何使用jdbc的CallableStatement在Java中使用存储过程?

Please help. 请帮忙。

First of all, you have to create the type that will contain the table of BLOB: 首先,您必须创建将包含BLOB表的类型:

CREATE OR REPLACE TYPE tab_blobs AS TABLE OF BLOB;

In Java, you have to rely on the STRUCT type provided by Oracle sql. 在Java中,您必须依靠Oracle sql提供的STRUCT类型。 You will create a STRUCT that will contain the array of BLOB to store into the DB. 您将创建一个STRUCT,其中包含要存储到数据库中的BLOB数组。

The code would look like the following: 该代码如下所示:

import java.sql.Connection;
import java.sql.SQLException;

import oracle.jdbc.driver.OracleDriver;
import oracle.sql.ARRAY;
import oracle.sql.ArrayDescriptor;
import oracle.sql.STRUCT;
import oracle.sql.StructDescriptor;

public class ArrayDemo
{

    public static void passArray()
        throws SQLException
    {
        Connection conn = new OracleDriver().defaultConnection();

        byte[] fileInByteArray = "value".getBytes();
        StructDescriptor itemDescriptor = StructDescriptor.createDescriptor("BLOB", conn);

        Object[] itemAtributes = new Object[] {};
        STRUCT itemObject1 = new STRUCT(itemDescriptor, conn, itemAtributes);

        itemAtributes = new Object[] {};
        STRUCT itemObject2 = new STRUCT(itemDescriptor, conn, itemAtributes);

        STRUCT[] idsArray = { itemObject1, itemObject2 };

        ArrayDescriptor descriptor = ArrayDescriptor.createDescriptor("IDS_TABLE", conn);

        ARRAY array_to_pass = new ARRAY(descriptor, conn, idsArray);

        OraclePreparedStatement ps = (OraclePreparedStatement) conn.prepareStatement("begin getInfo(:x); end;");

        ps.setARRAY(1, array_to_pass);
        ps.execute();

    }
}

But why don't you simplify the handling by iterating on the files, inserting them one after the other: 但是为什么不通过遍历文件,一个接一个地插入它们来简化处理:

public static void insererBlob(String name, String path) {
   File file = new File(path);
   try{
      //link to DB
      Connection connection = DriverManager.getConnection("url","user","password");

      //link to file
      FileInputStream stream = new FileInputStream(file);

      //prepare the SQL instruction
      String sql = "INSERT INTO file_table VALUES (?, ?)";
      PreparedStatement statement = connection.prepareStatement(sql);

      //blob insertion
      statement.setString(1, name);
      statement.setBinaryStream(2, stream, (int)file.length());
      statement.executeUpdate();

    }catch(Exception e){
       //ERROR SQL, IO, etc .
    }finally {
       //close connection ?
    }
}

详细信息可以在此链接找到, 使用Oracle数据库进行文件的装卸

Here is another attempty to help you. 这是另一种尝试来帮助您。 You can find more info from oracle here: http://docs.oracle.com/cd/B28359_01/java.111/e10788/connect.htm#CHDGHFCG http://docs.oracle.com/javase/tutorial/jdbc/basics/ 您可以在此处从oracle找到更多信息: http : //docs.oracle.com/cd/B28359_01/java.111/e10788/connect.htm#CHDGHFCG http://docs.oracle.com/javase/tutorial/jdbc/基本/

Also, example taken from (website of great help at the time i had to do it): http://docs.oracle.com/javase/tutorial/jdbc/basics/blob.html 另外,示例取自(我不得不这样做的时候在我的网站上提供了很大帮助): http : //docs.oracle.com/javase/tutorial/jdbc/basics/blob.html

public void addRowToCoffeeDescriptions(
    String coffeeName, String fileName)
    throws SQLException {

    PreparedStatement pstmt = null;
    try {
        Clob myClob = this.con.createClob();
        Writer clobWriter = myClob.setCharacterStream(1);
        String str = this.readFile(fileName, clobWriter);
        System.out.println("Wrote the following: " +
            clobWriter.toString());

        if (this.settings.dbms.equals("mysql")) {
            System.out.println(
                "MySQL, setting String in Clob " +
                "object with setString method");
            myClob.setString(1, str);
        }
        System.out.println("Length of Clob: " + myClob.length());

        String sql = "INSERT INTO COFFEE_DESCRIPTIONS " +
                     "VALUES(?,?)";

        pstmt = this.con.prepareStatement(sql);
        pstmt.setString(1, coffeeName);
        pstmt.setClob(2, myClob);
        pstmt.executeUpdate();
    } catch (SQLException sqlex) {
        JDBCTutorialUtilities.printSQLException(sqlex);
    } catch (Exception ex) {
      System.out.println("Unexpected exception: " + ex.toString());
    } finally {
        if (pstmt != null)pstmt.close();
    }
}

Below is my code hope you got your answer: 以下是我的代码,希望您能得到答案:

  1. from java code: 从Java代码:

      try {Class.forName("oracle.jdbc.driver.OracleDriver"); String url = "jdbc:oracle:thin:@localhost:1521:orcl"; Connection con = DriverManager.getConnection(url, db_user, password); System.out.println("Connected to database"); SimpleDateFormat simpleDateFormat = new SimpleDateFormat("dd/MM/yyyy"); Date now = new java.sql.Date(simpleDateFormat.parse("12/02/2001").getTime()); String command2 = "{call USER1(?,?,?,?)}"; String path; File[] roots = File.listRoots(); path=roots[0].getPath()+"dfg.jpg"; System.out.println("path: " + path); //shows drives in you computer for(int i = 0; i < roots.length ; i++){ System.out.println("drive: " + roots[i].getPath()); } CallableStatement insertStatment = con.prepareCall(command2); insertStatment.setInt(1, 18); insertStatment.setString(2, "ankssaait"); insertStatment.setDate(3, now); File file = new File(path); //link to file FileInputStream stream = new FileInputStream(file); insertStatment.setBinaryStream(4, stream,(int)file.length());; System.out.println("onExecute: "+ insertStatment.executeUpdate()); insertStatment.close(); System.out.println("done"); } catch (Exception e) { e.printStackTrace(); } 
  2. my tablei is: 我的桌子是:

    CREATE TABLE "ANKIT"."O_USER" ( "NAME" VARCHAR2(20 BYTE), "GENDER" CHAR(1 BYTE), "DESIGNTION" VARCHAR2(20 BYTE), "YEAR" INTERVAL YEAR (2) TO MONTH, "ID" NUMBER NOT NULL ENABLE, "DOB" DATE, "PROOF" CLOB, "ADDRESS" VARCHAR2(100 BYTE), "TELEPHONE" NUMBER, "RAW1" RAW(20), "IMAGE" BLOB, CONSTRAINT "O_USER_PK" PRIMARY KEY ("ID")); 创建表“ ANKIT”。“ O_USER”(“名称” VARCHAR2(20 BYTE),“ GENDER” CHAR(1 BYTE),“ DESIGNTION” VARCHAR2(20 BYTE),“ YEAR”间隔年(2)到MONTH,“ ID “ NUMBER NOT NULL ENABLE,” DOB“日期,” PROOF“ CLOB,” ADDRESS“ VARCHAR2(100 BYTE),” TELEPHONE“ NUMBER,” RAW1“ RAW(20),” IMAGE“ BLOB,CONSTRAINT” O_USER_PK“主键( “ID”));

  3. my procedure is: 我的程序是:

     CREATE OR REPLACE PROCEDURE USER1 (U_ID IN o_user.id%TYPE, U_NAME in o_user.name%TYPE, u_DOB in o_user.dob%TYPE, u_image in o_user.image%TYPE) AS BEGIN insert into o_user(id,name,dob,image) values(u_id,u_name,u_dob,u_image); END USER1; 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM