Fluxo reativo com MongoDB, Kotlin e Spring WebFlux
1. Overview
Neste tutorial, escreveremos um aplicativo simples apresentando um fluxo totalmente reativo usando Spring Data Reactive MongoDB e SpringSSeEmitter.
Por um lado, aplicaremos Spring Data Reactive MongoDB para salvar dados por meio de um banco de dados reativo Mongo e combiná-lo com o mecanismo Server-Sent-Events para notificar os clientes inscritos sobre os dados recebidos.
Além disso, tiraremos proveito do suporte Kotlin do Spring Boot.
Então vamos começar!
2. Configuração
Em primeiro lugar, temos que configurar nosso projeto Maven adicionando a dependência do MongoDB Spring Data Reactive em nossopom.xml:
org.springframework.boot
spring-boot-starter-data-mongodb-reactive
Além disso, para usar o Kotlin, precisaremos adicionarKotlin standard library ao mesmo arquivo:
org.jetbrains.kotlin
kotlin-stdlib
Agora, estamos prontos para começar a desenvolver nosso aplicativo. Começaremos a configurar o ambiente para suportar a programação reativa e o Mongo DB, então vamos lá!
3. Configuração Mongo reativa
A primeira coisa que precisamos fazer é configurar nosso projeto para suportar dados reativos do Spring. Adicionaremos uma nova classe que se estende deAbstractReactiveMongoConfiguration para configurar o cliente reativo Mongo e o Spring Data Repository:
@Configuration
@EnableReactiveMongoRepositories(
basePackageClasses = arrayOf(EventRepository::class))
class MongoConfig : AbstractReactiveMongoConfiguration() {
override fun getDatabaseName() = "mongoDatabase"
override fun reactiveMongoClient() = mongoClient()
@Bean
fun mongoClient() = MongoClients.create()
@Bean
override fun reactiveMongoTemplate()
= ReactiveMongoTemplate(mongoClient(), databaseName)
}
Essa configuração não é necessária se quisermos interagir com o MongoDB de maneira não reativa. Observe que temos que adicionar a tag@EnableReactiveMongoRepositories para que a configuração saiba onde nossos repositórios Spring Data estão.
Depois disso, agora estamos prontos para começar a implementar a funcionalidade principal. The first thing we’ll do is develop a new data class to persist the incoming information and then, a related Spring Data reactive repository to manage that persistence.
4. Documento
Odocument é a unidade de armazenamento de dados em um banco de dados MongoDB. Esta unidade usa o estilo JSON para armazenar dados.
Em nosso projeto, vamos mantê-lo simples usando um simuladodocument escalonadoEvent com dois atributos:idename:
@Document
class Event(id: String, name: String)
5. Spring Data Reactive Repository
O objetivo da abstração do Spring Data é reduzir a quantidade de código necessária para implementar as camadas de acesso a dados para armazenamentos de persistência.
Consequentemente, a versão reativa funciona da mesma forma, teremos a seguinte linha para implementar um repositório reativo completo:
interface EventRepository : ReactiveMongoRepository
6. Controlador
A classeController será responsável por enviar um Server-Sent Event sempre que algum dado reativo for salvo.
O métodosaveAndSend alvará primeiro os dados de entrada em nosso banco de dados Mongo Reactive, delegando esta ação ao nossoEventRepository.
Consequentemente, adicionaremos um novo endpoint que cria e salva novosEvents.
Primeiro, vamos ver o código Kotlin:
@GetMapping(value = "/save",
produces = arrayOf(MediaType.TEXT_EVENT_STREAM_VALUE))
fun saveAndSend(@RequestParam("eventName") eventName: String) =
eventRepository
.save(Event(UUID.randomUUID().toString(), eventName))
.flux()
Como podemos ver, depois de salvar os novos dados, o repositório reativo do Spring Data retornará um SSE que será enviado ao cliente inscrito.
Neste ponto, podemos dizer que temos um projeto reativo completo do lado do servidor Kotlin. Já temos todos os elementos necessários para executar nosso aplicativo Spring Boot.
Assim, agora vamos dar uma olhada em como criar um cliente web simples para enviar e receber todos os nossos eventos enviados pelo servidor.
7. Assinante
Aqui, temos um cliente Web simples que poderá salvar dados e receber alterações do servidor.
Vamos ver como isso é implementado:
7.1. Enviar dados
O cliente salvará o nome do evento digitado através do botãoSave new event .
Isso, por sua vez, fará uma solicitação HTTP ao endpoint do servidorsaveEvent:
7.2. Receber dados
Por outro lado, o cliente estará ouvindosave ponto de envio também. Observe que cada linguagem de programação possui suas estruturas específicas para gerenciar o SSE.
No entanto, para nosso exemplo, vamos mantê-lo o mais simples possível:
8. Conclusão
Em conclusão,Spring Data MongoDB has been updated to leverage the reactive programming model introduced in Spring Framework 5. Agora, temos uma maneira simples de usar esse paradigma de programação e eventos enviados pelo servidor.
Portanto, isso supõe uma alternativa para as aplicações não reativas tradicionais dos problemas com o bloqueio do banco de dados.
A implementação deste exemplo pode ser verificadain the GitHub project.
Como é um projeto baseado em Maven, execute o aplicativo Spring Boot para ver como ele funciona. Não se esqueça de executar o servidor Mongo DB primeiro.