func (log *memLog) Latest(ctx scope.Context, n int, before snowflake.Snowflake) ([]proto.Message, error) { log.Lock() defer log.Unlock() end := len(log.msgs) if !before.IsZero() { for end > 0 && !log.msgs[end-1].ID.Before(before) { end-- } } start := end - n if start < 0 { start = 0 } slice := make([]*proto.Message, 0, n) for _, msg := range log.msgs[start:] { if time.Time(msg.Deleted).IsZero() { slice = append(slice, maybeTruncate(msg)) if len(slice) >= n { break } } } if len(slice) == 0 { return []proto.Message{}, nil } messages := make([]proto.Message, len(slice)) for i, msg := range slice { messages[i] = *msg } return messages, nil }
func (b *Backend) latest(ctx scope.Context, room *Room, n int, before snowflake.Snowflake) ( []proto.Message, error) { if n <= 0 { return nil, nil } // TODO: define constant if n > 1000 { n = 1000 } var query string args := []interface{}{room.Name, n} // Get the time before which messages will be expired nDays, err := b.DbMap.SelectInt("SELECT retention_days FROM room WHERE name = $1", room.Name) if err != nil { return nil, err } if nDays == 0 { if before.IsZero() { query = ("SELECT room, id, previous_edit_id, parent, posted, edited, deleted," + " session_id, sender_id, sender_name, server_id, server_era, content, encryption_key_id" + " FROM message WHERE room = $1 AND deleted IS NULL ORDER BY id DESC LIMIT $2") } else { query = ("SELECT room, id, previous_edit_id, parent, posted, edited, deleted," + " session_id, sender_id, sender_name, server_id, server_era, content, encryption_key_id" + " FROM message WHERE room = $1 AND id < $3 AND deleted IS NULL ORDER BY id DESC LIMIT $2") args = append(args, before.String()) } } else { threshold := time.Now().Add(time.Duration(-nDays) * 24 * time.Hour) if before.IsZero() { query = ("SELECT room, id, previous_edit_id, parent, posted, edited, deleted," + " session_id, sender_id, sender_name, server_id, server_era, content, encryption_key_id" + " FROM message WHERE room = $1 AND posted > $3 AND deleted IS NULL ORDER BY id DESC LIMIT $2") } else { query = ("SELECT room, id, previous_edit_id, parent, posted, edited, deleted," + " session_id, sender_id, sender_name, server_id, server_era, content, encryption_key_id" + " FROM message WHERE room = $1 AND id < $3 AND deleted IS NULL AND posted > $4 ORDER BY id DESC LIMIT $2") args = append(args, before.String()) } args = append(args, threshold) } msgs, err := b.DbMap.Select(Message{}, query, args...) if err != nil { return nil, err } results := make([]proto.Message, len(msgs)) for i, row := range msgs { msg := row.(*Message) results[len(msgs)-i-1] = msg.ToBackend() } return results, nil }
func (b *Backend) latest(ctx scope.Context, rb *RoomBinding, n int, before snowflake.Snowflake) ( []proto.Message, error) { if n <= 0 { return nil, nil } // TODO: define constant if n > 1000 { n = 1000 } var query string args := []interface{}{rb.RoomName, n} // Get the time before which messages will be expired nDays, err := b.DbMap.SelectInt("SELECT retention_days FROM room WHERE name = $1", rb.RoomName) if err != nil { return nil, err } cols, err := allColumns(b.DbMap, Message{}, "") if err != nil { return nil, err } if nDays == 0 { if before.IsZero() { query = fmt.Sprintf("SELECT %s FROM message WHERE room = $1 AND deleted IS NULL ORDER BY id DESC LIMIT $2", cols) } else { query = fmt.Sprintf("SELECT %s FROM message WHERE room = $1 AND id < $3 AND deleted IS NULL ORDER BY id DESC LIMIT $2", cols) args = append(args, before.String()) } } else { threshold := time.Now().Add(time.Duration(-nDays) * 24 * time.Hour) if before.IsZero() { query = fmt.Sprintf("SELECT %s FROM message WHERE room = $1 AND posted > $3 AND deleted IS NULL ORDER BY id DESC LIMIT $2", cols) } else { query = fmt.Sprintf( "SELECT %s FROM message WHERE room = $1 AND id < $3 AND deleted IS NULL AND posted > $4 ORDER BY id DESC LIMIT $2", cols) args = append(args, before.String()) } args = append(args, threshold) } msgs, err := b.DbMap.Select(Message{}, query, args...) if err != nil { return nil, err } results := make([]proto.Message, len(msgs)) for i, row := range msgs { msg := row.(*Message) results[len(msgs)-i-1] = msg.ToTransmission() } return results, nil }