Java 查询 DynamoDB

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/19502518/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 17:48:12  来源:igfitidea点击:

Querying DynamoDB

javaamazon-web-servicesconditional-statementsamazon-dynamodb

提问by Diferdin

I've got a DynamoDB table with a an alpha-numeric string as a hash key (e.g. "d4ed6962-3ec2-4312-a480-96ecbb48c9da"). I need to query the table based on another field in the table, hence I need my query to select all the keys such as my field x is between dat x and date y.

我有一个 DynamoDB 表,其中包含一个字母数字字符串作为哈希键(例如“d4ed6962-3ec2-4312-a480-96ecbb48c9da”)。我需要根据表中的另一个字段查询表,因此我需要我的查询来选择所有键,例如我的字段 x 在 dat x 和日期 y 之间。

I know I need a condition on the hash key and another on a range key, however I struggle to compose a hash key condition that does not bind my query to specific IDs.

我知道我需要一个关于散列键的条件和另一个关于范围键的条件,但是我很难编写一个不会将我的查询绑定到特定 ID 的散列键条件。

I thought I could get away with a redundant condition based on the ID being NOT_NULL, but when I use it I get the error:

我以为我可以摆脱基于 ID NOT_NULL 的冗余条件,但是当我使用它时,我得到了错误:

Query key condition not supported

不支持查询键条件

Below is the conditions I am using, any idea how to achieve this goal?

以下是我正在使用的条件,知道如何实现这一目标吗?

 Condition hashKeyCondition = new Condition()
 .withComparisonOperator(ComparisonOperator.NOT_NULL.toString());

Condition rangeCondition = new Condition()
.withComparisonOperator(ComparisonOperator.BETWEEN.toString())
.withAttributeValueList(new AttributeValue().withS(dateFormatter.print(lastScanTime())), 
new AttributeValue().withS(dateFormatter.print(currentScanTime)));

Map<String, Condition> keyConditions = new HashMap<String, Condition>();
keyConditions.put("userId", hashKeyCondition);
keyConditions.put("lastAccesTime", rangeCondition);

Thanks in advance to everyone helping.

在此先感谢大家的帮助。

采纳答案by aaaristo

In DynamoDB you can get items with 3 api:

在 DynamoDB 中,您可以使用 3 个 api 获取项目:

. Scan(flexible but expensive),

. 扫描(灵活但昂贵),

. Query(less flexible: you have to specify an hash, but less expensive)

. 查询(不太灵活:你必须指定一个散列,但更便宜)

. GetItem(by Hash and, if your table has one, by range)

. GetItem(按哈希,如果您的表有一个,则按范围)

The only way to achieve what you want is by either:

实现您想要的唯一方法是:

  1. Use Scan, and be slow or expensive.

  2. Use another table (B) as an index to the previous one (A) like:

    B.HASH = 'VALUES' B.RANGE = userid
    B.lastAccesTime = lastAccesTime (with a secondary index)

  1. 使用扫描,缓慢或昂贵。

  2. 使用另一个表 (B) 作为前一个 (A) 的索引,例如:

    B.HASH = 'VALUES' B.RANGE = userid
    B.lastAccesTime = lastAccesTime(带有二级索引)

Now you have to maintain that index on writes, but you can use it with the Query operation, to get your userIds. Query B: hash='VALUES', lastaccessTime between x and y, select userid.

现在您必须在写入时维护该索引,但您可以将它与 Query 操作一起使用,以获取您的 userId。查询 B:hash='VALUES',x 和 y 之间的 lastaccessTime,选择用户 ID。

Hope this helps.

希望这可以帮助。

回答by John Kelvie

The NOT_NULL comparison operator is not valid for the hash key condition. The only valid operator for the Hash key condition on a query is EQ. More information can be found here: http://docs.aws.amazon.com/amazondynamodb/latest/APIReference/API_Query.html

NOT_NULL 比较运算符对哈希键条件无效。查询中哈希键条件的唯一有效运算符是 EQ。更多信息可以在这里找到:http: //docs.aws.amazon.com/amazondynamodb/latest/APIReference/API_Query.html

And what this means is that a query will not work, at least as your table is currently constructed. You can either use a Scan operation or you can create a separate table that stores the data by Date (hash) and User ID (range).

这意味着查询将不起作用,至少在您的表当前构建时是这样。您可以使用 Scan 操作,也可以创建一个单独的表,按日期(散列)和用户 ID(范围)存储数据。

Good luck!

祝你好运!

回答by Diferdin

I ended up scanning the table and enforcing a filter.

我最终扫描了表格并执行了过滤器。

Thanks to everyone taking time for helping out!

感谢大家抽出时间帮忙!

回答by irriss

You could add Global Secondary Index with, for example, year and month of your date and make it your hash key, range key for that index would be your date then you could query any data range in a certain month. It will help you avoid expensive full scan.

您可以添加全局二级索引,例如您日期的年份和月份,并使其成为您的哈希键,该索引的范围键将是您的日期,然后您可以查询某个月份的任何数据范围。它将帮助您避免昂贵的全面扫描。

E.g.

例如

Global Secondary Index:
Hash key: month_and_year for example '2014 March'
Range key: full_date

Hope it helps!

全局二级索引:
哈希键:month_and_year 例如“2014 年三月”
范围键:full_date

希望有帮助!

回答by irriss

You need to create GSI if you want to query other than Partition Key. Scan is very expensive in terms of cost and performance.

如果要查询除 Partition Key 以外的内容,则需要创建 GSI。就成本和性能而言,扫描非常昂贵。