1

我开始在这里学习 Dynamodb,目前正在尝试在我的表上进行搜索,其中 PK 是分区键,SK 是范围键。PK 包含一个电子邮件地址,而 SK 包含诸如AB_STATE, BC_STATE,之类的值MY_STATE。所以我想在 SK 中搜索值开始的地方,MY_但我不完全确定如何使用.get()函数来完成它。

这是我的查询Seller.get({ "PK": "imin@cats.com", "SK" : "MY" }),显然没有做我想要的。

我知道我也许可以使用下面的过滤器,但我在很多地方读到不推荐使用过滤器(?)

var filter = new dynamoose.Condition().where("PK").eq(email).filter("SK").beginsWith("MY_");
var premiseProfile = await Seller.query(filter).exec()

下面是我的卖方表的架构

const schema = new dynamoose.Schema({
    PK: {
        type: String,   
        hashKey: true,
    },
    SK: {
        type: String,   
        rangeKey: true,
    },
    "firstName": String,
    "lastName": String,
    "gender": {
        "type": Number,
        "default": 0
    },
}, {
    "saveUnknown": true,
    "timestamps": true
});
4

1 回答 1

2

拨打Model.get电话时,您必须传入一个完整的密钥。您不能传入以开头的密钥。这是因为它Model.get只会返回 1 个项目,并且查询表明您在那里可能有多个项目。

由于您没有发布架构,因此很难准确回答您的问题。但看起来query在这种情况下做 a 还不错,因为您正在查询数据而不是过滤数据。


基于评论的更多信息。

我意识到condition.filter文档并没有真正涵盖这一点。基本上取决于您的架构,它将确定最佳索引,并以它知道的最佳方式对其进行优化。

例如,如果您有以下代码:

const dynamoose = require("dynamoose");

(async () => {
    dynamoose.model.defaults.set({
        "create": false,
        "waitForActive": false
    });

    const schema = new dynamoose.Schema({
        "PK": {
            "type": String,
            "hashKey": true
        },
        "SK": {
            "type": String,
            "rangeKey": true
        }
    });

    const Model = dynamoose.model("User", schema);

    dynamoose.logger.providers.add(console);

    const filter = new dynamoose.Condition().where("PK").eq("test@test.com").filter("SK").beginsWith("MY_");
    const premiseProfile = await Model.query(filter).exec()
})();

它将产生以下输出:

aws:dynamodb:query:request - {
    "ExpressionAttributeNames": {
        "#qha": "PK",
        "#qra": "SK"
    },
    "ExpressionAttributeValues": {
        ":qhv": {
            "S": "test@test.com"
        },
        ":qrv": {
            "S": "MY_"
        }
    },
    "TableName": "User",
    "KeyConditionExpression": "#qha = :qhv AND begins_with (#qra, :qrv)"
}

如您所见,它使用KeyConditionExpression的是FilterExpression.

所以你没有过滤。如果它对您更有意义,您可以使用condition.whereor condition.attribute

需要注意的是,在某些情况下它会使用FilterExpression. 但它会首先查看您的架构并尝试查看它是否可以使用KeyConditionExpression,如果可以,它将使用它,否则它将使用FilterExpression.

于 2021-03-20T19:10:19.860 回答