Репозиторий данных MongoDB Spring - методы кеширования

Мне нужно, чтобы вызовы MongoDB были кэшированы с использованием аннотации spring @Cacheable:

public interface SiteRepository extends PagingAndSortingRepository<Site, String>{
    @Cacheable
    List<Site> findByStatus(Site.Status status);
}

К сожалению, аннотирование любого метода в интерфейсе с помощью @Cacheable вызывает следующее исключение:

Я ищу способ кеширования вызовов в БД (что довольно дорого). Любая идея?

Из документации Spring в кешах:


person checklist    schedule 22.11.2014    source источник


Ответы (1)


Spring рекомендует аннотировать только конкретные классы (и методы конкретных классов) аннотацией @ Cache *, вместо аннотирования интерфейсов. Вы, конечно, можете разместить аннотацию @ Cache * на интерфейсе (или методе интерфейса), но это работает только так, как вы ожидаете, если вы используете прокси на основе интерфейса. Тот факт, что аннотации Java не наследуются от интерфейсов, означает, что если вы используете прокси на основе классов (proxy-target-class = "true") или аспект на основе ткачества (mode = "aspectj"), тогда настройки кеширования будут не распознается инфраструктурой проксирования и переплетения, и объект не будет заключен в кэширующий прокси, что было бы определенно плохо.

Вероятно, ваша конфигурация кеша противоречит тому, как Spring создает реализации интерфейсов вашего репозитория во время выполнения.

Вы можете проверить свою конфигурацию кеширования, чтобы она хорошо взаимодействовала с данными Spring (см. здесь для различных вариантов конфигурации кеширования).

Или вы можете сделать это:

В итоге я использовал ваш второй вариант через службу и кэшировал его. Я считаю это довольно громоздким, так как вам нужна дополнительная услуга. Я ожидал, что люди Spring также включат @Cacheable в репозиториях. Спасибо за ответ!

public interface SiteRepository extends PagingAndSortingRepository<Site, String>{
    List<Site> findByStatus(Site.Status status);
}

@Service
public class CachedSiteService {

    @Autowired
    private SiteRepository siteRepository;

    @Cacheable("sites")
    List<Site> findByStatus(Site.Status status) {
        return siteRepository.findByStatus(status);
    }

}
person ESala    schedule 29.10.2015
comment
Применимо ли это также к методам контроллера? Если я добавлю @Cacheable к методу, который возвращает список объектов, будет ли этот список кеширован? Как мне убедиться, что список привязан к идентификатору? - person checklist; 30.10.2015
comment
22 ноября 2014 г., 19:11:06 org.apache.catalina.core.ApplicationContext log СЕРЬЕЗНО: StandardWrapper.Throwable org.springframework.beans.factory.BeanCreationException: ошибка при создании bean-компонента с именем 'example': не удалось ввести автоматически подключенные зависимости; вложенное исключение - org.springframework.beans.factory.BeanCreationException: не удалось автоматически подключить поле: com.example.repositories.mongodb.SiteRepository com.example.siteRepo; вложенное исключение - org.springframework.beans.factory.BeanCreationException: Ошибка при создании bean-компонента с именем siteRepository: завершилась неудачная обработка одноэлементного объекта FactoryBean; вложенное исключение - org.springframework.aop.framework.AopConfigException: не удалось создать подкласс CGLIB класса [класс com.sun.proxy. $ Proxy92]: общие причины этой проблемы включают использование последнего класса или невидимого класса; вложенное исключение - это java.lang.IllegalArgumentException: невозможно создать подкласс класса окончательного класса com.sun.proxy. $ Proxy92 в org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues ​​(AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues. factory.support.AbstractAutowireCapableBeanFactory.populateBean (AbstractAutowireCapableBeanFactory.java:1147) при org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean (AbstractAutowireCapableBeanFactory.java:519) в org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean ( AbstractAutowireCapableBeanFactory.java:458) по адресу org.springframework.beans.factory.support.AbstractBeanFactory $ 1.getObject (AbstractBeanFactory.java:293) по адресу org.springframework.beans.factory.support.SepportDefistryBeans.factory.support.getanaultReefaultSearchDefistry org.springframework.beans.factory.s upport.AbstractBeanFactory.doGetBean (AbstractBeanFactory.java:290) в org.springframework.beans.factory.support.AbstractBeanFactory.getBean (AbstractBeanFactory.java:191) по умолчанию java: 633) в org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization (AbstractApplicationContext.java:932) в org.springframework.context.support.AbstractApplicationContext.refresh . FrameworkServlet.configureAndRefreshWebApplicationContext (FrameworkServlet.java:651) в org.springframework.web.servlet.FrameworkServlet.createWebApplicationContext (FrameworkServlet.java:602) в org.springframevlet.java:602) в org.springframevlet Framework.Framework.webwork.example.java: .springframework.web.servlet.FrameworkServlet.initWebApplicationContext (FrameworkServlet.java:521) в org.springframework.web.servlet.FrameworkServlet.initServletBean (FrameworkServlet.java:462) в org.springframework.web.servlet.FrameworkServlet.initServletBean (FrameworkServlet.java:462) .java: 136) в javax.servlet.GenericServlet.init (GenericServlet.java:160) в org.apache.catalina.core.StandardWrapper.initServlet (StandardWrapper.java:1189) в org.apache.catalina.core.StandardWrapper. loadServlet (StandardWrapper.java:1103) в org.apache.catalina.core.StandardWrapper.load (StandardWrapper.java:1010) в org.apache.catalina.core.StandardContext.loadOnStartup (S tandardContext.java:4935) в org.apache.catalina.core.StandardContext $ 3.call (StandardContext.java:5262) ​​в org.apache.catalina.core.StandardContext $ 3.call (StandardContext.java:5257) в java.util .concurrent.FutureTask.run (Неизвестный источник) в java.util.concurrent.ThreadPoolExecutor.runWorker (Неизвестный источник) в java.util.concurrent.ThreadPoolExecutor $ Worker.run (Неизвестный источник) в java.lang.knownThread.run (Неизвестный источник) в java.lang.knownThread.run Источник) Вызвано: org.springframework.beans.factory.BeanCreationException: не удалось автоматически подключить поле: com.example.repositories.mongodb.SiteRepository com.example.siteRepo; вложенное исключение - org.springframework.beans.factory.BeanCreationException: Ошибка при создании bean-компонента с именем siteRepository: завершилась неудачная обработка одноэлементного объекта FactoryBean; вложенное исключение - org.springframework.aop.framework.AopConfigException: не удалось создать подкласс CGLIB класса [class com.sun.proxy. $ Proxy92]: общие причины этой проблемы включают использование последнего класса или невидимого класса; вложенное исключение - java.lang.IllegalArgumentException: невозможно создать подкласс класса окончательного класса com.sun.proxy. $ Proxy92 в org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor $ AutowiredFieldElement.inject (AutowiredBeanPostProcessor beans.factory.annotation.InjectionMetadata.inject (InjectionMetadata.java:87) в org.springframework.beans.factory.annotation. AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues ​​(AutowiredAnnotationBeanPostProcessor.java:286) ... еще 27 Причина: org.springframework.beans.factory.BeanCreationException: Ошибка при создании bean-компонента с именем 'siteRepository Factory вложенное исключение - org.springframework.aop.framework.AopConfigException: не удалось создать подкласс CGLIB класса [class com.sun.proxy. $ Proxy92]: общие причины этой проблемы включают использование последнего класса или невидимого класса; вложенное исключение - это java.lang.IllegalArgumentException: невозможно создать подкласс класса окончательного класса com.sun.proxy. $ Proxy92 в org.springframework.beans.factory.support.FactoryBeanRegistrySupport.getObjectFromFactoryBean (FactoryBeanRegistrySupport.getObjectFromFactoryBean (FactoryBeanRegistrySupport). factory.support.AbstractBeanFactory.getObjectForBeanInstance (AbstractBeanFactory.java:1465) в org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean (AbstractBeanFactory.java.dragon.support.framework.java.support. AbstractBeanFactory.java:191) по адресу org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates (DefaultListableBeanFactory.java:917) в org.springframework.beans.factoryLactoryDepport.java: .springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency (DefaultListableBeanFactory.j ava: 775) в org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor $ AutowiredFieldElement.inject (AutowiredAnnotationBeanPostProcessor.java:489) ... 29 еще of class [class com.sun.proxy. $ Proxy92]: Общие причины этой проблемы включают использование последнего класса или невидимого класса; вложенное исключение - java.lang.IllegalArgumentException: невозможно создать подкласс последнего класса класса com.sun.proxy. $ Proxy92 в org.springframework.aop.framework.CglibAopProxy.getProxy (CglibAopProxy.java:218) в org.spring.framework.aop ProxyFactory.getProxy (ProxyFactory.java:109) в org.springframework.aop.framework.autoproxy.AbstractAutoProxyCreator.createProxy (AbstractAutoProxyCreator.java:477) в org.springProxyCreator.java:477) в org.springProxywhomework.aop.framework.autoproxy.Aproxy.framework.autop 362) по адресу org.springframework.aop.framework.autoproxy. AbstractAutoProxyCreator.postProcessAfterInitialization (AbstractAutoProxyCreator.java:322) в org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyBeanPostProcessorsAfterInitialization (AbstractAutowireCapableBeanFactory.java:409) в org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.postProcessObjectFromFactoryBean (AbstractAutowireCapableBeanFactory.java: 1656) в org.springframework.beans.factory.support.FactoryBeanRegistrySupport.getObjectFromFactoryBean (FactoryBeanRegistrySupport.java:112) ... еще 36 Вызвано: java.lang.IllegalArgumentException: java.lang.IllegalArgumentException: Cannot subclass classproxy. на org.springframework.cglib.proxy.Enhancer.generateClass (Enhancer.java:446) на org.springframework.cglib.transform.TransformingClassGenerator.generateClass (TransformingClassGenerator.java:33) на org.springGenerator.java:33) на org. (DefaultGeneratorStrategy.java : 25) на org.springframework.cglib.core.AbstractClassGenerator.create (AbstractClassGenerator.java:216) на org.springframework.cglib.proxy.Enhancer.createHelper (Enhancer.java:377) на org.springframework.cglib. Enhancer.create (Enhancer.java:285) at org.springframework.aop.framework.CglibAopProxy.getProxy (CglibAopProxy.java:206) ... еще 43 - person AlexCon; 20.09.2016