spring - 是否可以将 BYTEA 字段与 Spring Data JDBC(不是 JPA)一起使用
问题描述
我正在尝试使用 Spring Data JDBC 读取具有 BYTEA 字段的 Postgresql 表中的一行,但它因Couldn't find PersistentEntity for type byte!
MappingException 而失败。该方法失败org.springframework.data.jdbc.core.EntityRowMapper.populateProperties
,它被解释byte[]
为isCollectionLike
并且(我想)试图创建 SQL 以将其读取为 PostgreSQL 字节数组,而不是它的 blob。
有很多关于如何使用 JPA 或手动 JdbcTemplate 执行此操作的示例,但 Spring Data JDBC 的文档不那么丰富。我无法想象我是第一个遇到这个问题的人。
java.lang.IllegalStateException: Failed to execute CommandLineRunner
at org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:782) ~[spring-boot-2.1.6.RELEASE.jar:2.1.6.RELEASE]
at org.springframework.boot.SpringApplication.callRunners(SpringApplication.java:763) ~[spring-boot-2.1.6.RELEASE.jar:2.1.6.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:318) ~[spring-boot-2.1.6.RELEASE.jar:2.1.6.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1213) ~[spring-boot-2.1.6.RELEASE.jar:2.1.6.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1202) ~[spring-boot-2.1.6.RELEASE.jar:2.1.6.RELEASE]
at markscottwright.Application.main(Application.java:18) ~[classes/:na]
Caused by: org.springframework.data.mapping.MappingException: Couldn't find PersistentEntity for type byte!
at org.springframework.data.mapping.context.MappingContext.getRequiredPersistentEntity(MappingContext.java:79) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.data.jdbc.core.SqlGeneratorSource.lambda$getSqlGenerator$0(SqlGeneratorSource.java:41) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at java.base/java.util.concurrent.ConcurrentHashMap.computeIfAbsent(ConcurrentHashMap.java:1705) ~[na:na]
at org.springframework.data.jdbc.core.SqlGeneratorSource.getSqlGenerator(SqlGeneratorSource.java:40) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at org.springframework.data.jdbc.core.DefaultDataAccessStrategy.sql(DefaultDataAccessStrategy.java:360) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at org.springframework.data.jdbc.core.DefaultDataAccessStrategy.findAllByProperty(DefaultDataAccessStrategy.java:252) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at org.springframework.data.jdbc.core.EntityRowMapper.populateProperties(EntityRowMapper.java:94) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at org.springframework.data.jdbc.core.EntityRowMapper.mapRow(EntityRowMapper.java:74) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at org.springframework.jdbc.core.RowMapperResultSetExtractor.extractData(RowMapperResultSetExtractor.java:94) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.RowMapperResultSetExtractor.extractData(RowMapperResultSetExtractor.java:61) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.JdbcTemplate$1.doInPreparedStatement(JdbcTemplate.java:678) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:616) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.JdbcTemplate.query(JdbcTemplate.java:668) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.JdbcTemplate.query(JdbcTemplate.java:693) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.JdbcTemplate.query(JdbcTemplate.java:747) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate.query(NamedParameterJdbcTemplate.java:215) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate.query(NamedParameterJdbcTemplate.java:227) ~[spring-jdbc-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.data.jdbc.core.DefaultDataAccessStrategy.findAll(DefaultDataAccessStrategy.java:217) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at org.springframework.data.jdbc.core.JdbcAggregateTemplate.findAll(JdbcAggregateTemplate.java:171) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at org.springframework.data.jdbc.repository.support.SimpleJdbcRepository.findAll(SimpleJdbcRepository.java:84) ~[spring-data-jdbc-1.0.9.RELEASE.jar:1.0.9.RELEASE]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:na]
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:na]
at java.base/java.lang.reflect.Method.invoke(Method.java:566) ~[na:na]
at org.springframework.data.repository.core.support.RepositoryComposition$RepositoryFragments.invoke(RepositoryComposition.java:359) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.data.repository.core.support.RepositoryComposition.invoke(RepositoryComposition.java:200) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$ImplementationMethodExecutionInterceptor.invoke(RepositoryFactorySupport.java:644) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.doInvoke(RepositoryFactorySupport.java:608) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.lambda$invoke$3(RepositoryFactorySupport.java:595) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.invoke(RepositoryFactorySupport.java:595) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.data.projection.DefaultMethodInvokingMethodInterceptor.invoke(DefaultMethodInvokingMethodInterceptor.java:59) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:295) ~[spring-tx-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:98) ~[spring-tx-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.invoke(PersistenceExceptionTranslationInterceptor.java:139) ~[spring-tx-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:93) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.data.repository.core.support.SurroundingTransactionDetectorMethodInterceptor.invoke(SurroundingTransactionDetectorMethodInterceptor.java:61) ~[spring-data-commons-2.1.9.RELEASE.jar:2.1.9.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212) ~[spring-aop-5.1.8.RELEASE.jar:5.1.8.RELEASE]
at com.sun.proxy.$Proxy44.findAll(Unknown Source) ~[na:na]
at markscottwright.Application.run(Application.java:23) ~[classes/:na]
at org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:779) ~[spring-boot-2.1.6.RELEASE.jar:2.1.6.RELEASE]
... 5 common frames omitted
2019-08-20 13:36:00.335 INFO 10604 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Shutdown initiated...
2019-08-20 13:36:00.344 INFO 10604 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Shutdown completed.
我的桌子:
CREATE TABLE IF NOT EXISTS test_entity (
id INTEGER PRIMARY KEY,
byte_array BYTEA
);
insert into test_entity values (1, decode('00010203', 'hex'));
测试实体.java
package markscottwright;
import org.springframework.data.annotation.Id;
public class TestEntity {
@Id
public Long id;
public byte[] byteArray;
}
TestEntityRepository.java
package markscottwright;
import org.springframework.data.repository.CrudRepository;
public interface TestEntityRepository extends CrudRepository<TestEntity, Long> {
}
我的应用程序.java
package markscottwright;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.data.jdbc.repository.config.EnableJdbcRepositories;
@EnableJdbcRepositories
@SpringBootApplication
public class Application implements CommandLineRunner {
@Autowired
TestEntityRepository testEntities;
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
@Override
public void run(String... args) throws Exception {
testEntities.findAll().forEach(System.out::println);
}
}
我的 pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>markscottwright</groupId>
<artifactId>springdata-bytea</artifactId>
<version>0.0.1-SNAPSHOT</version>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.6.RELEASE</version>
</parent>
<properties>
<java.version>11</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-jdbc</artifactId>
</dependency>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<scope>runtime</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
解决方案
这是作为DATAJDBC-327和DATAJDBC-259的一部分实现的,它们在 1.1.x 版本中可用。
推荐阅读
- python - 根据行和列条件保留熊猫数据框的行
- android - OnReceive 未在 Android Kotlin 中的 BroadcastReceiver 对象内调用
- c# - 当一项任务阻塞时,线程池如何使用工作线程管理工作项?
- javascript - 如何从 Excel 表格中读取传单标记的坐标并将标记放在正确的类别中
- javascript - Webpack DefinePlugin 包含整个目录
- angular - “Draw”如何在服务器端角度数据表中工作
- javascript - Await 不等待另一个 Await
- ios - Xcode模拟器网络连接问题
- vue.js - 如何使用 vue-html2pdf 自动打印而不是下载
- git - 如何切换到分支名称中带有正斜杠的远程分支?