Введение: Зачем нужно кэширование в JavaScript?
Современные веб-приложения на Node.js обрабатывают миллионы запросов ежедневно. Без грамотного кэширования каждое обращение к базе данных или внешнему API создает задержку, увеличивает нагрузку на сервер и снижает пользовательский опыт. Кэширование — это техника временного хранения часто запрашиваемых данных в быстром хранилище, чтобы при повторном запросе не выполнять тяжелые операции заново.
В экосистеме JavaScript (Node.js) существует три основных подхода к кэшированию:
- Встроенные решения (In-memory cache) — простые библиотеки, хранящие данные в памяти процесса Node.js.
- Memcached — распределенная система кэширования, работающая в оперативной памяти.
- Redis — продвинутое хранилище данных in-memory с поддержкой сложных структур данных.
В этой статье мы подробно разберем каждый подход, приведем примеры кода на JavaScript и поможем выбрать оптимальное решение для вашего проекта.
Встроенные решения для кэширования в Node.js
Самый простой способ организовать кэширование — использовать встроенные возможности JavaScript или легковесные библиотеки. Такие решения не требуют установки внешних сервисов и идеально подходят для небольших проектов или прототипов.
Простой объект-кэш
Базовый пример кэширования с использованием обычного JavaScript-объекта:
class SimpleCache {
constructor() {
this.cache = {};
}
get(key) {
return this.cache[key];
}
set(key, value, ttl = 60000) {
this.cache[key] = value;
setTimeout(() => {
delete this.cache[key];
}, ttl);
}
delete(key) {
delete this.cache[key];
}
clear() {
this.cache = {};
}
}
// Использование
const cache = new SimpleCache();
cache.set('user:123', { name: 'Анна', role: 'admin' }, 30000);
console.log(cache.get('user:123')); // { name: 'Анна', role: 'admin' }
Минусы такого подхода: отсутствие автоматической очистки памяти, утечки при большом количестве ключей, нет поддержки распределенного кэширования.
Библиотека node-cache
Более продвинутый вариант — использовать пакет node-cache:
const NodeCache = require('node-cache');
const myCache = new NodeCache({ stdTTL: 100, checkperiod: 120 });
// Сохраняем данные
myCache.set('key', { data: 'value' });
// Получаем данные
const value = myCache.get('key');
if (value === undefined) {
// Данные не найдены — нужно получить из БД
console.log('Cache miss');
} else {
console.log('Cache hit:', value);
}
// Удаление по ключу
myCache.del('key');
// Статистика
console.log(myCache.getStats());
node-cache поддерживает TTL (время жизни), автоматическую очистку просроченных ключей и базовую статистику. Однако он не подходит для многопроцессных приложений — каждый процесс Node.js хранит свою копию данных.
Memcached: легковесное распределенное кэширование
Memcached — это высокопроизводительная распределенная система кэширования объектов в оперативной памяти. Она идеальна для кэширования результатов запросов к БД, сессий пользователей и HTML-фрагментов.
Установка и подключение Memcached
Сначала установите сервер Memcached и клиент для Node.js:
# Установка сервера (Ubuntu/Debian)
sudo apt-get install memcached
# Установка клиента для Node.js
npm install memcached
Пример работы с Memcached в Node.js
const Memcached = require('memcached');
const memcached = new Memcached('localhost:11211');
// Сохранение данных с TTL (в секундах)
memcached.set('user:456', { name: 'Иван', email: 'ivan@example.com' }, 3600, (err) => {
if (err) console.error('Ошибка сохранения:', err);
});
// Получение данных
memcached.get('user:456', (err, data) => {
if (err) {
console.error('Ошибка получения:', err);
return;
}
if (data) {
console.log('Данные из кэша:', data);
} else {
console.log('Кэш пуст — запрос к БД');
}
});
// Удаление
memcached.del('user:456', (err) => {
if (err) console.error('Ошибка удаления:', err);
});
// Закрытие соединения
memcached.end();
Преимущества Memcached: высокая скорость, простота, поддержка распределенного кэширования. Недостатки: отсутствие персистентности (данные теряются при перезагрузке), ограниченный набор команд, нет поддержки сложных структур данных.
Redis: мощное кэширование с продвинутыми возможностями
Redis — это не просто кэш, а полноценное хранилище данных в памяти с поддержкой строк, списков, хэшей, множеств и даже геопространственных данных. Он стал стандартом для кэширования в современных Node.js-приложениях.
Установка и подключение Redis
# Установка сервера Redis
sudo apt-get install redis-server
# Установка клиента ioredis (рекомендуется)
npm install ioredis
Базовое кэширование с Redis
const Redis = require('ioredis');
const redis = new Redis(); // localhost:6379
// Сохранение строки
await redis.set('session:789', JSON.stringify({ userId: 1, role: 'user' }), 'EX', 3600);
// Получение данных
const data = await redis.get('session:789');
if (data) {
console.log('Сессия из кэша:', JSON.parse(data));
} else {
console.log('Сессия не найдена — создаем новую');
}
// Использование хэшей для сложных объектов
await redis.hmset('user:1', {
name: 'Ольга',
email: 'olga@example.com',
age: 28
});
const user = await redis.hgetall('user:1');
console.log(user); // { name: 'Ольга', email: 'olga@example.com', age: '28' }
Паттерн "кэш-ассид" (Cache-Aside)
Самый распространенный паттерн кэширования с Redis:
async function getUser(id) {
// 1. Проверяем кэш
const cached = await redis.get