fix(redemption): add status filtering and cleanup action
This commit is contained in:
+29
-7
@@ -60,7 +60,7 @@ func GetAllRedemptions(startIdx int, num int) (redemptions []*Redemption, total
|
||||
return redemptions, total, nil
|
||||
}
|
||||
|
||||
func SearchRedemptions(keyword string, startIdx int, num int) (redemptions []*Redemption, total int64, err error) {
|
||||
func SearchRedemptions(keyword string, status string, startIdx int, num int) (redemptions []*Redemption, total int64, err error) {
|
||||
tx := DB.Begin()
|
||||
if tx.Error != nil {
|
||||
return nil, 0, tx.Error
|
||||
@@ -71,14 +71,36 @@ func SearchRedemptions(keyword string, startIdx int, num int) (redemptions []*Re
|
||||
}
|
||||
}()
|
||||
|
||||
// Build query based on keyword type
|
||||
query := tx.Model(&Redemption{})
|
||||
|
||||
// Only try to convert to ID if the string represents a valid integer
|
||||
if id, err := strconv.Atoi(keyword); err == nil {
|
||||
query = query.Where("id = ? OR name LIKE ?", id, keyword+"%")
|
||||
} else {
|
||||
query = query.Where("name LIKE ?", keyword+"%")
|
||||
if keyword != "" {
|
||||
if id, err := strconv.Atoi(keyword); err == nil {
|
||||
query = query.Where("id = ? OR name LIKE ?", id, keyword+"%")
|
||||
} else {
|
||||
query = query.Where("name LIKE ?", keyword+"%")
|
||||
}
|
||||
}
|
||||
|
||||
if status != "" {
|
||||
now := common.GetTimestamp()
|
||||
switch status {
|
||||
case "expired":
|
||||
query = query.Where(
|
||||
"status = ? AND expired_time != 0 AND expired_time < ?",
|
||||
common.RedemptionCodeStatusEnabled,
|
||||
now,
|
||||
)
|
||||
case strconv.Itoa(common.RedemptionCodeStatusEnabled):
|
||||
query = query.Where(
|
||||
"status = ? AND (expired_time = 0 OR expired_time >= ?)",
|
||||
common.RedemptionCodeStatusEnabled,
|
||||
now,
|
||||
)
|
||||
case strconv.Itoa(common.RedemptionCodeStatusDisabled):
|
||||
query = query.Where("status = ?", common.RedemptionCodeStatusDisabled)
|
||||
case strconv.Itoa(common.RedemptionCodeStatusUsed):
|
||||
query = query.Where("status = ?", common.RedemptionCodeStatusUsed)
|
||||
}
|
||||
}
|
||||
|
||||
// Get total count
|
||||
|
||||
@@ -0,0 +1,100 @@
|
||||
package model
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"github.com/QuantumNous/new-api/common"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
func TestSearchRedemptionsFiltersAndPaginates(t *testing.T) {
|
||||
require.NoError(t, DB.AutoMigrate(&Redemption{}))
|
||||
require.NoError(t, DB.Session(&gorm.Session{AllowGlobalUpdate: true}).Unscoped().Delete(&Redemption{}).Error)
|
||||
t.Cleanup(func() {
|
||||
require.NoError(t, DB.Session(&gorm.Session{AllowGlobalUpdate: true}).Unscoped().Delete(&Redemption{}).Error)
|
||||
})
|
||||
|
||||
now := common.GetTimestamp()
|
||||
redemptions := []Redemption{
|
||||
{Id: 1, Name: "alpha-active", Key: "00000000000000000000000000000001", Status: common.RedemptionCodeStatusEnabled, ExpiredTime: 0},
|
||||
{Id: 2, Name: "alpha-future", Key: "00000000000000000000000000000002", Status: common.RedemptionCodeStatusEnabled, ExpiredTime: now + 3600},
|
||||
{Id: 3, Name: "alpha-expired", Key: "00000000000000000000000000000003", Status: common.RedemptionCodeStatusEnabled, ExpiredTime: now - 10},
|
||||
{Id: 4, Name: "beta-disabled", Key: "00000000000000000000000000000004", Status: common.RedemptionCodeStatusDisabled, ExpiredTime: 0},
|
||||
{Id: 5, Name: "beta-used", Key: "00000000000000000000000000000005", Status: common.RedemptionCodeStatusUsed, ExpiredTime: 0},
|
||||
}
|
||||
require.NoError(t, DB.Create(&redemptions).Error)
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
keyword string
|
||||
status string
|
||||
startIdx int
|
||||
num int
|
||||
wantTotal int64
|
||||
wantIds []int
|
||||
}{
|
||||
{
|
||||
name: "no filters returns all rows",
|
||||
num: 10,
|
||||
wantTotal: 5,
|
||||
wantIds: []int{5, 4, 3, 2, 1},
|
||||
},
|
||||
{
|
||||
name: "keyword filters by name prefix",
|
||||
keyword: "alpha",
|
||||
num: 10,
|
||||
wantTotal: 3,
|
||||
wantIds: []int{3, 2, 1},
|
||||
},
|
||||
{
|
||||
name: "enabled status excludes expired rows",
|
||||
status: "1",
|
||||
num: 10,
|
||||
wantTotal: 2,
|
||||
wantIds: []int{2, 1},
|
||||
},
|
||||
{
|
||||
name: "expired status returns enabled expired rows",
|
||||
status: "expired",
|
||||
num: 10,
|
||||
wantTotal: 1,
|
||||
wantIds: []int{3},
|
||||
},
|
||||
{
|
||||
name: "disabled status",
|
||||
status: "2",
|
||||
num: 10,
|
||||
wantTotal: 1,
|
||||
wantIds: []int{4},
|
||||
},
|
||||
{
|
||||
name: "used status",
|
||||
status: "3",
|
||||
num: 10,
|
||||
wantTotal: 1,
|
||||
wantIds: []int{5},
|
||||
},
|
||||
{
|
||||
name: "pagination keeps unpaged total",
|
||||
startIdx: 1,
|
||||
num: 2,
|
||||
wantTotal: 5,
|
||||
wantIds: []int{4, 3},
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
rows, total, err := SearchRedemptions(tt.keyword, tt.status, tt.startIdx, tt.num)
|
||||
require.NoError(t, err)
|
||||
assert.Equal(t, tt.wantTotal, total)
|
||||
gotIds := make([]int, 0, len(rows))
|
||||
for _, row := range rows {
|
||||
gotIds = append(gotIds, row.Id)
|
||||
}
|
||||
assert.Equal(t, tt.wantIds, gotIds)
|
||||
})
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user