Мы начали использовать DynamoDB в последние несколько недель в нашем проекте, как в качестве кеша, так и в качестве списка событий, которые произошли в системе (пожалуйста, давайте не будем вдаваться в то, почему есть лучшие альтернативы для реализации этого, я сам утверждал это раньше DynamoDB был выбран безрезультатно).
Похоже, что из-за предоставленного ограничения пропускной способности я должен реализовать в своем коде способ повторной попытки необработанных элементов всякий раз, когда превышены ограничения. Это имеет смысл, но также вызывает вопросы относительно пакетных операций или запросов, на которые я не могу ответить самостоятельно.
Я думаю, что BatchPutItem достаточно прост для реализации. Если я получаю необработанные элементы, я просто использую экспоненциальную повторную попытку, и элементы в конечном итоге будут сохранены. Я делаю что-то вроде этого:
(...)
BatchWriteItemOutcome outcome = dynamoDB.batchWriteItem(new TableWriteItems(tableName).withItemsToPut(items));
processUnprocessed(outcome, 0);
(...)
а также
private void processUnprocessed(BatchWriteItemOutcome outcome, int retryNumber) {
if (MapUtils.isEmpty(outcome.getUnprocessedItems())) {
return;
}
if (retryNumber > maxRetries) {
log.error(Joiner.on(" ").join("Unable to process", outcome.getUnprocessedItems().size(), "items after", retryNumber, "tries"));
return;
}
long retryTime = (long)Math.pow(retryFactor, retryNumber);
log.info("Exceeded provisioning throughput. Retrying in " + retryTime);
try {
Thread.sleep(retryTime);
} catch (InterruptedException e) {
log.error(e.getMessage());
}
processUnprocessed(dynamoDB.batchWriteItemUnprocessed(outcome.getUnprocessedItems()), ++retryNumber);
}
Поскольку асинхронные фоновые задачи заполняют БД, это работает нормально.
Однако для запроса или BatchGetItem все не так просто. Конечный пользователь ожидает результата вызова DynamoDB. Я не могу сделать здесь экспоненциальную повторную попытку, иначе пользователь может ждать очень долго. С другой стороны, я тоже не могу не показать все результаты по запрашиваемым ключам.
Есть ли у кого-нибудь предложения о правильном способе (я бы согласился на приличный способ) справиться с этим? Я неправильно подхожу к проблеме?
Я использую Amazon JavaSDK кстати.