Использовать Spring данные Cassandra Reactive или нет - PullRequest
0 голосов
/ 23 декабря 2018

У меня есть следующий сценарий:

Для данного запроса мы вызываем функцию с 2 различными наборами параметров.Результаты этих функций агрегируются и отправляются в виде карты.Вызываемая функция возвращает CompletableFuture.Функция выдает максимум 4 асинхронных (прослушиваемых) запроса кассандры.Результаты запросов обрабатываются в порядке их выдачи.На основании некоторых условий функция может вернуть после обработки ответа первого запроса или обработать все ответы, чтобы получить желаемый результат.

Функция

@Async
public Map<String,Price> getPricing(String assetType,String code) {
//Issue Query 1 - Returns ListenableFuture
//Issue Query 2 
//Issue Query 3
//Issue Query 4

Query 1 result satisfies return , else continue to Query 2 , followed by 3 and 4.
}

Служба

public Map<String,Price> getPrice(String assetType) {

CompletableFuture<Map<String,Price>> a = .getPrice(assetType,"A");
CompletableFuture<Map<String,Price>> b = .getPrice(assetType,"B");

//Join A and B and return the result
}

Является ли это лучшим кандидатом в Spring Cassandra для данных Webflux + Reactive Spring?Каков будет подход к реализации?

1 Ответ

0 голосов
/ 23 декабря 2018

Если честно, трудно ответить без подробностей.Главным образом, какому условию должен удовлетворять результат запроса, чтобы прекратить оценку и вернуть результат.Условная логика сложна при работе с потоками.Что вы можете сделать, например:

public Mono<Map<String, Person>> findCustomersAndGroupByName(){
    List<String> customer_id = ImmutableList.of("customer id 1", "customer id 2");

    return customerRepo
            .findAllById(customer_id)
            .filter(customer -> customer.getLastname().equals("Smith"))
            .switchIfEmpty(archivedCustomersRepo.findAllById(customer_id)) //if non of the customers has last name smith this will be evaluated
            .filter(customer -> customer.getLastname().equals("Smith"))
            .switchIfEmpty(associatedCustomersRepo.findAllById(customer_id)) //if non of the customers has last name smith this will be evaluated
            .filter(customer -> customer.getLastname().equals("Smith"))
            .collectMap(person -> person.getFirstname()) //grup by first name and return
    ;

}

это все реактивные репозитории.они выглядят так:

public interface ArchivedCustomersRepo extends ReactiveCassandraRepository<Person, String> {}

Но вы должны принять во внимание, что для того, чтобы воспользоваться преимуществами реактивного подхода, все должно быть реактивным (не блокирующим).Это также означает, что ваша служба (я полагаю, у вас есть ответ службы покоя в конце всего этого) должна вернуть mono, flux.

Стоит ли это того?Это зависит от бизнес-кейса, с которым вы имеете дело.Как правило, если у вас есть большое существующее приложение, ответ - нет.Поскольку для того, чтобы перевести ваше мышление (и ваших коллег) на более дорогой стиль функционального программирования, требуется интенсивное использование лямбда-выражений, это требует больших затрат.Это заняло у меня 2 года.

Дайте мне знать, если у вас есть какие-либо вопросы.

...