Home > Blockchain >  How to return just a String using Webflux - webclient?
How to return just a String using Webflux - webclient?

Time:10-23

I would like to make this call and return a string but I'm having this error:

"java.lang.IllegalStateException: block()/blockFirst()/blockLast() are blocking, which is not supported in thread reactor-http-nio-3"

I dont understand why am I doing wrong? WebClient supports asynchronous as well as synchronous calls.

This a springboot project with just 3 dependencies.

How can I return just a string like a normal synchronous call?

@RestController
public class HomeController {

@GetMapping("/")
public String home() {
String resp = webclient.get()                             
                       .uri(ANY_URL).retrieve()
                       .bodyToMono(String.class)
                       .block();
return resp;

 }


}

pom.xml
<dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-webflux</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>io.projectreactor</groupId>
            <artifactId>reactor-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

Thanks.

CodePudding user response:

Fixed by adding spring-boot-starter-web

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

CodePudding user response:

Not sure what is your goal but the whole idea of Webflux is to create non-blocking reactive services. WebClient support both async and sync usage but the error you are getting is from reactive controller. There is no reason to block in your example - just change return type from String to Mono<String>.

@GetMapping("/")
public Mono<String> home() {
String resp = webclient.get()                             
       .uri(ANY_URL).retrieve()
       .bodyToMono(String.class);
 }

The intuition behind this is

  • use spring-boot-starter-webflux and WebClient in async mode to create reactive services. Controller should return Mono or Flux. The caveat here is that your logic should be reactive (async) end-to-end to get full advantage of the Reactive API.
  • add spring-boot-starter-web if you want to build non-reactive service and just use WebClient in sync (blocking) mode as your Http client.
  • Related