ITPub博客

首页 > Linux操作系统 > Linux操作系统 > Tomcat和WebLogic在使用连接池处理CLOB字段的诡异问题

Tomcat和WebLogic在使用连接池处理CLOB字段的诡异问题

原创 Linux操作系统 作者:kiddwyl 时间:2019-02-24 19:24:08 0 删除 编辑

上篇文章说到在Oracle PL/SQL中如何处理CLOB字段,现在来说说这几天碰到的一个诡异问题

为了符合业务部门的要求,需要将一些数据存储到CLOB字段中,当然,在日常的生产系统上当然是使用ConnectionPool来连接数据库的了,代码段如下:

     public Connection getJdbcConnection(){
      Connection conn = null;
      try {
   conn = getJdbcTemplate().getDataSource().getConnection();
    } catch (SQLException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
   }
      return  conn;
     }

处理代码段如下:

......    
oracle.sql.CLOB clobtt = null;
    if(rs.next()){
        clobtt = (oracle.sql.CLOB)rs.getClob(1);
        Writer wr = clobtt.getCharacterOutputStream();
        char[] b = obj.getValue1().toCharArray();
......

运行结果:
ClassCastException

奇怪了,难道是我的Driver用错了(这时我使用的是Tomcat DataSource),查看了common/lib下的driver,classes12.jar!没错呀。。等一下,好像不对,怎么才1.04MB,这个是Oracle9i R1的Driver,当然是不包括oracle.sql.CLOB对象的,更换(classes12.jar是1.14MB的)

写了一段测试,代码如下(连接方式采用DriverManager方式测试):

 public Connection getConnectionDB(){
  Connection conn = null;
  try {
   Class.forName("XXXXXXXXXXXXXXXXX");
   conn = DriverManager.getConnection("XXXXXXX","XXXXX","XXXXX");
  } catch (ClassNotFoundException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
  } catch (SQLException e1) {
   // TODO Auto-generated catch block
   e1.printStackTrace();
  }
  return conn;
 }

哈哈,结果是成功的,然后更换到生产机上运行。。。晕,使用DataSource还是ClassCastException,查找了一翻。。还是一样的问题,难道是tomcat不支持CLOB方式?更换至weblogic,同样问题。。。

我有点晕了,通过如下方式进行Debug捕捉,看看到底对象中是什么:

Object o = rs.getClob(1);
结果是oracle.sql.CLOB,晕了。。那怎么会在使用DataSource的情况下就ClassCastException呢?使用DriverManager却不会发生?查看一下WEB-INF\lib下的包,没有任何问题

考虑再三,首先先要解决问题,由于项目开发中使用tomcat(开发人员的机器太烂,没办法在开发环境也用weblogic),QA和现场均使用weblogic DataSource,而且客户现场不可以在配制文件中出现密码明文、考虑到performance,所以使用DriverManager是不现实的

实现代码如下:
......
   //获取J2EE服务器类型 1-tomcat 0-weblogic
   String r = ((Gparam)getParamByCode("1050")).getValue1();
   
   Connection conn = null;
   if("1".equals(r)){//tomcat
    conn = jdbcManager.getConnectionDB();
   }else if("0".equals(r)){//weblogic
    conn = jdbcManager.getJdbcConnection();
   }

   conn.setAutoCommit(false);
   ResultSet rs = null;
   
   String sql=getLparamSQL(obj,editMode);
   PreparedStatement stmt = conn.prepareStatement(sql);
 
   stmt.executeUpdate();
   sql = "SELECT VALUE1,VALUE2 FROM LPARAM WHERE KEY = "+obj.getKey()+" AND USERID="+obj.getUserid()+" FOR UPDATE";
   stmt = conn.prepareStatement(sql);
   rs= stmt.executeQuery();

   if("1".equals(r)){//tomcat
    oracle.sql.CLOB clobtt = null;
    if(rs.next()){
        clobtt = (oracle.sql.CLOB)rs.getClob(1);
        Writer wr = clobtt.getCharacterOutputStream();
        char[] b = obj.getValue1().toCharArray();
        wr.write(b);
        wr.flush();
        wr.close();
       
        clobtt = (oracle.sql.CLOB)rs.getClob(2); 
        wr = clobtt.getCharacterOutputStream();
        b = obj.getValue2().toCharArray();
        wr.write(b);
        wr.flush();
        wr.close();
     }
   }else if("0".equals(r)){//weblogic
    weblogic.jdbc.vendor.oracle.OracleThinClob clobtt = null;
    if(rs.next()){
        clobtt = (weblogic.jdbc.vendor.oracle.OracleThinClob)rs.getClob(1);
        Writer wr = clobtt.getCharacterOutputStream();
        char[] b = obj.getValue1().toCharArray();
        wr.write(b);
        wr.flush();
        wr.close();
       
        clobtt = (weblogic.jdbc.vendor.oracle.OracleThinClob)rs.getClob(2); 
        wr = clobtt.getCharacterOutputStream();
        b = obj.getValue2().toCharArray();
        wr.write(b);
        wr.flush();
        wr.close();
     }
   }

   rs.close();
   stmt.close();
   conn.commit();
   conn.close();
......

在weblogic环境下使用weblogic.jdbc.vendor.oracle.OracleThinClob专用方式来进行处理,在tomcat环境下使用driverManager,然后通过系统配置文件进行开关式配置,用来解决2个矛盾的问题

通过以上处理来看,解决事情还是要多动脑精,不能死钻。。。
关于JDBC Driver的这个疑问还有待深入研究。。。等待下文

来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/111631/viewspace-605995/ ,如需转载,请注明出处,否则将追究法律责任。

上一篇: oracle临时表
请登录后发表评论 登录
全部评论

注册时间:2004-08-27

  • 博文量
    66
  • 访问量
    59992