OAF_JDBC系列1 - 数据库交互取值方式(案例)

2014-06-15 Created By BaoXinjian

一、摘要


通过VO和数据库交互

通过OracleStatement和数据库交互

通过OraclePreparedStatement和数据库交互

通过OracleCallableStatement和数据库交互

通过OracleCallableStatement调用存储过程

 

二、具体解析


1. 通过VO和数据库交互

public void initQuery(String reportName)
{
    if ((reportName != null) && (!("".equals(reportName.trim()))))
    {
       String repName = null;
       try
       {
         repName = new String(reportName); //由String得到一个Number类
       } catch (Exception e)
      {
         throw new OAException("AK", "FWK_TBX_INVALID_EMP_NUMBER");
       }
       setWhereClause("REPORT_HEADER_ID = :1");
       setWhereClauseParams(null); // Always reset
       setWhereClauseParam(0, repName);
       System.out.println("viktor3 repName=" + repName);
       executeQuery();
     }
   }
}

 

2. 通过OracleStatement和数据库交互

public void create(AttributeList attributeList)
 {
     super.create(attributeList);
 try
 {
    OracleConnection conn =  (OracleConnection)transaction.getJdbcConnection(); //获取当前连接
    OracleStatement stmt = (OracleStatement)conn.createStatement();  //生成语句
    OracleResultSet rset = (OracleResultSet)stmt.executeQuery("select msi.segment1  from mtl_system_items_b msi"); //执行查询
    while (rset.next()) //向前转移指针
    {
     setItemDesc(rset.getString(1)); //获取结果集中的第一个字段
     break;  //假定只取一条记录
    }
    rset.close(); //关闭结果集
 } catch(SQLException ex) {}
    //process exception
}

 

3. 通过OracleStatement和数据库交互

  private Map<String, String> getDisplayInst(String supplierClass) throws Exception
  {
    if (supplierClass == null)
      return null;
      
    Map<String, String> ret = null;
    OraclePreparedStatement ops = null;
    OracleResultSet ors = null;
    OADBTransaction trx = null;
    trx = this.getOADBTransaction();
    ops = (OraclePreparedStatement)trx.createPreparedStatement("SELECT * FROM CUX_SUP_INFO_DISP t WHERE t.supplier_class = ?", -1);

    ops.setString(1, supplierClass);
    ors = (OracleResultSet)ops.executeQuery();
    if (ors.next())
    {
      ret = new HashMap<String, String>();
      for (int i = 1; i <= ors.getMetaData().getColumnCount(); i++)
      {
        String columnName = ors.getMetaData().getColumnName(i);
        ret.put(columnName, ors.getString(columnName));

        Logger.debug( "getDisplayInst" + i + "==>" + columnName + ":" + ors.getString(columnName));
      }
    }
    if (ors != null)
    {
      ors.close();
    }
    if (ops != null)
    {
      ops.close();
    }
    return ret;
  }

 

4. 通过OracleCallableStatement和数据库交互

public void setAllAttribute(){
      System.out.println("ExpenseHeaderEOImpl.setAllAttribute");
      
      OADBTransaction transaction = getOADBTransaction();  
      Number n_report_header_id = transaction.getSequenceValue("BXJ_EXPENSE_REPORT_ID_S");
      setReportHeaderId(n_report_header_id);
      
      Number n_employee_id = new Number(25);
      String v_sql_getsupervisor = "BEGIN\n" +
                                   "   SELECT nvl(supervisor_id, 25)\n" +
                                   "     INTO :p_supervisor_id   \n" +
                                   "     FROM per_all_assignments_f\n" +
                                   "    WHERE person_id = :2\n" +
                                   "      AND effective_start_date <= sysdate\n" +
                                   "      AND effective_end_date > sysdate\n" +
                                   "      AND rownum <= 1;\n" +
                                   "END;";
      OracleCallableStatement callablestatement
                    = (OracleCallableStatement)transaction.createCallableStatement(v_sql_getsupervisor, 1);
      try{
        callablestatement.registerOutParameter(1, OracleTypes.NUMBER);
        callablestatement.setNUMBER(2, n_employee_id);
        callablestatement.execute();
        Number n_supervisor_id = new Number(callablestatement.getNUMBER(1));
        setApproveId(n_supervisor_id);
      }
      catch(Exception bxj_exception){
        throw OAException.wrapperException(bxj_exception);
      }
      finally{
        try{
          callablestatement.close();
        }
        catch(Exception bxj_excpetion){
          throw OAException.wrapperException(bxj_excpetion);
        }
      }
   }

 

5. 通过OracleCallableStatement调用存储过程

public String updateVendor(String type, String supplierName,
                             String rejectReason, String date, String pRecommended, String vendorid)
  {
    String status = null;
    String msg = null;
    String sql =
      "begin\n" + "  bxj_po_supplier_common_pkg.update_vendor(p_vendor_id => :1,\n" +
      "                                           p_vendor_name => :2,\n" +
      "                                           p_inactive_date => :3,\n" +
      "                                           p_reject_reason => :4,\n" +
      "                                           p_recommended   => :5,\n" +
      "                                           x_status => :6,\n" +
      "                                           x_message => :7,\n" +
      "                                           p_flag => :8);\n" + "end;";


    OADBTransaction tnx = getOADBTransaction();
    CallableStatement ocs = tnx.createCallableStatement(sql, 1);
    Date endDate = null;
    if (date != null && !"".equals(date))
    {
      endDate = Date.valueOf(date);
    }
    try
    {
      ocs.setObject(1, vendorid);
      ocs.setObject(2, supplierName);
      ocs.setDate(3, endDate);
      ocs.setObject(4, rejectReason);
      ocs.setObject(5, pRecommended);
      ocs.registerOutParameter(6, Types.VARCHAR);
      ocs.registerOutParameter(7, Types.VARCHAR);
      ocs.setObject(8, type);
      ocs.execute();
      status = ocs.getString(6);
      msg = ocs.getString(7);
    }
    catch (Exception e)
    {
      throw new OAException("鏇存柊渚涘簲鍟�:" + supplierName + "淇℃伅澶辫触!" +
                            e.getMessage());
    }
    finally
    {
      if (ocs != null)
      {
        try
        {
          ocs.close();
        }
        catch (Exception e)
        {
          e.printStackTrace();
        }
      }
    }
    if (!"S".equalsIgnoreCase(status))
    {
      throw new OAException(msg);
    }
    return msg;
  }

 

三、知识点


1. OracleStatement 和 OraclePrepareStatement

1. PreparedStatement是预编译的,对于批量处理可以大大提高效率. 也叫JDBC存储过程

 

2. 使用 Statement 对象。在对数据库只执行一次性存取的时侯,用 Statement 对象进行处理。

PreparedStatement 对象的开销比Statement大,对于一次性操作并不会带来额外的好处。

 

3. statement每次执行sql语句,相关数据库都要执行sql语句的编译,preparedstatement是预编译得,   preparedstatement支持批处理

 

4. 执行许多SQL语句的JDBC程序产生大量的Statement和PreparedStatement对象。

通常认为PreparedStatement对象比Statement对象更有效,特别是如果带有不同参数的同一SQL语句被多次执行的时候。

PreparedStatement对象允许数据库预编译SQL语句,这样在随后的运行中可以节省时间并增加代码的可读性。 

然而,在Oracle环境中,开发人员实际上有更大的灵活性。当使用Statement或PreparedStatement对象时,Oracle数据库会缓存SQL语句以便以后使用。

在一些情况下,由于驱动器自身需要额外的处理和在Java应用程序和Oracle服务器间增加的网络活动,执行PreparedStatement对象实际上会花更长的时间。

然而,除了缓冲的问题之外,至少还有一个更好的原因使我们在企业应用程序中更喜欢使用PreparedStatement对象,那就是安全性。

传递给PreparedStatement对象的参数可以被强制进行类型转换,使开发人员可以确保在插入或查询数据时与底层的数据库格式匹配。

当处理公共Web站点上的用户传来的数据的时候,安全性的问题就变得极为重要。

传递给PreparedStatement的字符串参数会自动被驱动器忽略。

最简单的情况下,这就意味着当你的程序试着将字符串“D'Angelo”插入到VARCHAR2中时,该语句将不会识别第一个“,”,从而导致悲惨的失败。几乎很少有必要创建你自己的字符串忽略代码。

在Web环境中,有恶意的用户会利用那些设计不完善的、不能正确处理字符串的应用程序。

特别是在公共Web站点上,在没有首先通过PreparedStatement对象处理的情况下,所有的用户输入都不应该传递给SQL语句。此外,在用户有机会修改SQL语句的地方,如HTML的隐藏区域或一个查询字符串上,SQL语句都不应该被显示出来。 

 

5.  一般来说,我会习惯使用PreparedStatement对数据库进行操作。

PreparedStatement是预编译方式的,在执行SQL语句的时候效率就要高一些,还有就是PreparedStatement可以更好地避免SQL注入问题;

在拼接sql语句时,采用PreparedStatement可以有效地减少出错的几率;

PreparedStatement是Statement的一个子类,理所当然地PreparedStatement对Statement有一定的扩展,在性能方面有一定的提高。

 

Thanks and Regards

posted on 2015-04-20 21:12  东方瀚海  阅读(1009)  评论(0编辑  收藏  举报