DynamoDB — управляемый NoSQL с предсказуемой задержкой на любом масштабе. Но он требует развернуть мышление: данные моделируют под запросы, а не под нормализацию. Кто приходит из реляционного мира и проектирует DynamoDB «как таблицы», получает либо дорогие сканы, либо невозможность ответить на нужный запрос. Поэтому ключевое в DynamoDB — модель доступа.

Ключи

У элемента есть первичный ключ из одной или двух частей:

  • Partition key — определяет, в какую физическую партицию ляжет элемент. От него зависит распределение нагрузки: плохой ключ (мало значений, перекос) создаёт «горячую» партицию-бутылочное горлышко.
  • Sort key (опционально) — упорядочивает элементы внутри партиции, даёт запросы по диапазону и иерархии (begins_with, between).

Запрос (Query) эффективен только по ключу: «дай элементы с этим partition key и sort key в диапазоне». Всё, что не по ключу, — это Scan (полный перебор), дорогой и медленный. Отсюда правило: сначала пойми запросы, потом выбери ключи.

Индексы: GSI и LSI

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

  • GSI (Global Secondary Index) — свой partition+sort key, отдельная ёмкость; можно добавить в любой момент; eventually consistent.
  • LSI (Local Secondary Index) — тот же partition key, другой sort key; задаётся при создании таблицы; делит ёмкость с таблицей.

GSI — основной инструмент дополнительных паттернов доступа. Каждый индекс — это копия данных (с проекцией нужных атрибутов), за которую платят, поэтому индексы заводят под конкретные запросы, а не «на всякий случай».

Ёмкость: on-demand против provisioned

Два режима оплаты пропускной способности:

  • On-demand — платишь за запрос, масштабируется мгновенно сам. Для непредсказуемой/спайковой нагрузки и старта — просто и без управления.
  • Provisioned — задаёшь единицы чтения/записи (с авто-масштабированием). Дешевле при стабильной предсказуемой нагрузке.

Начинают обычно с on-demand, переходят на provisioned, когда нагрузка устоялась и важна цена (оптимизация затрат).

Консистентность и single-table

Чтение по умолчанию eventually consistent (дёшево, но может вернуть чуть устаревшее); по запросу — strongly consistent (дороже, актуальные данные). GSI всегда eventually consistent — это закладывают в дизайн.

Single-table design — продвинутый приём DynamoDB: разные типы сущностей в одной таблице, чтобы одним запросом достать связанные данные (заказ и его позиции). Мощно, но сложно; для многих сервисов проще несколько таблиц. Это осознанный выбор, не обязательная практика.

Когда DynamoDB, а когда RDS

Граница, которую важно проговорить:

  • DynamoDB — известные паттерны доступа по ключу, огромный масштаб, предсказуемая задержка, простые запросы (сессии, профили, события, корзины).
  • RDS — сложные запросы, join'ы, агрегаты, транзакции по нескольким сущностям, отчётность; когда модель доступа меняется и нужна гибкость SQL.

DynamoDB не «лучше» или «хуже» — он про другой класс задач. Выбор «реляционка vs документная/ключ-значение» — это та же развилка хранилища, что обсуждается для PostgreSQL и MongoDB.

Где это в UCP

DynamoDB добавляет в managed-данные AWS нишу ключ-значение с предсказуемой задержкой на масштабе — ценой того, что данные моделируют под запросы заранее. Для backend-разработчика практический вывод: DynamoDB берут, когда паттерны доступа известны и стабильны, и проектируют ключи под них; если нужна гибкость SQL и сложные связи — это RDS. Осознанный выбор хранилища под задачу — часть продуктового мышления, не вкусовщина.