feat(scopes): Add pagination support with Paginate and AdvancedPagination functions
Some checks failed
Gitea Build Check / Build (push) Failing after 29s
Some checks failed
Gitea Build Check / Build (push) Failing after 29s
- Introduce Paginate function for basic pagination - Add AdvancedPagination for pagination, sorting, and counting - Define Pagination struct to hold pagination data - Set MaxPageSizeLimit and DefaultPageSize in models/constants
This commit is contained in:
parent
8668d504b9
commit
78e17cf100
84
pkg/database/scopes.go
Normal file
84
pkg/database/scopes.go
Normal file
@ -0,0 +1,84 @@
|
||||
package database
|
||||
|
||||
import (
|
||||
"math"
|
||||
|
||||
"git.anthrove.art/Anthrove/otter-space-sdk/v2/pkg/models"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
type Pagination struct {
|
||||
Limit int `json:"limit,omitempty;query:limit"`
|
||||
Page int `json:"page,omitempty;query:page"`
|
||||
Sort string `json:"sort,omitempty;query:sort"`
|
||||
TotalRows int64 `json:"total_rows"`
|
||||
TotalPages int `json:"total_pages"`
|
||||
}
|
||||
|
||||
// Paginate applies pagination to a GORM query.
|
||||
// It takes two parameters:
|
||||
//
|
||||
// - page: the current page number (1-based index). If the page is less than or equal to 0, it defaults to 1.
|
||||
//
|
||||
// - pageSize: the number of records per page. If the pageSize is greater than the MaxPageSizeLimit defined in models, it defaults to MaxPageSizeLimit. If the pageSize is less than or equal to 0, it defaults to DefaultPageSize defined in models.
|
||||
//
|
||||
// The function calculates the offset based on the page and pageSize, and applies the offset and limit to the GORM DB instance.
|
||||
func Paginate(page int, pageSize int) func(db *gorm.DB) *gorm.DB {
|
||||
return func(db *gorm.DB) *gorm.DB {
|
||||
|
||||
if page <= 0 {
|
||||
page = 1
|
||||
}
|
||||
|
||||
switch {
|
||||
case pageSize > models.MaxPageSizeLimit:
|
||||
pageSize = models.MaxPageSizeLimit
|
||||
case pageSize <= 0:
|
||||
pageSize = models.DefaultPageSize
|
||||
}
|
||||
|
||||
offset := (page - 1) * pageSize
|
||||
return db.Offset(offset).Limit(pageSize)
|
||||
}
|
||||
}
|
||||
|
||||
// AdvancedPagination applies pagination, sorting, and counting to a GORM query.
|
||||
// Parameters:
|
||||
//
|
||||
// - value: The model or table to query.
|
||||
//
|
||||
// - pagination: A pointer to a Pagination struct containing page, limit, sort, total rows, and total pages information.
|
||||
//
|
||||
// - db: A pointer to the GORM database instance.
|
||||
//
|
||||
// The function calculates the offset based on the Page and Limit of the Pagination struct, and applies the offset and limit to the GORM DB instance.
|
||||
func AdvancedPagination(value any, pagination *Pagination, db *gorm.DB) func(db *gorm.DB) *gorm.DB {
|
||||
var totalRows int64
|
||||
|
||||
if pagination.Page <= 0 {
|
||||
pagination.Page = 1
|
||||
}
|
||||
|
||||
if pagination.Sort == "" {
|
||||
pagination.Sort = "Id desc"
|
||||
}
|
||||
|
||||
switch {
|
||||
case pagination.Limit > models.MaxPageSizeLimit:
|
||||
pagination.Limit = models.MaxPageSizeLimit
|
||||
case pagination.Limit <= 0:
|
||||
pagination.Limit = models.DefaultPageSize
|
||||
}
|
||||
|
||||
db.Model(value).Count(&totalRows)
|
||||
|
||||
pagination.TotalRows = totalRows
|
||||
totalPages := int(math.Ceil(float64(totalRows) / float64(pagination.Limit)))
|
||||
pagination.TotalPages = totalPages
|
||||
|
||||
offset := (pagination.Page - 1) * pagination.Limit
|
||||
|
||||
return func(db *gorm.DB) *gorm.DB {
|
||||
return db.Offset(offset).Limit(pagination.Limit).Order(pagination.Sort)
|
||||
}
|
||||
}
|
@ -24,6 +24,11 @@ type (
|
||||
UserFavoriteID string
|
||||
)
|
||||
|
||||
const (
|
||||
MaxPageSizeLimit = 100
|
||||
DefaultPageSize = 50
|
||||
)
|
||||
|
||||
const (
|
||||
SFW Rating = "safe"
|
||||
NSFW Rating = "explicit"
|
||||
|
Loading…
Reference in New Issue
Block a user