Skip to content

Instantly share code, notes, and snippets.

@vchakoshy
Last active June 14, 2021 18:57
Show Gist options
  • Save vchakoshy/786cdf176ec0904aec4689e6ddf66fd3 to your computer and use it in GitHub Desktop.
Save vchakoshy/786cdf176ec0904aec4689e6ddf66fd3 to your computer and use it in GitHub Desktop.
Golang Gorm Gin simple list api
package api
import (
"fmt"
"github.com/gin-gonic/gin"
"github.com/spf13/cast"
)
type FilterBold struct {
c *gin.Context
filters []string
wheres map[string]interface{}
preloads []string
joins []string
fieldAlias map[string]string
model interface{}
Result interface{}
Offset int
Limit int
NextURL string
order string
RowsCount int64
Token string
}
func NewFilterBold(c *gin.Context) *FilterBold {
token := c.DefaultQuery("token", "")
offset := cast.ToInt(c.DefaultQuery("offset", "0"))
limit := cast.ToInt(c.DefaultQuery("limit", "10"))
f := &FilterBold{
Limit: limit,
Token: token,
Offset: offset,
wheres: make(map[string]interface{}, 0),
fieldAlias: make(map[string]string, 0),
c: c,
order: "id DESC",
}
return f
}
func (f *FilterBold) Preloads(m ...string) *FilterBold {
for _, c := range m {
f.preloads = append(f.preloads, c)
}
return f
}
func (f *FilterBold) Where(k string, v interface{}) *FilterBold {
f.wheres[k] = v
return f
}
func (f *FilterBold) Alias(k, v string) *FilterBold {
f.fieldAlias[k] = v
return f
}
func (f *FilterBold) Joins(m ...string) *FilterBold {
for _, c := range m {
f.joins = append(f.joins, c)
}
return f
}
func (f *FilterBold) Model(m interface{}) *FilterBold {
f.model = m
return f
}
func (f *FilterBold) Order(o string) *FilterBold {
f.order = o
return f
}
func (f *FilterBold) Filters(i ...string) *FilterBold {
for _, filter := range i {
f.filters = append(f.filters, filter)
}
return f
}
func (f *FilterBold) Find(o interface{}) *FilterBold {
q := db.Model(f.model)
for _, filter := range f.filters {
i := f.c.DefaultQuery(filter, "")
if i != "" {
qf := fmt.Sprintf("%s=?", filter)
q = q.Where(qf, i)
}
}
for k, v := range f.wheres {
qf := fmt.Sprintf("%s=?", k)
q = q.Where(qf, v)
}
for k, filter := range f.fieldAlias {
i := f.c.DefaultQuery(k, "")
if i != "" {
qf := fmt.Sprintf("%s=?", filter)
q = q.Where(qf, i)
}
}
for _, p := range f.preloads {
q = q.Preload(p)
}
for _, p := range f.joins {
q = q.Joins(p)
}
q.Order(f.order).
Limit(f.Limit).
Offset(f.Offset).
Find(o)
f.makeNextURL()
q.Count(&f.RowsCount)
return f
}
func (f *FilterBold) makeNextURL() *FilterBold {
up := f.c.Request.URL
uq := up.Query()
uq.Set("token", f.Token)
uq.Set("offset", cast.ToString(f.Offset+f.Limit))
for _, filter := range f.filters {
i := f.c.DefaultQuery(filter, "")
if i != "" {
uq.Set(filter, i)
}
}
up.RawQuery = uq.Encode()
if DebugModeEnabled() {
f.NextURL = apiPrefixDebug + up.String()
} else {
f.NextURL = apiPrefix + up.String()
}
return f
}
func (f *FilterBold) GetMeta() gin.H {
return gin.H{
"next": f.NextURL,
"limit": f.Limit,
"total_count": f.RowsCount,
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment