Перейти к основному содержимому

Первые шаги с Redis

Разработчику Аналитику Тестировщику
Архитектору Инженеру

Установка системы Redis

Процесс установки СУБД требует выполнения действий в зависимости от операционной системы пользователя. Для работы с базой данных необходим серверный компонент (redis-server) и клиентские утилиты (redis-cli).

Требования к системе

  • Операционная система: Windows, Linux (Debian/Ubuntu/CentOS) или macOS.
  • Права администратора на машине.
  • Доступ к интернету для загрузки установочных пакетов.
  • Минимум 512 МБ оперативной памяти (рекомендуется 1 ГБ).

Алгоритм установки

Вариант А: Установка на Linux (на примере Ubuntu/Debian)

Откройте терминал и выполните следующие команды:

sudo apt update
sudo apt install redis-server

После завершения установки проверьте статус службы:

sudo systemctl status redis

Для входа в интерактивную оболочку используйте команду:

redis-cli

Вариант Б: Установка на Windows

  1. Перейдите на официальный сайт проекта Redis или используйте менеджер пакетов Chocolatey.
  2. Скачайте дистрибутив для Windows (например, версию от Microsoft или официальную сборку).
  3. Запустите исполняемый файл Redis-x64-*.exe.
  4. Следуйте инструкциям мастера установки:
    • Выберите тип установки «Complete».
    • Укажите порт подключения (стандартное значение — 6379).
    • Настройте параметры запуска службы. Рекомендуется выбрать «Run as a service».
  5. Завершите установку и откройте консоль для проверки работы.

Вариант В: Использование Docker (универсальный способ)

Создание контейнера с базой данных позволяет изолировать среду разработки:

docker run --name my-redis \
-d \
-p 6379:6379 \
redis:latest

Подключение к контейнеру выполняется командой:

docker exec -it my-redis redis-cli

Создание базы данных

В Redis понятие «база данных» отличается от реляционных систем. Сервер хранит все данные в одной общей памяти, разделенной на логические пространства имен, называемые базами данных. По умолчанию доступно 16 баз данных (от 0 до 15).

Командный способ

Переключение между базами данных выполняется командой SELECT с указанием номера базы:

SELECT 1

Или использование команды в скриптах:

127.0.0.1:6379> SELECT 1
OK

Графический способ (RedisInsight)

  1. Откройте приложение RedisInsight и подключитесь к локальному серверу.
  2. В левой панели отображаются доступные базы данных.
  3. Нажмите на любую базу (например, DB 1), чтобы работать с ней.
  4. Все ключи, созданные в этой базе, будут видны только в ней.

Важно помнить, что каждая база данных в Redis — это просто логическое разделение одного набора данных. Данные в разных базах могут пересекаться по ключам, но физически они изолированы в рамках сессии.


Создание структур данных и вставка элементов

В отличие от таблиц, в Redis нет жесткой схемы. Данные хранятся в виде ключей и значений. Тип данных определяется при создании ключа. Основные типы: строка (String), список (List), множество (Set), сортированное множество (Sorted Set), хэш (Hash).

Синтаксис вставки строки

Команда SET создает или обновляет строковое значение.

SET company_name "Universe IT"
GET company_name

Результат: "Universe IT"


Синтаксис вставки хэша

Хэш удобен для хранения объектов, таких как профиль сотрудника, где каждый атрибут — это отдельное поле.

HSET employee:1001 first_name "Ivan"
HSET employee:1001 last_name "Ivanov"
HSET employee:1001 email "ivanov@example.com"
HSET employee:1001 salary 75000
HSET employee:1001 hire_date "2024-01-15"

Чтение всех полей хэша:

HGETALL employee:1001

Синтаксис вставки списка

Список используется для очередей задач или ленты новостей. Элементы добавляются в начало или конец.

LPUSH tasks "Review PR #123"
LPUSH tasks "Fix bug in module X"
LPUSH tasks "Deploy to production"

Чтение списка:

LRANGE tasks 0 -1

Анализ компонентов определения

  • Ключ: Уникальный идентификатор элемента. Может быть любым текстом, часто используется префикс (например, employee:) для группировки.
  • Значение: Содержимое элемента. Может быть строкой, числом, объектом или массивом.
  • Тип данных: Определяет доступные операции. Нельзя использовать методы списка для строки.
  • Тайм-аут (TTL): Каждому ключу можно задать время жизни, после которого он удалится автоматически.

Добавление ограничений и индексов

В Redis нет традиционных ограничений целостности (как внешние ключи) и индексов в классическом понимании. Производительность обеспечивается за счет архитектуры in-memory и алгоритмов хеширования. Однако существуют механизмы обеспечения уникальности и ограничения доступа.


Обеспечение уникальности ключей

Уникальность гарантируется самим типом данных «ключ». Если попытаться создать ключ, который уже существует, новое значение перезапишет старое.

Для эмуляции уникальности внутри структуры (например, уникальный email в хэше) необходимо проверять наличие ключа перед вставкой или использовать транзакции.

Пример проверки существования:

EXISTS employee:1001

Если возвращает 1, ключ существует. Если 0 — не существует.


Сценарии оптимизации (вместо индексов)

Redis работает очень быстро без индексов благодаря использованию структур данных, оптимизированных под конкретные операции:

  • Хэши для быстрого доступа по полю (O(1)).
  • Списки для добавления в начало (O(1)).
  • Сортируемые множества для получения топ-N элементов (O(log N)).

Для больших наборов данных рекомендуется использовать шардирование (разделение данных по разным серверам) или кластеризацию Redis Cluster.


Выполнение CRUD операций

CRUD (Create, Read, Update, Delete) в Redis реализуется через специфичные команды для каждого типа данных.

Создание записей (Create)

Вставка строки:

SET user:status "online" EX 3600 NX

Параметры: EX 3600 устанавливает время жизни в секундах (1 час), NX означает создание только если ключ не существует.

Вставка хэша:

HSET user:1001 name "Maria" age 28 city "Ufa"

Вставка списка:

RPUSH notifications "New message from Ivan" "System update"

Чтение данных (Read)

Выборка строки:

GET user:status

Выборка конкретного поля хэша:

HGET user:1001 city

Выборка нескольких полей хэша:

HMGET user:1001 name age

Чтение всего списка:

LRANGE notifications 0 -1

Фильтрация и поиск (для строк):

KEYS user:*

Примечание: Команда KEYS медленная на больших базах данных. В продакшене используют SCAN.


Обновление данных (Update)

Изменение значения строки:

SET user:status "offline"

Обновление поля хэша:

HSET user:1001 salary 80000

Добавление элемента в список:

RPUSH notifications "Alert: Server load high"

Инкрементация числа (счетчик):

INCR counter:page_views
INCRBY counter:downloads 50

Удаление данных (Delete)

Удаление конкретного ключа:

DEL user:1001

Удаление всех ключей, соответствующих шаблону:

DEL $(KEYS user:*)

Важно: Будьте осторожны с удалением большого количества ключей сразу, так как это может заблокировать сервер. Используйте UNLINK для асинхронного удаления.

Очистка всей базы данных (осторожно!):

FLUSHDB

Создание представлений (Views)

В Redis нет концепции представлений (VIEW) в том виде, в котором они есть в SQL или MongoDB. Однако функциональность представлений реализуются через:

  1. Вычисляемые ключи: Ключи, содержащие результат агрегации.
  2. Lua-скрипты: Скрипты, выполняющие сложные запросы и возвращающие результат.
  3. Команды MGET и HMGET: Групповая выборка данных для формирования виртуальной таблицы на стороне клиента.

Пример реализации «представления» через вычисляемый ключ

Представление списка активных сотрудников:

SADD active_employees "user:1001" "user:1002" "user:1003"
SMEMBERS active_employees

Если структура данных меняется, достаточно обновить набор, и «представление» будет актуальным.


Использование Lua-скрипта для сложной логики

Скрипт может выполнить серию команд атомарно и вернуть результат, имитируя сложную выборку.

-- Скрипт для получения имени и зарплаты сотрудника
local name = redis.call('HGET', KEYS[1], 'name')
local salary = redis.call('HGET', KEYS[1], 'salary')
return {name, salary}

Вызов скрипта:

EVAL "local name = redis.call('HGET', KEYS[1], 'name'); local salary = redis.call('HGET', KEYS[1], 'salary'); return {name, salary}" 1 user:1001

Создание функций и процедур с агрегатными функциями и Join

В Redis нет встроенных триггеров или хранимых процедур в классическом понимании. Логика реализуется через:

  1. Lua-скрипты (выполняются на сервере).
  2. Pub/Sub (система публикаций/подписок).
  3. Streams (очереди сообщений).

Функция с агрегатными функциями (через Lua)

Расчет средней зарплаты в отделе (эмуляция JOIN через ключи).

Предположим, у нас есть ключи dept:1:emp:1001, dept:1:emp:1002 и т.д.

-- Lua скрипт для расчета средней зарплаты
local dept_id = ARGV[1]
local keys = {}
local total_salary = 0
local count = 0

-- Получаем список сотрудников отдела (упрощенно, предположим, что имена известны)
-- В реальности нужно использовать SCAN или хранить список ID в SET
for i = 1, 2 do
local emp_key = "dept:" .. dept_id .. ":emp:" .. i
local salary = redis.call('HGET', emp_key, 'salary')
if salary then
total_salary = total_salary + tonumber(salary)
count = count + 1
end
end

if count > 0 then
return total_salary / count
else
return 0
end

Вызов:

EVAL "..." 0 1

Процедура с использованием Pub/Sub (аналог триггера)

Реализация автоматического уведомления при изменении данных.

  1. Подписка на канал:
SUBSCRIBE new_employee_alerts
  1. Отправка сообщения (при вставке нового сотрудника):
PUBLISH new_employee_alerts "Новый сотрудник: Maria Petrova, Зарплата: 82000"

Это позволяет разделить логику записи данных и реакцию на них.


Триггерная логика (Validation Rules)

Проверка условий перед записью реализуется в приложении или через Lua-скрипт, который блокирует операцию при нарушении правил.

Пример проверки: зарплата не может быть отрицательной.

-- Lua скрипт проверки
local key = KEYS[1]
local salary = tonumber(ARGV[1])

if salary < 0 then
return "ERROR: Salary cannot be negative"
end

redis.call('HSET', key, 'salary', salary)
return "OK"

Вызов:

EVAL "..." 1 user:1001 -5000
-- Результат: ERROR: Salary cannot be negative