领先一步
VMware 提供培训和认证,以加快您的进度。
了解更多我代表团队和所有做出贡献的人员,高兴地宣布 Spring Data R2DBC 1.0 的第一个候选版本已发布,可从我们的里程碑存储库获取。此版本包含 60 个问题和拉取请求。它将其基线升级到 R2DBC 0.8 RC1 和 Spring Data Moore GA。
最值得注意的功能包括:
AbstractRoutingConnectionFactory
进行ConnectionFactory
路由。ResourceDatabasePopulator
和ScriptUtils
进行模式初始化的实用程序。TransactionDefinition
传播和重置自动提交和隔离级别控制。ConnectionFactory
路由对于每个操作,DatabaseClient
从用于创建 DatabaseClient
的 ConnectionFactory
获取一个 Connection
。
其基本思想是路由ConnectionFactory
充当中间体——而“真实”的ConnectionFactory
是基于查找键在运行时动态确定的。一个潜在的用例是通过使用指向单独数据库的多个ConnectionFactory
实例来满足多租户需求。为了让路由ConnectionFactory
确定要使用哪个ConnectionFactory
,它需要上下文信息。Spring Data R2DBC 带有一个AbstractRoutingConnectionFactory
,它可以返回一个查找键,该键用于查找正确的ConnectionFactory
。
响应式流可以通过使用 Project Reactor 的Context
将上下文信息附加到订阅。
路由ConnectionFactory
的示例实现可能如下所示:
class RoutingConnectionFactory extends AbstractRoutingConnectionFactory {
public static final String ROUTING_KEY = "routing-key";
@Override
protected Mono<Object> determineCurrentLookupKey() {
return Mono.subscriberContext().filter(it -> it.hasKey(ROUTING_KEY)).map(it -> it.get(ROUTING_KEY));
}
}
以下清单显示了如何初始化查找键和目标ConnectionFactory
之间的映射的连接工厂。
RoutingConnectionFactory connectionFactory = new RoutingConnectionFactory();
Map<String, ConnectionFactory> factories = new HashMap<>();
factories.put("customer1", …);
factories.put("customer2", …);
connectionFactory.setTargetConnectionFactories(factories);
connectionFactory.afterPropertiesSet();
您可以通过使用路由ConnectionFactory
为每个订阅确定合适的ConnectionFactory
来创建DatabaseClient
。路由键本身附加到Context
中,并由RoutingConnectionFactory
进行评估,如下所示:
DatabaseClient client = DatabaseClient.create(connectionFactory);
Context routingContext = Context.of(ROUTING_KEY, "customer1");
Flux<User> users = client.execute("SELECT first_name, last_name FROM user")
.as(User.class)
.fetch()
.all()
.subscriberContext(routingContext);
org.springframework.data.r2dbc.connectionfactory.init
包提供了初始化现有ConnectionFactory
的支持。您有时可能需要初始化在某个服务器上运行的实例或嵌入式数据库。以下清单显示了如何注册和配置ConnectionFactoryInitializer
bean以通过ConnectionFactory
初始化数据库。
@Configuration
public class InitializerConfiguration {
@Bean
public ConnectionFactoryInitializer initializer(ConnectionFactory connectionFactory) {
ConnectionFactoryInitializer initializer = new ConnectionFactoryInitializer();
initializer.setConnectionFactory(connectionFactory);
CompositeDatabasePopulator populator = new CompositeDatabasePopulator();
populator.addPopulators(new ResourceDatabasePopulator(new ClassPathResource("com/foo/sql/db-schema.sql")));
populator.addPopulators(new ResourceDatabasePopulator(new ClassPathResource("com/foo/sql/test-data1.sql")));
initializer.setDatabasePopulator(populator);
return initializer;
}
}
此初始化支持由 Spring Boot R2DBC 自动配置使用,以将schema.sql
和data.sql
应用于配置的ConnectionFactory
。
此版本附带 Kotlin 扩展,用于在使用 Kotlin 开发应用程序时习惯性地使用 Spring Data R2DBC。
Spring Data R2DBC 提供以下扩展:
DatabaseClient
和Criteria
的具现化泛型支持DatabaseClient
的 Kotlin 协程支持要检索 Java 中的User
对象列表,通常会编写以下代码:
Flux<User> characters = client.select().from(User.class).fetch().all();
使用 Kotlin 和 Spring Data 扩展,您可以改为编写以下代码:
val users = client.select().from<User>().fetch().all()
Kotlin 协程是 Kotlin 轻量级线程,允许以命令式风格编写非阻塞代码。Spring Data R2DBC 的协程扩展利用响应式基础架构来公开可以suspend
的函数,并将Flux
结果桥接到 Kotlin 的Flow
类型。
以下示例显示了使用 Spring Framework 的TransactionalOperator
以原子方式插入两行的协程用法:
operator.executeAndAwait {
client.execute("INSERT INTO person VALUES(:first_name, :last_name)")
.bind("first_name", "John")
.bind("last_name", "Doe")
.await()
client.execute("INSERT INTO person_events VALUES(:first_name, :last_name, :event_type)")
.bind("first_name", "John")
.bind("last_name", "Doe")
.bind("event_type", "CREATED")
.await()
}
请注意,大多数suspend
方法以await
结尾,作为协程方法的指示符。
目前,R2DBC 驱动程序生态系统仅包含少数几个已知的驱动程序,但驱动程序的数量正在增长。为了实现与其他驱动程序的无缝集成,Spring Data R2DBC 公开了一个用于R2dbcDialect
注册的扩展点。Spring Data R2DBC 可以通过注册一个通过 Spring 的META-INF/spring.factories
机制实现org.springframework.data.r2dbc.dialect.DialectResolver$R2dbcDialectProvider
的类来自动发现R2dbcDialect
。以下清单显示了如何操作:
public class MyDialectProvider implements DialectResolver.R2dbcDialectProvider {
@Override
public Optional<R2dbcDialect> getDialect(ConnectionFactory connectionFactory) {
if (connectionFactory.getMetadata().getName().equals("my-dastabase")) {
return Optional.of(…);
}
return Optional.empty();
}
}
spring.factories
org.springframework.data.r2dbc.dialect.DialectResolver$R2dbcDialectProvider=com.example.MyDialectProvider
如果您使用 Maven,请将以下几行添加到您的pom.xml
文件中以升级到 Spring Data R2DBC 1.0 RC1:
<dependencies>
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-r2dbc</artifactId>
<version>1.0.0.RC1</version>
</dependency>
</dependencies>
<!-- R2DBC 0.8.0.RC1 required -->
<dependencyManagement>
<dependencies>
<dependency>
<groupId>io.r2dbc</groupId>
<artifactId>r2dbc-bom</artifactId>
<version>Arabba-RC1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<repositories>
<repository>
<id>spring-milestone</id>
<url>https://repo.spring.io/milestone</url>
</repository>
</repositories>
R2DBC 0.8.0 RC1 最近发布,我们预计今年晚些时候将发布 GA 版本。我们正在努力发布 Spring Data R2DBC 1.0 GA 版本,并在 R2DBC 本身发布 GA 后发布下一个版本。我们的待办事项列表包含一系列增强功能,例如查询派生、乐观锁以及允许查询拦截在执行之前更改绑定和 SQL 语句。
最后,以下是变更日志、GitHub 存储库和文档的链接: