新增功能
This commit is contained in:
@@ -6,18 +6,53 @@ import (
|
||||
"fmt"
|
||||
"strings"
|
||||
|
||||
"github.com/luxsin/app-api/internal/cache"
|
||||
"github.com/luxsin/app-api/internal/model"
|
||||
"github.com/redis/go-redis/v9"
|
||||
)
|
||||
|
||||
type BrandRepository struct {
|
||||
db *sql.DB
|
||||
db *sql.DB
|
||||
cache *cache.BrandCache
|
||||
}
|
||||
|
||||
func NewBrandRepository(db *sql.DB) *BrandRepository {
|
||||
return &BrandRepository{db: db}
|
||||
func NewBrandRepository(db *sql.DB, brandCache *cache.BrandCache) *BrandRepository {
|
||||
return &BrandRepository{db: db, cache: brandCache}
|
||||
}
|
||||
|
||||
func (r *BrandRepository) List(ctx context.Context, brandName string) ([]model.Brand, error) {
|
||||
// 尝试从 Redis 获取全量品牌
|
||||
list, err := r.cache.GetAll(ctx)
|
||||
if err == nil {
|
||||
// 缓存命中,在应用层过滤
|
||||
if brandName = strings.TrimSpace(brandName); brandName != "" {
|
||||
list = filterBrands(list, brandName)
|
||||
}
|
||||
return list, nil
|
||||
}
|
||||
|
||||
// 缓存未命中或 Redis 异常,降级到数据库
|
||||
if err != redis.Nil {
|
||||
fmt.Printf("brand cache read failed, fallback to db: %v\n", err)
|
||||
}
|
||||
|
||||
list, err = r.ListFromDB(ctx, brandName)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// 回写缓存(全量数据)
|
||||
if allBrands, dbErr := r.ListFromDB(ctx, ""); dbErr == nil {
|
||||
if cacheErr := r.cache.SetAll(ctx, allBrands); cacheErr != nil {
|
||||
fmt.Printf("brand cache write failed: %v\n", cacheErr)
|
||||
}
|
||||
}
|
||||
|
||||
return list, nil
|
||||
}
|
||||
|
||||
// ListFromDB 直接从数据库查询(用于预热和缓存回写)
|
||||
func (r *BrandRepository) ListFromDB(ctx context.Context, brandName string) ([]model.Brand, error) {
|
||||
query := "SELECT id, name FROM brand"
|
||||
args := []any{}
|
||||
|
||||
@@ -48,3 +83,17 @@ func (r *BrandRepository) List(ctx context.Context, brandName string) ([]model.B
|
||||
|
||||
return list, nil
|
||||
}
|
||||
|
||||
// filterBrands 在应用层做模糊过滤
|
||||
func filterBrands(list []model.Brand, brandName string) []model.Brand {
|
||||
filtered := make([]model.Brand, 0)
|
||||
for _, b := range list {
|
||||
if strings.Contains(
|
||||
strings.ToLower(b.Name),
|
||||
strings.ToLower(brandName),
|
||||
) {
|
||||
filtered = append(filtered, b)
|
||||
}
|
||||
}
|
||||
return filtered
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user