summaryrefslogtreecommitdiff
path: root/internal/util/paging.go
diff options
context:
space:
mode:
authorLibravatar tobi <31960611+tsmethurst@users.noreply.github.com>2023-05-22 16:32:36 +0200
committerLibravatar GitHub <noreply@github.com>2023-05-22 16:32:36 +0200
commitc48abd8bc0e708fedcddd7985c00243580464452 (patch)
tree6f9eb8b0537c75c3d68f1a9e0135870e6e0e7575 /internal/util/paging.go
parent[chore]: Bump github.com/go-playground/validator/v10 (#1812) (diff)
downloadgotosocial-c48abd8bc0e708fedcddd7985c00243580464452.tar.xz
[chore] update account statuses paging logic (#1814)
Diffstat (limited to 'internal/util/paging.go')
-rw-r--r--internal/util/paging.go108
1 files changed, 64 insertions, 44 deletions
diff --git a/internal/util/paging.go b/internal/util/paging.go
index 3d620ca1f..0ab4b9567 100644
--- a/internal/util/paging.go
+++ b/internal/util/paging.go
@@ -20,6 +20,7 @@ package util
import (
"fmt"
"net/url"
+ "strings"
apimodel "github.com/superseriousbusiness/gotosocial/internal/api/model"
"github.com/superseriousbusiness/gotosocial/internal/config"
@@ -47,6 +48,13 @@ type PageableResponseParams struct {
// a bunch of pageable items (notifications, statuses, etc), as well
// as a Link header to inform callers of where to find next/prev items.
func PackagePageableResponse(params PageableResponseParams) (*apimodel.PageableResponse, gtserror.WithCode) {
+ if len(params.Items) == 0 {
+ // No items to page through.
+ return EmptyPageableResponse(), nil
+ }
+
+ // Set default paging values, if
+ // they weren't set by the caller.
if params.NextMaxIDKey == "" {
params.NextMaxIDKey = "max_id"
}
@@ -55,58 +63,70 @@ func PackagePageableResponse(params PageableResponseParams) (*apimodel.PageableR
params.PrevMinIDKey = "min_id"
}
- pageableResponse := EmptyPageableResponse()
+ var (
+ protocol = config.GetProtocol()
+ host = config.GetHost()
+ nextLink string
+ prevLink string
+ linkHeaderParts = make([]string, 0, 2)
+ )
- if len(params.Items) == 0 {
- return pageableResponse, nil
- }
+ // Parse next link.
+ if params.NextMaxIDValue != "" {
+ nextRaw := params.NextMaxIDKey + "=" + params.NextMaxIDValue
- // items
- pageableResponse.Items = params.Items
+ if params.Limit != 0 {
+ nextRaw = fmt.Sprintf("limit=%d&", params.Limit) + nextRaw
+ }
- protocol := config.GetProtocol()
- host := config.GetHost()
+ for _, p := range params.ExtraQueryParams {
+ nextRaw += "&" + p
+ }
- // next
- nextRaw := params.NextMaxIDKey + "=" + params.NextMaxIDValue
- if params.Limit != 0 {
- nextRaw = fmt.Sprintf("limit=%d&", params.Limit) + nextRaw
- }
- for _, p := range params.ExtraQueryParams {
- nextRaw = nextRaw + "&" + p
- }
- nextLink := &url.URL{
- Scheme: protocol,
- Host: host,
- Path: params.Path,
- RawQuery: nextRaw,
- }
- nextLinkString := nextLink.String()
- pageableResponse.NextLink = nextLinkString
+ nextLink = func() string {
+ u := &url.URL{
+ Scheme: protocol,
+ Host: host,
+ Path: params.Path,
+ RawQuery: nextRaw,
+ }
+ return u.String()
+ }()
- // prev
- prevRaw := params.PrevMinIDKey + "=" + params.PrevMinIDValue
- if params.Limit != 0 {
- prevRaw = fmt.Sprintf("limit=%d&", params.Limit) + prevRaw
+ linkHeaderParts = append(linkHeaderParts, `<`+nextLink+`>; rel="next"`)
}
- for _, p := range params.ExtraQueryParams {
- prevRaw = prevRaw + "&" + p
- }
- prevLink := &url.URL{
- Scheme: protocol,
- Host: host,
- Path: params.Path,
- RawQuery: prevRaw,
- }
- prevLinkString := prevLink.String()
- pageableResponse.PrevLink = prevLinkString
- // link header
- next := fmt.Sprintf("<%s>; rel=\"next\"", nextLinkString)
- prev := fmt.Sprintf("<%s>; rel=\"prev\"", prevLinkString)
- pageableResponse.LinkHeader = next + ", " + prev
+ // Parse prev link.
+ if params.PrevMinIDValue != "" {
+ prevRaw := params.PrevMinIDKey + "=" + params.PrevMinIDValue
+
+ if params.Limit != 0 {
+ prevRaw = fmt.Sprintf("limit=%d&", params.Limit) + prevRaw
+ }
+
+ for _, p := range params.ExtraQueryParams {
+ prevRaw = prevRaw + "&" + p
+ }
- return pageableResponse, nil
+ prevLink = func() string {
+ u := &url.URL{
+ Scheme: protocol,
+ Host: host,
+ Path: params.Path,
+ RawQuery: prevRaw,
+ }
+ return u.String()
+ }()
+
+ linkHeaderParts = append(linkHeaderParts, `<`+prevLink+`>; rel="prev"`)
+ }
+
+ return &apimodel.PageableResponse{
+ Items: params.Items,
+ LinkHeader: strings.Join(linkHeaderParts, ", "),
+ NextLink: nextLink,
+ PrevLink: prevLink,
+ }, nil
}
// EmptyPageableResponse just returns an empty