es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Encadenando llamadas reactivas a Redis en Spring

Estoy intentando obtener todas las claves y luego obtener todos sus valores usando un ReactiveRedisTemplate en Spring Data Redis.

(Sé que se prefiere scan, pero quiero mantenerlo simple por ahora, a menos que ese sea mi problema).

Fragmento de código:

@Service
class Test {
    Logger logger = LoggerFactory.getLogger(Test.class);

    @Autowired
    private ReactiveRedisTemplate<String, String> reactiveRedisTemplate;

    @EventListener(ApplicationReadyEvent.class)
    public void test() {
        logger.info("test");
        var ops = reactiveRedisTemplate.opsForValue();
        var keys = reactiveRedisTemplate.keys("*");
        keys
                .map(l -> {
                    logger.info("test1 " + l);
                    return ops.get(l);
                })
                .doOnNext(
                        l -> logger.info("test2 " + l)
                )
                .blockLast();

        logger.info("done");
    }

}

El problema es que obtengo esta salida:

test
test1 key1
test2 MonoNext
test1 key2
test2 MonoNext
test1 key3
test2 MonoNext
test1 key4
test2 MonoNext
done

Esperaría:

test
test1 key1
test2 val1
test1 key2
test2 val2
test1 key3
test2 val3
test1 key4
test2 val4
done

Soy nuevo en rx-java, así que probablemente me esté perdiendo algo.

Tags:  , , ,

Answer

  1. Avatar for davy.ai

    Parece que estás recibiendo un objeto Mono en lugar del valor en sí. Para solucionar esto, debes suscribirte a cada objeto Mono para obtener el valor actual.

    Aquí tienes el fragmento de código actualizado:

    @Service
    class Test {
        Logger logger = LoggerFactory.getLogger(Test.class);
    
        @Autowired
        private ReactiveRedisTemplate<string, string=""> reactiveRedisTemplate;
    
        @EventListener(ApplicationReadyEvent.class)
        public void test() {
            logger.info("test");
            var ops = reactiveRedisTemplate.opsForValue();
            var keys = reactiveRedisTemplate.keys("*");
            keys
                    .flatMap(l -> {
                        logger.info("test1 " + l);
                        return ops.get(l);
                    })
                    .doOnNext(
                            l -> logger.info("test2 " + l)
                    )
                    .subscribe();
    
            logger.info("done");
        }
    }
    

    Ten en cuenta el uso de flatMap en lugar de map para manejar los objetos Mono. Además, utiliza subscribe() en lugar de blockLast() para asegurar que los valores se recuperen de forma asíncrona.

    ¡Espero que esto te ayude!</string,>

Comments are closed.