<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    MDA/MDD/TDD/DDD/DDDDDDD
    posts - 536, comments - 111, trackbacks - 0, articles - 0
      BlogJava :: 首頁 :: 新隨筆 :: 聯系 :: 聚合  :: 管理

    java調oracle存儲過程

    Posted on 2009-08-12 11:46 leekiang 閱讀(1415) 評論(2)  編輯  收藏 所屬分類: oraclejdbc、事務、并發
    ??????? OracleCallableStatement cst = null;
    ?? ??? ?int oracleId = CharacterSet.ZHS16GBK_CHARSET;
    ?? ??? ?oracle.sql.CharacterSet dbCharset = oracle.sql.CharacterSet.make(oracleId);
    ?? ??? ??? ?cst = (OracleCallableStatement) conn
    ?? ??? ??? ??? ??? ?.prepareCall("begin ?:= pkg_test.f_getList(?); end;");
    //String sql = "{?=call PckgStudSltCourse.addStudPreSltCourse(?,?,?,?)}";也可以這樣寫
    //sql="{call sp(?,?,?,?,?)}";//如果無返回值
    ?? ??? ??? ?cst.registerOutParameter(1, OracleTypes.ARRAY, "T_ARRAY");//第一個問號表示返回結果
    ?? ??? ??? ?cst.setString(2, userid);//第二個問號
    ?? ??? ??? ?cst.executeUpdate();//哪怕是個查詢也用executeUpdate

    ?? ??? ??? ?oracle.sql.ARRAY simpleArray = cst.getARRAY(1);//從statement獲取,而不是rs
    ?? ??? ??? ?String[] values = (String[]) simpleArray.getArray();
    ?? ??? ??? ?for (int i = 0; i < values.length; i++) {
    ?? ??? ??? ??? ?oracle.sql.CHAR out_value = new oracle.sql.CHAR(values[i],dbCharset);
    ?? ??? ??? ??? ?System.out.println(out_value.stringValue());
    ?? ??? ??? ?}
    ?? ??? ??? ?
    注意:在new oracle.sql.CHAR處,可能會報
    java.lang.NoClassDefFoundError: oracle/gss/util/NLSError
    ?? ?at oracle.sql.CharacterSetUnknown.failCharsetUnknown(CharacterSetFactoryThin.java:178)
    ?? ?at oracle.sql.CharacterSetUnknown.convert(CharacterSetFactoryThin.java:145)
    ?? ?at oracle.sql.CHAR.(CHAR.java:147)
    ?? ?即missing some jar file in runtime environment
    ?? ?原因是weblogic沒有加載web應用下的classes12.jar,而是加載了weblogic81\server\lib里的ojdbc14.jar,
    ?? ?而ojdbc14.jar里沒有oracle.gss.util.NLSError。
    ?? ?修改classpath先加載classes12.jar,打印出來的是亂碼,只出現亂碼,這次沒有出現類似這樣的異常java.sql.SQLException:?? Non?? supported?? character?? set:?? oracle-character-set-850? 。
    ?? ?還需要修改classpath先加載nls_charset12.jar;(必須這樣,光放在web應用的lib下或光放在weblogic81\server\lib都
    ?? ?不行,jar包放置或加載的這三種方式是有區別的)
    問題:如果使用的是ojdbc.jar,我覺得可能就不要nls_charset12.jar了,并且不需要new oracle.sql.CHAR(values[i],dbCharset)來轉換
    ?? ?
    http://topic.csdn.net/t/20051110/17/4385336.html
    ?? ?類是通過類加載器classloader載入的。 ?
    ? 缺省情況下web容器遵循java的標準標準類載入機制?? --?? 由現載入父加載器level的類。 ?
    ? weblogic的web容器的classloader繼承自ejb容器的classloader,ejb容器的classloader又繼承自 application?? classloader--該loader負責加載classpath下面的類,所以缺省情況下classpath下面的類會被優先載入,即使相同的類存在于web應用的lib目錄。 ?
    ? 可以通過配置文件來修改這種加載順序,使得lib目錄中的類得到優先調用,在weblogic?? 8.1中,方法是在weblogic.xml中加入下面的代碼段: ?
    ? <container-descriptor> ?
    ? <prefer-web-inf-classes>true</prefer-web-inf-classes> ?
    ? </container-descriptor>? ?
    ? weblogic?? 的加載順序就是weblogic?? classpath優先?
    ?
    ?
    ? 一下見http://www.javaeye.com/topic/21141
    ? ClassNotFoundException發生在裝入階段。
    當應用程序試圖通過類的字符串名稱,使用常規的三種方法裝入類,但卻找不到指定名稱的類定義時就拋出該異常。

    NoClassDefFoundError: 當目前執行的類已經編譯,但是找不到它的定義時

    也就是說你如果編譯了一個類B,在類A中調用,編譯完成以后,你又刪除掉B,運行A的時候那么就會出現這個錯誤
    當你使用字符串去轉換類,也就是嘗試使用Class.forName等方法去獲得一個類的時候,如果這個類不存在,就會拋出ClassNotFoundException。
    ?? 而你編譯的類無錯,但是在運行時刻,缺乏某些必須的類時,就是拋出NoClassDefFoundError。這種情況最常見就是你在編譯時,在classpath下有這個類,但是在運行時,你的classpath缺少這個類。
    ? ?
    ? 加載時從外存儲器找不到需要的class就出現ClassNotFoundException
    ? 連接時從內存找不到需要的class就出現NoClassDefFoundError
    ? 問題:加載和連接的區別

    創建測試用表

    CREATETABLE T_TEST(
    I_ID
    NVARCHAR(20),
    I_NAME
    NVARCHAR(20)
    )

    一:無返回值的存儲過程

    1、建立存儲過程
    CREATE OR REPLACE PROCEDURE TESTA(PARA1 IN VARCHAR2,PARA2 IN VARCHAR2) AS
    BEGIN
    ?? INSERT INTO T_TEST (I_ID,I_NAME) VALUES (PARA1, PARA2);
    END TESTA;

    2、相應的JAVA程序
    import java.sql.*;
    import java.io.OutputStream;
    import java.io.Writer;
    import java.sql.PreparedStatement;
    import java.sql.ResultSet;
    import oracle.jdbc.driver.*;
    public class TestProcedureOne {
    ??? public TestProcedureOne() {
    ????? }
    ????? public static void main(String[] args ){
    ??????? String driver = "oracle.jdbc.driver.OracleDriver";
    ??????? String strUrl = "jdbc:oracle:thin:@192.168.10.216:1521:ctbu";
    ??????? Statement stmt = null;
    ??????? ResultSet rs = null;
    ??????? Connection conn = null;
    ??????? CallableStatement cstmt = null;
    ??????? try {
    ????????? Class.forName(driver);
    ????????? conn = DriverManager.getConnection(strUrl, "dbname", "password");
    ????????? CallableStatement proc = null;
    ????????? proc = conn.prepareCall("{ call dbname.TESTA(?,?) }");
    ????????? proc.setString(1, "100");
    ????????? proc.setString(2, "TestOne");
    ????????? proc.execute();
    ??????? }
    ??????? catch (SQLException ex2) {
    ????????? ex2.printStackTrace();
    ??????? }
    ??????? catch (Exception ex2) {
    ????????? ex2.printStackTrace();
    ??????? }
    ??????? finally{
    ????????? try {
    ??????????? if(rs != null){
    ????????????? rs.close();
    ????????????? if(stmt!=null){
    ??????????????? stmt.close();
    ????????????? }
    ????????????? if(conn!=null){
    ??????????????? conn.close();
    ????????????? }
    ??????????? }
    ????????? }
    ????????? catch (SQLException ex1) {
    ????????? }
    ??????? }
    ????? }
    ??? }

    二:有返回值的存儲過程(非列表)

    1、存儲過程為
    CREATE OR REPLACE PROCEDURE TESTB(PARA1 IN VARCHAR2,PARA2 OUT VARCHAR2) AS
    BEGIN
    ?? SELECT INTO PARA2 FROM TESTTB WHERE I_ID= PARA1;
    END TESTB;

    2、JAVA代碼
    public class TestProcedureTWO {
    public TestProcedureTWO() {
    }
    public static void main(String[] args ){
    ??? String driver = "oracle.jdbc.driver.OracleDriver";
    ??? String strUrl = "jdbc:oracle:thin:@192.168.10.216:1521:ctbu";
    ??? Statement stmt = null;
    ??? ResultSet rs = null;
    ??? Connection conn = null;
    ??? try {
    ????? Class.forName(driver);
    ????? conn = DriverManager.getConnection(strUrl, "dbname", "password");
    ????? CallableStatement proc = null;
    ????? proc = conn.prepareCall("{ call HYQ.TESTB(?,?) }");
    ????? proc.setString(1, "100");
    ????? proc.registerOutParameter(2, Types.VARCHAR);
    ????? proc.execute();
    ????? String testPrint = proc.getString(2);
    ????? System.out.println("=testPrint=is="+testPrint);
    ??? }
    ??? catch (SQLException ex2) {
    ????? ex2.printStackTrace();
    ??? }
    ??? catch (Exception ex2) {
    ????? ex2.printStackTrace();
    ??? }
    ??? finally{
    ????? try {
    ??????? if(rs != null){
    ????????? rs.close();
    ????????? if(stmt!=null){
    ??????????? stmt.close();
    ????????? }
    ????????? if(conn!=null){
    ??????????? conn.close();
    ????????? }
    ??????? }
    ????? }
    ????? catch (SQLException ex1) {
    ????? }
    ??? }
    }
    }
    }
    注意,這里的proc.getString(2)中的數值2并非任意的,而是和存儲過程中的out列對應的,如果out是在第一個位置,那就是 proc.getString(1),如果是第三個位置,就是proc.getString(3),當然也可以同時有多個返回值,那就是再多加幾個out 參數了。

    三:返回列表
    由于oracle存儲過程沒有返回值,它的所有返回值都是通過out參數來替代的,列表同樣也不例外,但由于是集合,所以不能用一般的參數,必須要用pagkage了.所以要分兩部分。
    1、在SQL*PLUS中建一個程序包

    CREATE OR REPLACE PACKAGE TESTPACKAGE AS
    TYPE Test_CURSOR IS REF CURSOR;
    procedure TESTC(cur_ref out Test_CURSOR);
    end TESTPACKAGE;

    建立存儲過程,存儲過程為:
    create or replace package body TESTPACKAGE as
    procedure TESTC(cur_ref out Test_CURSOR) is
    begin??
    OPEN cur_ref FOR SELECT * FROM T_TEST;
    end TESTC;
    END TESTPACKAGE;
    可以看到,它是把游標(可以理解為一個指針),作為一個out 參數來返回值的。
    JAVA程序如下:

    import java.sql.*;
    import java.io.OutputStream;
    import java.io.Writer;
    import java.sql.PreparedStatement;
    import java.sql.ResultSet;
    import oracle.jdbc.driver.*;

    public class TestProcedureOne {
    ??? public TestProcedureOne() {
    ????? }
    ????? public static void main(String[] args ){
    ??????? String driver = "oracle.jdbc.driver.OracleDriver";
    ??????? String strUrl = "jdbc:oracle:thin:@192.168.10.216:1521:ctbu";
    ??????? Statement stmt = null;
    ??????? ResultSet rs = null;
    ??????? Connection conn = null;
    ??????? CallableStatement cstmt = null;
    ??????? try {
    ????????? Class.forName(driver);
    ????????? conn = DriverManager.getConnection(strUrl,"databasename" "password");
    ????????? CallableStatement proc = null;
    ????????? proc = conn.prepareCall("{ call cqsb.TESTA(?,?) }");
    ????????? proc.setString(1, "100");
    ????????? proc.setString(2, "TestOne");
    ????????? proc.execute();
    ??????? }
    ??????? catch (SQLException ex2) {
    ????????? ex2.printStackTrace();
    ??????? }
    ??????? catch (Exception ex2) {
    ????????? ex2.printStackTrace();
    ??????? }
    ??????? finally{
    ????????? try {
    ??????????? if(rs != null){
    ????????????? rs.close();
    ????????????? if(stmt!=null){
    ??????????????? stmt.close();
    ????????????? }
    ????????????? if(conn!=null){
    ??????????????? conn.close();
    ????????????? }
    ??????????? }
    ????????? }
    ????????? catch (SQLException ex1) {
    ????????? }
    ??????? }
    ????? }
    ??? }

    特別注意:
    1、在執行前一定要先把oracle的驅動包放到class路徑里。
    2、Toad在我建立存儲過程中搞了很多莫名的錯誤,多數是沒有創建成功而不報錯,
    或者是創建有誤而不提示,應當引起重視。所以最好還是在SQL*PLUS玩這些。
    3、在SQL*PLUS中的換行是無效的,要換行的時候一定要空格結尾,特別是你直接復制代碼的時候!



    評論

    # re: java調oracle存儲過程  回復  更多評論   

    2010-01-12 19:18 by leekiang
    //如果java代碼是utf-8編碼,則不需要ZHS16GBK_CHARSET和new oracle.sql.CHAR(values[i],dbCharset)了:
    如下:
    ARRAY a= cst.getARRAY(1);
    Datum[] data = a.getOracleArray();
    for (int i = 0; i < data.length; i++) {
    System.out.println(
    new String(data[i].shareBytes()));
    }

    # re: java調oracle存儲過程  回復  更多評論   

    2010-01-12 19:24 by leekiang

    http://zhouyq.javaeye.com/blog/240440
    主站蜘蛛池模板: 一个人看www免费高清字幕| 亚洲综合伊人久久综合| 外国成人网在线观看免费视频| 亚洲国产综合AV在线观看| 亚洲成在人天堂在线| 久久亚洲国产成人影院网站| 处破痛哭A√18成年片免费| 59pao成国产成视频永久免费| 福利免费在线观看| 国产精品亚洲va在线观看| 亚洲 日韩 色 图网站| 亚洲国产精品成人久久久| 亚洲国产高清人在线| 最新国产AV无码专区亚洲| 亚洲国产精品碰碰| 国产免费牲交视频| 国产成人aaa在线视频免费观看 | 在线观看视频免费完整版| 中文字幕视频免费| 久久99精品视免费看| 国产在线观看xxxx免费| 国产免费内射又粗又爽密桃视频 | 韩国欧洲一级毛片免费 | 国产精品亚洲一区二区麻豆| 亚洲国产精品张柏芝在线观看| 亚洲午夜久久影院| 亚洲一区二区三区四区在线观看| 亚洲精品国产精品乱码视色| 亚洲精品中文字幕无码蜜桃| 亚洲人色婷婷成人网站在线观看| 亚洲美女在线国产| 狠狠亚洲婷婷综合色香五月排名| 亚洲国产精品日韩| 77777亚洲午夜久久多人| 国产亚洲一区二区精品| 亚洲AV无码乱码国产麻豆穿越 | a级毛片免费在线观看| 亚洲免费人成在线视频观看| 久久九九全国免费| 69影院毛片免费观看视频在线| 91成人免费观看网站|