Python - 如何使用主键和排序键在 GSI 上查询 DynamoDB

问题描述 投票:0回答:3

嗯,正如标题所示,我想使用带有主键和排序键(均来自 GSI)的 GSI 来查询 DynamoDB 表。我尝试了一些方法,但都成功了。

我有一个带有

url-date-index
的表,
url
是来自 GSI 的主键,
date
是排序键。

我尝试了以下方法:

  1. KeyConditionExpression
    &
    比较器一起使用:

    这个给我找回了错误:

    TypeError: expected string or bytes-like

boto3.resource('dynamodb').Table('table').query(
    IndexName='url-date-index',
    KeyConditionExpression=conditions.Key('url')).eq(url) & conditions.Key('date')).eq(date)
)
  1. 使用

    KeyConditionExpression
    FilterExpression

    这检索到以下错误:

    Filter Expression can only contain non-primary key attributes

boto3.resource('dynamodb').Table('table').query(
    IndexName='url-date-index',
    KeyConditionExpression=conditions.Key('url')).eq(url),
    FilterExpression=conditions.Key('date')).eq(date)
)
  1. 使用

    ExpressionAttributeNames
    ExpressionAttributeValues
    KeyConditionExpression

    这返回了任何内容,甚至不是与桌子上的

    url
    date
    匹配的项目。

boto3.resource('dynamodb').Table('table').query(
    IndexName='url-date-index',
    ExpressionAttributeNames={
        '#n0': 'url',
        '#n1': 'date'
    },
    ExpressionAttributeValues={
        ':v0': url,
        ':v1': date
    },
    KeyConditionExpression='(#n0 = :v0) AND (#n1 = :v1)'
)

有谁知道我做错了什么或者我可以做些什么来使这项工作成功。

python amazon-web-services amazon-dynamodb boto3
3个回答
2
投票

在您的特定用例中,您需要使用

ExpressionAttributeNames
,因为您的属性名称
url
date
是 DynamoDB 中的 保留字

有关查询辅助 idnexes 的 DynamoDB 文档 提供了一个结构正确的查询示例,我们可以将其应用于您的情况:

以此为指导,我们可以构造查询操作的参数应该是什么样子。例如

 {
    "TableName": "table",
    "IndexName": "url-date-index",
    "KeyConditionExpression": "#pk = :pk And #sk = :sk",
    "ExpressionAttributeNames": {"#pk":"url","#sk":"date"},
    "ExpressionAttributeValues": {":pk": {"S":url},":sk": {"S":date}}}
}

如果这仍然不适合您,请考虑查看NoSQL Workbench For DynamoDB。在它的许多有用功能中,它有一个操作生成器,可以帮助您使用图形界面构建 DynamoDB 操作。您甚至可以针对实时数据库运行该操作。一旦您的操作按您想要的方式工作,该工具就可以将操作转换为完整的 Phython、Javascript(Node) 或 Java 代码示例,您可以使用它来查看操作是如何构造的。


1
投票

query 是一个带有一些命名参数的函数(

IndexName
KeyConditionExpression
、...)。

让我们尝试像普通函数一样调用带有命名参数的函数:

boto3.resource('dynamodb').Table('table').query(
    IndexName='url-date-index', 
    KeyConditionExpression=conditions.Key('url')).eq(url) & conditions.Key('date')).eq(date)
)

0
投票

只需用两个表达式创建

KeyConditionExpression
即可。一个带有分区键,另一个带有排序键。

该视频有助于逐步找到答案和所有 DynamoDB 相关查询(插入、删除、使用 GSI 查询、使用本地索引查询等) https://youtu.be/x8IxY4zoBGI

Python代码如下。

customer_id
是分区键,
order_id
是排序键。

def query_by_partition_key_and_sort_key(customer_value, order_value):
    response = {}
    filtering_exp = Key('customer_id').eq(customer_value)
    filtering_exp2 = Key('order_id').eq(order_value)
    response = demo_table.query(
        KeyConditionExpression=filtering_exp and filtering_exp2)
    
    for item in response["Items"]:
        print(f'Item: {item}')
© www.soinside.com 2019 - 2024. All rights reserved.