Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

returning a result set from a java stored procedure through SQL "select * from "

Can I get the result from a java stored procedure (oracle) directly through an SQL select * from statement ?

On the database I would have a java stored procedure / function, which when it called returns a multi-column, multi-row result set.
I would like to access these results directly through a select * from [table] statement.

So the java stored procedure should behave like a table.
In MySQL the following should be possible (but not java stored procedures): SELECT col1 FROM (EXEC proc1)

Is this possible in oracle where proc1 is a java stored procedure?

like image 675
Ruben S. Avatar asked Apr 21 '11 07:04

Ruben S.


People also ask

Can we return ResultSet in Java?

Yes, just like any other objects in Java we can pass a ResultSet object as a parameter to a method and, return it from a method.


1 Answers

This answer on a different forum may help you.

Look at the sample in the bottom of the message to see how to select from a collection returned by a Java method ( that may also be a Java Stored Procedure).

Here is a sample on how to do it with Java Stored Procedure

1) Create DB object to define the type of the returned rows:

create type try_obj as object (
        field_a number,
        field_b varchar2(10)
    )
/

create type try_obj_tab as table of try_obj
/

2) Create the Java class on the DB with a static method(GetSampleResult) that returns a Collection

create or replace and compile java source named QueryReturn as
import java.sql.*;
import java.util.*;

import oracle.jdbc.*;
import oracle.jdbc.pool.OracleDataSource;
import oracle.sql.*;


public class QueryReturn implements ORADataFactory,ORAData{
    private NUMBER field1;
    private CHAR field2;

    public QueryReturn(OracleConnection conn,int n,String c) throws SQLException {
        field1 = new NUMBER(n);
        field2 = new CHAR(c,oracle.sql.CharacterSet.make(conn.getStructAttrCsId()));
    }

    public QueryReturn(NUMBER n, CHAR c) {
        field1 = n;
        field2 = c;
    }
    public QueryReturn(Object[] attributes) {
        this(
                (NUMBER) attributes[0],
                (CHAR) attributes[1]
            );
    }
    public QueryReturn(Datum d) throws SQLException {
        this(((STRUCT) d).getOracleAttributes());
    }

    public ORAData create(Datum d, int sqlType) throws SQLException {
        if (d == null)
            return null;
        else {
            return new QueryReturn(d);
        }
    }

    public STRUCT toSTRUCT(Connection conn) throws SQLException  {
        StructDescriptor sd =
            StructDescriptor.createDescriptor("TRY_OBJ", conn);
        Object [] attributes = { field1,field2 };
        return new STRUCT(sd, conn, attributes);
    }
    public Datum toDatum(Connection conn) throws SQLException {
        return toSTRUCT(conn); 
    }


    public static ARRAY GetSampleResult() throws SQLException, ClassNotFoundException {
        // initialize the connection
        OracleConnection conn = null;
        conn = (OracleConnection) (new oracle.jdbc.OracleDriver()).defaultConnection();

        // create the return java array
        // There will be two Rows
        //  1   abc
        //  2   dce
        QueryReturn javaArray[] = {
                new QueryReturn(conn,1,"abc"),
                new QueryReturn(conn,2,"dce")
            };

        // Map the java class to the Oracle type
        Map map = conn.getTypeMap();
        map.put("TRY_OBJ", Class.forName("QueryReturn"));
        ArrayDescriptor jTryObjArrayDesc = ArrayDescriptor.createDescriptor (
                "TRY_OBJ_TAB",
                conn
            );


        // create an Oracle collection on client side to use as parameter
        ARRAY oracleCollection = new ARRAY(jTryObjArrayDesc,conn,javaArray);

        return oracleCollection;
    }
}

3) Create the Wrap to use Java Stored Procedure in a function

create or replace function GetSampleResult 
    return try_obj_tab
AS LANGUAGE JAVA
    NAME  'QueryReturn.GetSampleResult()  return oracle.sql.ARRAY';

4) Show the result

SQL> select *
  2  from table(GetSampleResult())
  3  /

   FIELD_A FIELD_B
---------- ----------
         1 abc
         2 dce

SQL>
like image 184
Alessandro Rossi Avatar answered Sep 19 '22 15:09

Alessandro Rossi