Разбивка на страницы с фильтрацией с использованием операции запроса в шаблоне DynamoDB - PullRequest
1 голос
/ 10 апреля 2020

Я бы хотел иметь возможность отфильтровать результаты разбивки на страницы с помощью операции запроса до того, как будет учтен лимит. Есть ли какие-либо предложения по правильной разбивке на страницы отфильтрованных результатов?

Я хотел бы реализовать DynamoDB Запрос сканирования ИЛИ со следующими логинами c:

Scanning -> Filtering(boolean true or false) -> Limiting(for pagination)

Однако мне удалось реализовать запрос сканирования ИЛИ только с этим логом c:

Scanning -> Limiting(for pagination) -> Filtering(boolean true or false)

Примечание: Я уже пробовал Global Secondary Index, но в моем случае он не работал, потому что у меня есть 5 различных атрибутов для фильтрации и ограничения.

1 Ответ

1 голос
/ 11 апреля 2020

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

Давайте проверим ваш пример - у вас логическое значение и у вас есть индекс по этому полю. Допустим, 50% предметов являются ложными, а 50% правдивыми. После поиска по этому индексу вы прочитаете 50% всех элементов в таблице (так что это почти как SCAN). Если вы установите предел, он будет читать только это количество элементов, а затем остановится. Вы не можете использовать комбинацию limit и skip/page/offset, как в других базах данных.

Существует некоторый уровень разбиения на страницы https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Query.Pagination.html, но он не позволяет перейти на страницу 10, он только позволяет go по всем страницам по одной. Кроме того, я не уверен, как он оценивается, может быть, внутренне AWS будет go по всем пунктам до подготовки результатов для вас, поэтому вы будете платить за чтение 50% всей таблицы, даже если вы прекратите итерации до того, как достигнете конец.

Существует также ограничение, что индекс может иметь максимум 2 поля (раздел, сортировка).


ПРИМЕР

Вы написали, что у вас есть 5 параметры, которые вы хотите запросить. Обходной путь, используемый для устранения этих ограничений, заключается в создании и управлении дополнительными полями, которые содержат комбинацию параметров, которые вы хотите запросить. Допустим, у вас есть таблица пользователей, и у вас есть gender, age, name, surname and position. Допустим, это огромная база данных, поэтому вам нужно подумать о количестве данных, которые вы можете загрузить. Затем, если вы хотите использовать DynamoDB, вам нужно подумать обо всех запросах, которые вы хотите сделать.

Скорее всего, вы хотите искать по имени и фамилии, поэтому вы создаете индекс с фамилией в качестве ключа раздела и именем в качестве сортировки ключ (в этом случае вы можете искать по фамилии или по фамилии и имени). Это может работать для большого количества имен, но вы обнаружили, что некоторые комбинации имен слишком распространены, и вам также необходимо отфильтровать по позиции. В таком случае вы создаете новое поле (столбец) с именем, например, name-surname, и всякий раз, когда вы создаете или обновляете элемент, вам нужно будет обработать это поле в своем приложении, чтобы убедиться, что оно содержит оба поля, то есть will-smith. Затем вы можете создать другой индекс, который будет иметь name-surname в качестве ключа раздела и position в качестве ключа сортировки. Теперь вы можете использовать его для таких поисков.

Однако вы узнали, что для некоторой комбинации имя-фамилия-позиция вы получаете слишком много результатов, и вы не хотите обрабатывать их на уровне приложения и хотите ограничить результаты. по возрасту. Затем вы можете создать индекс с name-surname-position в качестве ключа раздела и возрастом в качестве ключа сортировки. В этот момент вы также можете выяснить, что ваше старое поле name-surname и индекс могут быть удалены, так как он больше не имеет смысла (имя и фамилия обрабатываются другим индексом, и для поиска только name-фамилия-позиция вы можете использовать этот индекс)

Вы также хотите делать запросы по полу? Вероятно, лучше обрабатывать это на уровне приложения (или дополнительного фильтра в запросе базы данных), а не создавать новый индекс, который должен обрабатываться и оплачиваться. Есть только два типа пола (хорошо, допустим, существует больше, но у 99% людей будет только мужчина или женщина), поэтому, вероятно, дешевле просто скрыть несколько полей на уровне приложения, если кто-то хочет проверить только мужчину / женщину / трансгендеры ..., но загрузи их всех. Потому что за дополнительный индекс вам придется платить за каждую отдельную вставку, но этот фильтр будет использоваться только время от времени. Кроме того, когда кто-то ищет уже по имени, фамилии и положению, вы все равно не ожидаете такого большого количества результатов, поэтому, если вы получите результаты 20 (для всех полов) или только 10 (только для мужчин), не имеет большого значения.


Этот ^^ был просто примером того, как вы можете думать и работать с DynamoDB. Как именно вы его используете, зависит от вашей бизнес-логики c.

Очень важное примечание: DynamoDB - очень простая база данных, которая может выполнять только очень простые запросы. Он имеет немного больше функциональности, чем Redis, но гораздо меньше функциональности, чем традиционные базы данных. Действительный результат размышления о вашей бизнес-модели / сценариях использования заключается в том, что, возможно, вам вообще НЕ следует использовать DynamoDB, поскольку он может просто не удовлетворить ваши потребности и запросы.

Некоторые основы c мышления могут выглядеть как это:

  • Достаточно ли постоянного хранилища с ключом-значением? Использовать DynamoDB
  • Является ли постоянное хранилище со значением ключа, где один элемент может иметь несколько ключей, и я могу выполнять поиск и фильтрацию максимум по двум полям? Использовать DynamoDB
  • Является ли постоянное хранилище, где я хочу искать в одной таблице / коллекции по множеству ключей с достаточным количеством опций? Использовать MongoDB
  • Нужно ли искать в нескольких таблицах или выполнять сложные объединения или требовать транзакций? Используйте традиционную SQL базу данных
...