JPA 休眠 + UCP 甲骨文。从保存方法执行的查询不使用 table 的索引
JPA Hibernate + UCP Oracle. Query executed from save method does not use the index of the table
我正在使用接口 CRUDRepository 以便在注入存储库的其他 class 中使用保存方法。
这个方法做一个插入和一个 select 来检索这个从数据库插入的对象,我的意思是。
执行的查询非常简单:
select auditoriab0_.adb_seqitm as adb_seqitm1_1_0_,
auditoriab0_.adb_codprv as adb_codprv2_1_0_, auditoriab0_.adb_ideses as adb_ideses3_1_0_,
auditoriab0_.adb_locata as adb_locata4_1_0_, auditoriab0_.adb_rqores as adb_rqores5_1_0_,
auditoriab0_.adb_rstime as adb_rstime6_1_0_, auditoriab0_.adb_subprv as adb_subprv7_1_0_,
auditoriab0_.adb_swierr as adb_swierr8_1_0_, auditoriab0_.adb_tiptrz as adb_tiptrz9_1_0_,
auditoriab0_.adb_ubitrz as adb_ubitrz10_1_0_, auditoriab0_.adb_xmltxt as adb_xmltxt11_1_0_
from nwt00.auditoria_bus_gsi auditoriab0_ where auditoriab0_.adb_seqitm=:p1
其中 adb_seqitm
列有索引(这是 table 的主键)。
如果这个查询是在 SQLDeveloper 上执行的,例如,解释计划是正确的(通过 rowid 访问)。
但是,如果这个查询是由hibernate执行的,结果是全扫描。
你能帮我解决这个问题吗?我将不胜感激,因为我没有在互联网上看到针对这个特定问题的真正解决方案。
提前致谢。
此行为发生在 ucp(通用连接池)池中。接下来是我的数据库 bean 配置(变量由 application.properties 文件设置):
UniversalConnectionPoolManager mgr;
try {
mgr = UniversalConnectionPoolManagerImpl. getUniversalConnectionPoolManager();
mgr.destroyConnectionPool("hotels");
} catch (UniversalConnectionPoolException e) {
}
PoolDataSourceImpl poolDataSource = (PoolDataSourceImpl) PoolDataSourceFactory.getPoolDataSource();
poolDataSource.setUser(userName);
poolDataSource.setPassword(passWord);
poolDataSource.setURL(url);
poolDataSource.setConnectionFactoryClassName(driver);
poolDataSource.setConnectionPoolName("hotels");
poolDataSource.setInitialPoolSize(initialNumConnections);
poolDataSource.setMinPoolSize(minNumConnections);
poolDataSource.setMaxPoolSize(maxNumConnections);
poolDataSource.setMaxConnectionReuseTime(reconnectTime);
poolDataSource.setMaxConnectionReuseCount(maxReconnectCount);
poolDataSource.setTimeToLiveConnectionTimeout(timeToLive);
poolDataSource.setConnectionWaitTimeout(connectWaitTimeOut);
poolDataSource.setValidateConnectionOnBorrow(true);
poolDataSource.setInactiveConnectionTimeout(inactiveConnectionTimeOut);
Properties properties = new Properties();
properties.put("v$session.program", "xxxx");
properties.put("defaultNChar", "false");
poolDataSource.setConnectionProperties(properties );
我正在使用 Spring Boot + Spring Data JPA。这些是我对 pom.xml:
的依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>com.oracle</groupId>
<artifactId>ojdbc6</artifactId>
<version>11.2.0.4.0</version>
</dependency>
<dependency>
<groupId>com.oracle</groupId>
<artifactId>ucp</artifactId>
<version>11.2.0.4.0</version>
</dependency>
@krokodilko 如您所料,错误出现在数据库类型和 java 类型之间。在 DDBB 中,这个字段是一个字符串 (varchar2(15))。在Java中,该字段映射为long类型。我猜休眠或数据库正在做一个破坏索引的转换。我已经通过 String 类型更改了 java 类型,并且查询成功运行。解释计划是正确的。
我正在使用接口 CRUDRepository 以便在注入存储库的其他 class 中使用保存方法。
这个方法做一个插入和一个 select 来检索这个从数据库插入的对象,我的意思是。
执行的查询非常简单:
select auditoriab0_.adb_seqitm as adb_seqitm1_1_0_,
auditoriab0_.adb_codprv as adb_codprv2_1_0_, auditoriab0_.adb_ideses as adb_ideses3_1_0_,
auditoriab0_.adb_locata as adb_locata4_1_0_, auditoriab0_.adb_rqores as adb_rqores5_1_0_,
auditoriab0_.adb_rstime as adb_rstime6_1_0_, auditoriab0_.adb_subprv as adb_subprv7_1_0_,
auditoriab0_.adb_swierr as adb_swierr8_1_0_, auditoriab0_.adb_tiptrz as adb_tiptrz9_1_0_,
auditoriab0_.adb_ubitrz as adb_ubitrz10_1_0_, auditoriab0_.adb_xmltxt as adb_xmltxt11_1_0_
from nwt00.auditoria_bus_gsi auditoriab0_ where auditoriab0_.adb_seqitm=:p1
其中 adb_seqitm
列有索引(这是 table 的主键)。
如果这个查询是在 SQLDeveloper 上执行的,例如,解释计划是正确的(通过 rowid 访问)。
但是,如果这个查询是由hibernate执行的,结果是全扫描。
你能帮我解决这个问题吗?我将不胜感激,因为我没有在互联网上看到针对这个特定问题的真正解决方案。
提前致谢。
此行为发生在 ucp(通用连接池)池中。接下来是我的数据库 bean 配置(变量由 application.properties 文件设置):
UniversalConnectionPoolManager mgr;
try {
mgr = UniversalConnectionPoolManagerImpl. getUniversalConnectionPoolManager();
mgr.destroyConnectionPool("hotels");
} catch (UniversalConnectionPoolException e) {
}
PoolDataSourceImpl poolDataSource = (PoolDataSourceImpl) PoolDataSourceFactory.getPoolDataSource();
poolDataSource.setUser(userName);
poolDataSource.setPassword(passWord);
poolDataSource.setURL(url);
poolDataSource.setConnectionFactoryClassName(driver);
poolDataSource.setConnectionPoolName("hotels");
poolDataSource.setInitialPoolSize(initialNumConnections);
poolDataSource.setMinPoolSize(minNumConnections);
poolDataSource.setMaxPoolSize(maxNumConnections);
poolDataSource.setMaxConnectionReuseTime(reconnectTime);
poolDataSource.setMaxConnectionReuseCount(maxReconnectCount);
poolDataSource.setTimeToLiveConnectionTimeout(timeToLive);
poolDataSource.setConnectionWaitTimeout(connectWaitTimeOut);
poolDataSource.setValidateConnectionOnBorrow(true);
poolDataSource.setInactiveConnectionTimeout(inactiveConnectionTimeOut);
Properties properties = new Properties();
properties.put("v$session.program", "xxxx");
properties.put("defaultNChar", "false");
poolDataSource.setConnectionProperties(properties );
我正在使用 Spring Boot + Spring Data JPA。这些是我对 pom.xml:
的依赖 <dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>com.oracle</groupId>
<artifactId>ojdbc6</artifactId>
<version>11.2.0.4.0</version>
</dependency>
<dependency>
<groupId>com.oracle</groupId>
<artifactId>ucp</artifactId>
<version>11.2.0.4.0</version>
</dependency>
@krokodilko 如您所料,错误出现在数据库类型和 java 类型之间。在 DDBB 中,这个字段是一个字符串 (varchar2(15))。在Java中,该字段映射为long类型。我猜休眠或数据库正在做一个破坏索引的转换。我已经通过 String 类型更改了 java 类型,并且查询成功运行。解释计划是正确的。