Java DynamoDB-查询而不是扫描-如何使用随机生成的密钥实现

Java DynamoDB-查询而不是扫描-如何使用随机生成的密钥实现,java,amazon-dynamodb,Java,Amazon Dynamodb,设置 我在java和DynamoDB(DynamoDB映射器)注释中有下表: @DynamoDBTable(tableName="myentity") public class MyEntity { @DynamoDBHashKey @DynamoDBAutoGeneratedKey private String id; @DynamoDBIndexHashKey() //@DynamoDBIndexRangeKey private String userId; private Date e

设置

我在java和DynamoDB(DynamoDB映射器)注释中有下表:

@DynamoDBTable(tableName="myentity")
public class MyEntity {
@DynamoDBHashKey
@DynamoDBAutoGeneratedKey
private String id;

@DynamoDBIndexHashKey()
//@DynamoDBIndexRangeKey
private String userId;

private Date eventDate;
id
在保存时随机生成,多个实体可以使用相同的
userId

通过Web GUI定义的表如下所示: 主分区键:id(字符串) 主排序键:userId(字符串)

问题

我希望一个用户ID的所有实体都有一个查询,而不是扫描

查询-不是这样工作的:

public List<MyEntity> findByUserIdQuery(String userId) {
    Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>();
    eav.put(":val1", new AttributeValue().withS(userId));

    DynamoDBQueryExpression<MyEntity> queryExpression = new DynamoDBQueryExpression<MyEntity>()
        .withKeyConditionExpression("userId = :val1").withExpressionAttributeValues(eav);

    List<MyEntity> list = mapper.query(MyEntity.class, queryExpression);
String partitionKey = forumName + "#" + threadSubject;*
eav.put(":val1", new AttributeValue().withS(partitionKey))
Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>();
DynamoDBQueryExpression<Reply> queryExpression = new DynamoDBQueryExpression<Reply>()
            .withKeyConditionExpression("Id = :val1 and ReplyDateTime > :val2").withExpressionAttributeValues(eav);
因为当我想读取数据时,我不知道生成的id

解决方法

相反,我使用:

public List<MyEntity> findByOwner(String userId){

    Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>();
    eav.put(":val1", new AttributeValue().withS(userId));

    DynamoDBScanExpression scanExpression = new DynamoDBScanExpression()
        .withFilterExpression("userId = :val1").withExpressionAttributeValues(eav);

    List<MyEntity> list = mapper.scan(MyEntity.class, scanExpression);
公共列表findByOwner(字符串userId){
Map eav=newhashmap();
eav.put(“:val1”,新的AttributeValue().with(userId));
DynamoDBScanExpression scanExpression=新的DynamoDBScanExpression()
.withFilterExpression(“userId=:val1”)。WithExpressionAttributeValue(eav);
List=mapper.scan(MyEntity.class,scanExpression);
可能的解决方案

问题是,我从来都不知道随机生成的元素键。当我想读取时,我只知道userId,我想拥有它们的所有实体

我看了下面的例子: …但他们始终知道搜索内容的密钥。他们使用的组合密钥如下:

public List<MyEntity> findByUserIdQuery(String userId) {
    Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>();
    eav.put(":val1", new AttributeValue().withS(userId));

    DynamoDBQueryExpression<MyEntity> queryExpression = new DynamoDBQueryExpression<MyEntity>()
        .withKeyConditionExpression("userId = :val1").withExpressionAttributeValues(eav);

    List<MyEntity> list = mapper.query(MyEntity.class, queryExpression);
String partitionKey = forumName + "#" + threadSubject;*
eav.put(":val1", new AttributeValue().withS(partitionKey))
Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>();
DynamoDBQueryExpression<Reply> queryExpression = new DynamoDBQueryExpression<Reply>()
            .withKeyConditionExpression("Id = :val1 and ReplyDateTime > :val2").withExpressionAttributeValues(eav);
String partitionKey=forumName+“#”+threadSubject*
eav.put(“:val1”,新的AttributeValue().with(partitionKey))
Map eav=newhashmap();
DynamoDBQueryExpression queryExpression=新建DynamoDBQueryExpression()
.withKeyConditionExpression(“Id=:val1和ReplyDateTime>:val2”)。WithExpressionAttributeValue(eav);
问题

  • 我可以使用这个组合分区键的通配符吗?(类似于:“*#myGreatUser”)
  • 关于db设置和其他注释作为关键元素的其他建议
  • 也许是一个我可以用查询代替扫描的索引
  • 也许有人有这种用例的工作示例

您只需切换分区键和排序键即可

@DynamoDBTable(tableName="myentity")
public class MyEntity {

@DynamoDBRangeKey
@DynamoDBAutoGeneratedKey
private String id;

@DynamoDBHashKey
private String userId;

private Date eventDate;
然后使用

public List<MyEntity> findByUserIdQuery(String userId) {
    Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>();
    eav.put(":val1", new AttributeValue().withS(userId));

DynamoDBQueryExpression<MyEntity> queryExpression = new DynamoDBQueryExpression<MyEntity>()
    .withKeyConditionExpression("userId = :val1").withExpressionAttributeValues(eav);

List<MyEntity> list = mapper.query(MyEntity.class, queryExpression);
公共列表findByUserIdQuery(字符串userId){
Map eav=newhashmap();
eav.put(“:val1”,新的AttributeValue().with(userId));
DynamoDBQueryExpression queryExpression=新建DynamoDBQueryExpression()
.withKeyConditionExpression(“userId=:val1”)。WithExpressionAttributeValue(eav);
List=mapper.query(MyEntity.class,queryExpression);

顺便说一句,您提到您认为您的排序键是userId,但在提供的示例中,您有一个id的主散列键和一个userId的全局二级索引散列键。没有排序键。

谢谢它的帮助。太简单了。当我想到web gui
主分区键
DynamoDBHashKey
时,我总是使用uni在我的脑海中是这样的。更好的是,我可以放弃自动生成的
id
,取而代之的是
eventDate
。对于排序键:在web gui中,如果您创建一个表,则在“分区键”后面直接有一个带有“添加排序键”的复选框。