Java кешируется и обновляется динамически - PullRequest
1 голос
/ 30 января 2012

Мне нужно предварительно загрузить некоторые данные из базы данных при запуске сервлета.

Так что я подумал создать кеш, например используя HashMap или аналогичную синхронизированную версию.

Мне также необходимо обновить кэш при изменении обновлений базы данных.
Поэтому я подумал добавить какого-нибудь «слушателя».

Мой вопрос: это как-то доступно, или я должен на самом деле реализовать это?

Если да, какой шаблон дизайна будет лучшим подходом здесь?

Обновление:
JPA или ORM не используются. Но весна доступна

Ответы [ 4 ]

3 голосов
/ 03 февраля 2012

Да, конечно, вы можете реализовать это
Я нарисую небольшую архитектуру, а затем объясню вам:

Architecture diagram

Прежде всего, вы можете узнать оКартографы здесь и TDG здесь .У маппера есть метод с именем cacheAll () , который вызывает и делегирует методу TDG cacheAll () , который, в свою очередь, выполняет задачу получения всех строк из таблицы из базы данных (строк, которые вы хотите кэшировать в объекте кеша).

поэтому сначала вам нужно создать слушатель, реализующий "ServletContextListener" , что означает, что он слушает весь контекст сервлета, и внутри contextInitialized вам нужно вызвать mp.fill (Mapper.cacheAll ()) , поэтому это похоже на sthg (это общий код, конечно, лучше его написать и оптимизировать)

public class myServletContextListener implements ServletContextListener{

@Override
public void contextInitialized(ServletContextEvent sce) {
        mp.fill(Mapper.cacheAll());
 }

//
}

Не забудьте добавить ваш слушатель в web.xml:

<listener>
    <listener-class>myServletContextListener </listener-class>
</listener>

, поэтому при запуске сервера он будет кэшировать все записи в mp hashmap.в объекте кэша.

Что касается обновления кэша на основе изменения базы данных, вам придется использовать шаблон наблюдателя .

ОБНОВЛЕНИЕ
Я забыл упомянуть об объекте кэша, я предполагаю, что вы хотите, чтобы он был доступен для всех пользователей или вашего приложения, поэтому вы должны кодировать его как одиночный(одноэлементный шаблон), код такой:

 public class cacheObject
{
    private static Map cMap;
    private static cacheObject cObject;
    private cacheObject()
    {
        cMap = Mapper.cacheAll();
    }
    public static synchronized cacheObject getInstance()
    {
        if (cObject == null){
            cObject = new cacheObject();
        }
        return cObject;
    }

}

Также, если данные, которые вы хотите кэшировать, могут быть изменены пользователями, поэтому сделайте его Threadlocal синглтон.

2 голосов
/ 30 января 2012

Вы можете найти ваши потребности лучше всего по Гуава здесь.Вики статья о кешах, вероятно, наиболее актуальна для вас, но точный подход здесь будет сильно зависеть от условий изменения обновления базы данных.Если вы хотите обновить весь кэш при изменениях обновления базы данных или, по крайней мере, сделать недействительными старые записи, вы можете просто вызывать Cache.invalidateAll() всякий раз, когда происходит обновление базы данных.Если вы хотите, чтобы кэш-память лишь немного отставала от времени, использование CacheBuilder.refreshAfterWrite(long, TimeUnit) может вам помочь.

0 голосов
/ 30 января 2012

У меня действительно был проект на уровне производства, где мне нужно было сделать что-то подобное.Моим решением было (и это просто МОЕ решение) было загрузить объект (ваши "данные") в память при запуске сервлета.Это решение было принято, потому что объект был достаточно большим, чтобы он делал медленные запросы клиентов, чтобы извлечь его из базы данных, и у меня было небольшое количество одновременных пользователей.Любые запросы, которые изменят данные этого объекта в базе данных, также изменят объект в памяти.Конечно, вам нужно использовать синхронизированный объект, если вы работаете с большим количеством пользователей.Если объем данных невелик, вы всегда можете извлечь данные из базы данных каждый раз, когда пользователь запрашивает информацию о данных.

Удачи.

0 голосов
/ 30 января 2012

Hashmap и его потокобезопасный вариант ConcurrentHashMap уже доступен.

Существуют решения для кэширования, такие как ehcache, которые также предоставляют расширенную поддержку, такую ​​как политики выселения и многое другое.

Что касается шаблона проектирования, прочитайте шаблон проектирования Observer.

...