WSCallHelper.jdbcCall WAS 8.5 的 XMLType 映射实现

WSCallHelper.jdbcCall XMLType Mapping implementation for WAS 8.5

早上好!
我正在尝试从 Websphere 6.5 升级到 8.5。当应用程序将 xml 数据提交到数据库时,出现以下错误:

Caused by: 
java.sql.SQLException: java.lang.IllegalAccessException: Class com.ibm.ws.rsadapter.jdbc.WSJdbcUtil can not access a member of class oracle.jdbc.driver.OraclePreparedStatementWrapper with modifiers "public"
    at com.ibm.ws.rsadapter.AdapterUtil.toSQLException(AdapterUtil.java:1727)
    at com.ibm.ws.rsadapter.jdbc.WSJdbcUtil.call(WSJdbcUtil.java:684)
    at com.ibm.ws.rsadapter.jdbc.WSJdbcUtil.call(WSJdbcUtil.java:377)
    at com.ibm.websphere.rsadapter.WSCallHelper.jdbcCall(WSCallHelper.java:302)
    at J.D.A.A.WASOracleXMLType.nullSafeSet(Unknown Source)
    at J.D.A.A.A.nullSafeSet(Unknown Source)
    at org.hibernate.type.CustomType.nullSafeSet(CustomType.java:146)

经过一段时间的调查,我想我已经找到了问题所在:WebSphere 方法名称 jdbcCall 在 WebSphere 6.5 中有 5 个参数,但现在可以有 6 个参数。

该方法在此处描述:https://www-01.ibm.com/support/knowledgecenter/SS7K4U_8.5.5/com.ibm.websphere.javadoc.doc/web/apidocs/com/ibm/websphere/rsadapter/WSCallHelper.html 参数是这样的:

**vendorClassName** - The name of the vendor-specific interface class
on which methName is defined. This value can be used in cases where the 
implementation class of the vendor's JDBC object is a protected class, i.e. 
calling methName on the underlying JDBC object produces an **IllegalAccessException**. This value should specify the name of the vendor's recommended Class/Interface which is extended/implemented by the underlying JDBC object. For example "oracle.jdbc.driver.OracleResultSet" may need to be specified when the underlying object is an OracleResultSetImpl object. If not needed, this value may be null.

这是我的实现:

com.ibm.websphere.rsadapter.WSCallHelper.jdbcCall(
                    null,
                    a-Prepared-Statement, //OraclePreparedStatementWrapper
                    "setObject",
                    new Object[]{new Integer(index), xmlType},
                    new Class[]{int.class, Object.class})

所以,我已经阅读了文档,但我不明白我应该插入什么作为 vendorClassName,也许就够了 "oracle.jdbc.OracleDriver"?谁能更好地解释我能理解我应该在这个参数中插入什么?
否则你认为可能是什么问题?
我正在使用 Oracle12c、ojdbc6 和 WebSphere 8.5
谢谢!

为什么你需要使用 WSCallHelper.jdbcCall()
由于 PreparedStatement.setObject(int, Object) 完全是 JDBC 标准,您可以只在语句对象上调用它而无需进行任何类型的展开。如果您需要调用供应商特定的 API,您应该只尝试打开 WebSphere JDBC 连接。

只需做:

aStatement.setObject(index, xmlType);


如果您需要访问供应商特定的 API:
WSCallHelper.jdbcCall() 的用法已经过时了。我建议改用 Connection.unwrap(Class<?>)

示例:

OraclePreparedStatement oracleStmt = aStatement.unwrap(OraclePreparedStatement.class);


如果你真的、真的需要用WSCallHelper.jdbcCall():
传入供应商 class 名称将允许 WebSphere 加载供应商 class 并在应用适当的 class 加载程序的情况下以特权方式执行调用操作。

您要传入的供应商 class 名称是您尝试调用的供应商对象的 class 名称。因此,如果您在 oracle 驱动器中使用语句,您将传入字符串 "oracle.jdbc.OracleStatement" 作为您的 vendorClassName。

示例:

com.ibm.websphere.rsadapter.WSCallHelper.jdbcCall(
    null,
    aStatement, // WSJdbcPreparedStatement wrapping an OraclePreparedStatement
    "someOracleSpecificMethod",
    new Object[]{new Integer(index), xmlType},
    new Class[]{int.class, Object.class},
    "oracle.jdbc.OracleStatement");