Кэширование в Java: Redis, Caffeine, Ehcache — полное руководство

Онлайн-тренажер Python для начинающих

Изучайте Python легко и без перегрузки теорией. Решайте практические задачи с автоматической проверкой, получайте подсказки на русском языке и пишите код прямо в браузере — без необходимости что-либо устанавливать.

Начать курс

Кэширование в Java: Redis, Caffeine, Ehcache и JCache

Кэширование — один из ключевых инструментов для повышения производительности Java-приложений. Оно позволяет сократить время отклика, снизить нагрузку на базы данных и внешние API. В этой статье мы разберём три популярных решения: Redis (внешний распределённый кэш), Caffeine (высокопроизводительный in-memory кэш) и Ehcache (гибридный кэш с поддержкой диска). Также рассмотрим стандарт JCache (JSR 107), который унифицирует работу с кэшами.

Зачем нужно кэширование в Java?

Основные сценарии использования:

  • Снижение задержек — данные из кэша возвращаются за микросекунды, а не миллисекунды (как при запросе к БД).
  • Уменьшение нагрузки — кэш защищает базу данных от повторяющихся запросов.
  • Экономия ресурсов — меньше вызовов внешних сервисов → меньше затрат на инфраструктуру.

1. Redis — распределённый кэш для микросервисов

Redis — это in-memory хранилище данных, которое часто используется как распределённый кэш. Он поддерживает различные структуры данных: строки, хеши, списки, множества. Для Java есть два основных клиента: Jedis и Lettuce (рекомендуется для Spring Boot).

Пример подключения через Spring Data Redis:

@Configuration
public class RedisConfig {
    @Bean
    public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory connectionFactory) {
        RedisTemplate<String, Object> template = new RedisTemplate<>();
        template.setConnectionFactory(connectionFactory);
        template.setKeySerializer(new StringRedisSerializer());
        template.setValueSerializer(new GenericJackson2JsonRedisSerializer());
        return template;
    }
}

@Service
public class UserService {
    @Autowired
    private RedisTemplate<String, Object> redisTemplate;

    public User getUserById(String id) {
        String key = "user:" + id;
        User cached = (User) redisTemplate.opsForValue().get(key);
        if (cached != null) return cached;

        User user = database.findUserById(id); // дорогой запрос
        redisTemplate.opsForValue().set(key, user, 10, TimeUnit.MINUTES);
        return user;
    }
}

Плюсы Redis: распределённость, поддержка TTL, pub/sub, персистентность. Минусы: сетевая задержка, потребление памяти на сервере.

2. Caffeine — сверхбыстрый in-memory кэш

Caffeine — это библиотека для локального кэширования, основанная на алгоритме W-TinyLFU. Она обеспечивает почти 100% hit rate при минимальном потреблении памяти. Идеально подходит для однопоточных и многопоточных приложений.

Пример использования Caffeine:

Cache<String, User> cache = Caffeine.newBuilder()
    .expireAfterWrite(5, TimeUnit.MINUTES)
    .maximumSize(10_000)
    .recordStats()
    .build();

public User getUser(String id) {
    return cache.get(id, key -> database.findUserById(key));
}

// Получение статистики
CacheStats stats = cache.stats();
System.out.println("Hit rate: " + stats.hitRate());

Плюсы Caffeine: минимальная задержка (наносекунды), встроенная статистика, автоматическая вытеснение старых записей. Минусы: только локальный кэш, не подходит для распределённых систем.

3. Ehcache — гибридный кэш с записью на диск

Ehcache — одна из старейших библиотек кэширования для Java. Поддерживает кэширование в памяти и на диске, а также кластеризацию через Terracotta. Часто используется в связке с Hibernate.

Пример конфигурации Ehcache 3 (XML):

<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://www.ehcache.org/v3"
        xsi:schemaLocation="http://www.ehcache.org/v3 http://www.ehcache.org/schema/ehcache-core-3.0.xsd">
    <cache alias="users">
        <resources>
            <heap>1000</heap>          <!-- 1000 объектов в памяти -->
            <disk>100MB</disk>         <!-- до 100 МБ на диске -->
        </resources>
        <expiry>
            <ttl>5</ttl>               <!-- время жизни 5 минут -->
        </expiry>
    </cache>
</config>

Пример программного создания кэша:

Рекомендаций