首页 > 解决方案 > SQLX 中查询结果的控制流(懒惰/渴望)

问题描述

我正在使用 postgres (aws-rds) 实现一个消息表,并且我使用 golang 作为后端来查询该表。

创建表:

CREATE TABLE IF NOT EXISTS msg.Messages(
    id SERIAL PRIMARY KEY,
    content BYTEA,
    timestamp DATE
);

这是插入查询:

INSERT INTO msg.Messages (content,timestamp) VALUES ('blob', 'date')
RETURNING id;

现在我希望能够获取特定消息,如下所示:

特定的 SELECT 查询:

SELECT id, content,timestamp
FROM msg.Messages
WHERE id = $1

现在假设用户长时间离线,他需要从这个表中获取大量消息,假设 10M 消息,我不想返回所有结果,因为它可能会爆炸应用程序内存。

每个用户保存他获取的最后一个 message.id,因此查询将是:

SELECT id, content, timestamp
FROM msg.Messages
WHERE id > $1

在这个查询中实现分页感觉就像再次发明轮子,必须有开箱即用的解决方案。

我正在使用 sqlx,这是我的代码的粗略示例:

query := `
        SELECT id, content, timestamp
        FROM msg.Messages
        WHERE id > $0
    `

args = 5
query = ado.db.Rebind(query)
rows, err := ado.db.Queryx(query, args...)
var res []Message

for rows.Next() {
    msg := Message{}
    err = rows.StructScan(&msg)
    if err != nil {
        return nil, err
    }
    res = append(res, msg)
}

return res, nil

如何将此代码转换为延迟加载,仅在 rows.next() 上会获取下一个项目(而不是提前加载所有项目),垃圾收集器呢,它会在每次迭代时释放内存row.next() 的??

标签: sqlpostgresqlgordssqlx

解决方案


推荐阅读