diff options
Diffstat (limited to 'internal/db/bundb/timeline.go')
-rw-r--r-- | internal/db/bundb/timeline.go | 68 |
1 files changed, 38 insertions, 30 deletions
diff --git a/internal/db/bundb/timeline.go b/internal/db/bundb/timeline.go index d2b3cf07e..d4740dd96 100644 --- a/internal/db/bundb/timeline.go +++ b/internal/db/bundb/timeline.go @@ -34,38 +34,48 @@ type timelineDB struct { } func (t *timelineDB) GetHomeTimeline(ctx context.Context, accountID string, maxID string, sinceID string, minID string, limit int, local bool) ([]*gtsmodel.Status, db.Error) { + // Ensure reasonable + if limit < 0 { + limit = 0 + } + // Make educated guess for slice size statusIDs := make([]string, 0, limit) q := t.conn. NewSelect(). - Table("statuses"). - + TableExpr("? AS ?", bun.Ident("statuses"), bun.Ident("status")). // Select only IDs from table - Column("statuses.id"). + Column("status.id"). // Find out who accountID follows. - Join("LEFT JOIN follows ON follows.target_account_id = statuses.account_id AND follows.account_id = ?", accountID). + Join("LEFT JOIN ? AS ? ON ? = ? AND ? = ?", + bun.Ident("follows"), + bun.Ident("follow"), + bun.Ident("follow.target_account_id"), + bun.Ident("status.account_id"), + bun.Ident("follow.account_id"), + accountID). // Sort by highest ID (newest) to lowest ID (oldest) - Order("statuses.id DESC") + Order("status.id DESC") if maxID != "" { // return only statuses LOWER (ie., older) than maxID - q = q.Where("statuses.id < ?", maxID) + q = q.Where("? < ?", bun.Ident("status.id"), maxID) } if sinceID != "" { // return only statuses HIGHER (ie., newer) than sinceID - q = q.Where("statuses.id > ?", sinceID) + q = q.Where("? > ?", bun.Ident("status.id"), sinceID) } if minID != "" { // return only statuses HIGHER (ie., newer) than minID - q = q.Where("statuses.id > ?", minID) + q = q.Where("? > ?", bun.Ident("status.id"), minID) } if local { // return only statuses posted by local account havers - q = q.Where("statuses.local = ?", local) + q = q.Where("? = ?", bun.Ident("status.local"), local) } if limit > 0 { @@ -78,13 +88,11 @@ func (t *timelineDB) GetHomeTimeline(ctx context.Context, accountID string, maxI // // This is equivalent to something like WHERE ... AND (... OR ...) // See: https://bun.uptrace.dev/guide/queries.html#select - whereGroup := func(*bun.SelectQuery) *bun.SelectQuery { + q = q.WhereGroup(" AND ", func(*bun.SelectQuery) *bun.SelectQuery { return q. - WhereOr("follows.account_id = ?", accountID). - WhereOr("statuses.account_id = ?", accountID) - } - - q = q.WhereGroup(" AND ", whereGroup) + WhereOr("? = ?", bun.Ident("follow.account_id"), accountID). + WhereOr("? = ?", bun.Ident("status.account_id"), accountID) + }) if err := q.Scan(ctx, &statusIDs); err != nil { return nil, t.conn.ProcessError(err) @@ -118,28 +126,28 @@ func (t *timelineDB) GetPublicTimeline(ctx context.Context, accountID string, ma q := t.conn. NewSelect(). - Table("statuses"). - Column("statuses.id"). - Where("statuses.visibility = ?", gtsmodel.VisibilityPublic). - WhereGroup(" AND ", whereEmptyOrNull("statuses.in_reply_to_id")). - WhereGroup(" AND ", whereEmptyOrNull("statuses.in_reply_to_uri")). - WhereGroup(" AND ", whereEmptyOrNull("statuses.boost_of_id")). - Order("statuses.id DESC") + TableExpr("? AS ?", bun.Ident("statuses"), bun.Ident("status")). + Column("status.id"). + Where("? = ?", bun.Ident("status.visibility"), gtsmodel.VisibilityPublic). + WhereGroup(" AND ", whereEmptyOrNull("status.in_reply_to_id")). + WhereGroup(" AND ", whereEmptyOrNull("status.in_reply_to_uri")). + WhereGroup(" AND ", whereEmptyOrNull("status.boost_of_id")). + Order("status.id DESC") if maxID != "" { - q = q.Where("statuses.id < ?", maxID) + q = q.Where("? < ?", bun.Ident("status.id"), maxID) } if sinceID != "" { - q = q.Where("statuses.id > ?", sinceID) + q = q.Where("? > ?", bun.Ident("status.id"), sinceID) } if minID != "" { - q = q.Where("statuses.id > ?", minID) + q = q.Where("? > ?", bun.Ident("status.id"), minID) } if local { - q = q.Where("statuses.local = ?", local) + q = q.Where("? = ?", bun.Ident("status.local"), local) } if limit > 0 { @@ -181,15 +189,15 @@ func (t *timelineDB) GetFavedTimeline(ctx context.Context, accountID string, max fq := t.conn. NewSelect(). Model(&faves). - Where("account_id = ?", accountID). - Order("id DESC") + Where("? = ?", bun.Ident("status_fave.account_id"), accountID). + Order("status_fave.id DESC") if maxID != "" { - fq = fq.Where("id < ?", maxID) + fq = fq.Where("? < ?", bun.Ident("status_fave.id"), maxID) } if minID != "" { - fq = fq.Where("id > ?", minID) + fq = fq.Where("? > ?", bun.Ident("status_fave.id"), minID) } if limit > 0 { |