1

I wanted to get an opinion on how to properly implement this and if this is the right approach to doing so. So I have created a fully reactive application using reactive-messaging but have come to know that I have an overarching constraint - and that constraint being Oracle. As you know, JDBC is inherently blocking in nature and cannot really be executed asynchronously. I am trying to figure out a way to achieve this so that the event loop thread does not get blocked and so far the only thing that seems to work is something like this:

@Incoming(KAFKA_DATA)
@Blocking
@Acknowledgment(Acknowledgment.Strategy.MANUAL)
fun consume(record: Message<Notification>): CompletionStage<Void> {
    val metadata = record.getMetadata(IncomingKafkaRecordMetadata::class.java).orElse(null)
    if (metadata != null) {
        log.debug(
            "Received Kafka Record - " +
                "topic: {}, " +
                "partition: {}, " +
                "offset: {}, " +
                "payload: {}",
            metadata.topic, metadata.partition, metadata.offset, record.payload
        )
    }
    return Uni.createFrom().voidItem()
        .invoke { -> invokeBlockingCall(record.payload) }
        .call { -> handleSuccess(record) }
        .onFailure().call { failure -> handleFailure(failure, record) }
        .runSubscriptionOn(Infrastructure.getDefaultExecutor())
        .subscribeAsCompletionStage()
}

I have managed to get that working as-is but I am unsure if it is the correct/efficient way of doing so. Does anyone have any suggestions on how to achieve such a task? Any suggestions are greatly appreciated and taken into account, thanks!

Lazaro R.
  • 39
  • 8
  • Oracle may not be a constraint anymore. There is a non-blocking driver developed here: https://vertx.io/docs/4.2.0/vertx-oracle-client/java/. In your snippet, you can remove the @Blocking, as you call the blocking method on a worker thread. – Clement Jan 27 '22 at 12:27
  • Understood. I have removed the @Blocking annotation as that makes sense to me, was just unsure if it had to be used in-tandem with blocking calls. For the reactive oracle client, do you know if it integrates with Mutiny? If so, is there an example of such code? I am still new to reactive and learning as I go. – Lazaro R. Jan 27 '22 at 13:42
  • 1
    If you are using Quarkus, there is an extension for it and yes, we have a Mutiny API for it. You can find the Javadoc here: https://smallrye.io/smallrye-mutiny-vertx-bindings/2.17.0/apidocs/io/vertx/mutiny/oracleclient/package-summary.html. It's the same API as the other reactive datasource. – Clement Jan 28 '22 at 17:52
  • 1
    Starting with the 21.1 release, Oracle JDBC now includes Reactive Extensions for asynchronous non-blocking database calls: docs.oracle.com/en/database/oracle/oracle-database/21/jjdbc/… You can also check out the Oracle R2DBC project, which is an open source implementation built on top of the Reactive Extensions: github.com/oracle/oracle-r2dbc I worked on both of these projects, so I'm biased in thinking they are both great solutions :) – Michael McMahon Jan 31 '22 at 23:34
  • @MichaelMcMahon Yes I was actually thinking of looking into that! Would you be able to guide me further by helping me with maybe a sample proof-of-concept project or code so that I may get a better understanding of how to implement it in my project? – Lazaro R. Feb 01 '22 at 16:49
  • @LazaroR. For Oracle JDBC's Reactive Extensions, you can find some code examples in the developers guide: [Developer's Guide](https://docs.oracle.com/en/database/oracle/oracle-database/21/jjdbc/jdbc-reactive-extensions.html#GUID-1C40C43B-3823-4848-8B5A-D2F97A82F79B) And for Oracle R2DBC, the R2DBC Specification is good place to start, and has many code examples: [R2DBC Spec](https://r2dbc.io/spec/0.9.0.RELEASE/spec/html/) We also have some Oracle specific code examples here: [Oracle Examples](https://github.com/oracle/oracle-r2dbc/tree/main/sample/src/main/java/oracle/r2dbc/samples) – Michael McMahon Feb 02 '22 at 17:59
  • 1
    I would recommend not using R2DBC in Quarkus. You would not be able to use most of the features of Quarkus with that model. Quarkus provides its own reactive Oracle client. – Clement Feb 16 '22 at 07:08
  • Clement, I have seen that Quarkus 2.7.x has integrated the reactive-oracle-client and marked as "experimental" in the docs. I have been trying to implement that but cannot seem to get any transaction inserted into the database due to this error: `HR000061: Session is currently connecting to database`. Feel free to check the issue out on Quarkus GH: https://github.com/quarkusio/quarkus/issues/23736 – Lazaro R. Feb 16 '22 at 14:59

0 Answers0