Я тестирую Redis с помощью spring-data-redis, используя такие репозитории:
public interface CreditCardRepository extends CrudRepository<CreditCard, String>{
List<CreditCard> findByIssuer(String issuer);
List<CreditCard> findByCreditNetwork(String creditNetwork);
List<CreditCard> findByCreditNetworkAndIssuer(String creditNetwork, String issuer);
}
Вышеупомянутые методы будут запрашивать структуры Redis, такие как:
creditcard:creditNetwork:mastercard
creditcard:creditNetwork:visa
creditcard:issuer:company1
creditcard:issuer:company2
Прямо сейчас мой объект CreditCard содержит два атрибута (эмитент, сеть и идентификатор), поэтому легко искать такие объекты:
private List<CreditCard> searchCardFromCache(CreditCardGetReq req) {
if (req.getIssuer() != null && req.getNetwork() != null) {
return ccRepository.findByIssuerAndCreditNetwork(req.getIssuer(), req.getNetwork().name());
}
if (req.getIssuer() != null) {
return ccRepository.findByIssuer(req.getIssuer());
}
if (req.getNetwork() != null) {
return ccRepository.findByCreditNetwork(req.getNetwork().name());
}
return null;
}
Однако мне не нравится этот код, так как мне придется создать комбинацию всех свойств, и это будет очень беспорядочно. В будущем я планирую иметь 15 свойств, поэтому цепочка if невозможна.
Я хотел бы спросить вас, как я могу создавать динамические запросы с помощью spring-data-redis, чтобы Redis мог возвращать пересечение на основе свойств объекта лучше, чем проверка каждого свойства?
Пробовали использовать MethodHandle путем жесткого кодирования (я ранее удалил из репозитория findByIssuerAndCreditNetwork
) имя метода, которое будет динамически сгенерировано следующим образом:
MethodType methodType = MethodType.methodType(cardList.getClass(), String.class, String.class);
// Dynamic create 'findByIssuerAndCreditNetwork'
MethodHandle methodHandle = MethodHandles.lookup().findVirtual(CreditCardRepository.class, "findByIssuerAndCreditNetwork", methodType);
Но кажется, что MethodHandle не работает, так как я получил ошибку ниже:
java.lang.NoSuchMethodException: такого метода нет: com.creditcard.dao.CreditCardRepository.findByIssuerAndCreditNetwork (String, String) ArrayList / invokeInterface
CreditCardGetReq
- person Eugene   schedule 01.03.2017MethodHandle
s, а не через рефлексию, которая будет работать, если у вас есть реальный экземпляр репозитория. Проблема в том, что для обработчиков методов явно нужны аргументы вызова. - person Eugene   schedule 01.03.2017RedisCallback
иRedisTemplate
не дадут вам то, что вы хотите? Хотя он будет менее абстрактным, чем при использовании чистых данных Spring - person Leon   schedule 01.03.2017