Kotlin SDK v2查询DynamoDB GSI报错:缺少键架构元素
问题原因及解决方案
这个报错的核心原因是你没有指定查询目标GSI,默认在查询主表。主表的主键是PartitionKey(分区键)+SortKey(排序键),而你用AuthorId作为分区键条件去查主表,主表的键结构里根本没有AuthorId这个分区键,自然会触发主键条件缺失的错误。
解决步骤
1. 确保实体类正确映射GSI
首先要在你的数据类中,用DynamoDB增强客户端的注解标记GSI的主键:
@DynamoDbBean data class YourEntity( // 主表主键 @get:DynamoDbPartitionKey var PartitionKey: String? = null, @get:DynamoDbSortKey var SortKey: String? = null, // GSI的分区键 @get:DynamoDbSecondaryIndexPartitionKey(indexNames = ["by-users-gsi"]) var AuthorId: String? = null, // GSI的排序键(与GSI定义的SortKey对应,若和主表SortKey为同一字段则直接标注) @get:DynamoDbSecondaryIndexSortKey(indexNames = ["by-users-gsi"]) var SortKey: String? = null, // 其他业务字段 var content: String? = null )
2. 查询时指定使用GSI并构建正确条件
在查询代码中,必须通过index()方法指定要查询的GSI名称,再基于GSI的主键构建条件:
// 初始化增强异步客户端 val enhancedAsyncClient = DynamoDbEnhancedAsyncClient.builder() .dynamoDbClient(DynamoDbAsyncClient.create()) .build() // 获取表对象 val table = enhancedAsyncClient.table("table-name", TableSchema.fromBean(YourEntity::class.java)) // 构建GSI的查询条件:分区键精确匹配,排序键范围筛选 val queryConditional = QueryConditional.keyEqualTo( Key.builder() .partitionValue("author_id") // GSI分区键AuthorId的目标值 .sortValue(ConditionSortKey.builder() .between("value_1", "value_2") .build()) .build() ) // 执行查询,关键是调用index()指定目标GSI val queryPage = table.query(QueryEnhancedRequest.builder() .queryConditional(queryConditional) .index("by-users-gsi") // 必须显式指定要查询的GSI .build()) // 异步处理查询结果 queryPage.thenAccept { page -> page.items().forEach { entity -> // 处理查询到的实体数据 } }
关键注意点
- 必须显式指定
index("by-users-gsi"),否则增强客户端默认查询主表,导致主键不匹配。 - 确保GSI的名称和DynamoDB控制台定义的完全一致(大小写敏感)。
- 查询条件必须基于GSI的主键:分区键必须精确匹配,排序键可使用范围条件(between/lessThan/greaterThan等)。
内容的提问来源于stack exchange,提问作者GreatNews
相关产品推荐
相关产品推荐

