init: radio init commit
This commit is contained in:
@@ -0,0 +1,87 @@
|
||||
package radio
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"sundynix-go/global"
|
||||
"sundynix-go/model/radio"
|
||||
radioReq "sundynix-go/model/radio/request"
|
||||
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
type CategoryService struct{}
|
||||
|
||||
// GetCategoryList 获取分类列表
|
||||
func (s *CategoryService) GetCategoryList(info radioReq.GetCategoryList) ([]radio.RadioCategory, int64, error) {
|
||||
db := global.DB.Model(&radio.RadioCategory{}).Preload("Icon").Preload("Cover")
|
||||
var list []radio.RadioCategory
|
||||
var total int64
|
||||
|
||||
if info.Name != "" {
|
||||
db = db.Where("name LIKE ?", "%"+info.Name+"%")
|
||||
}
|
||||
if info.Status > 0 {
|
||||
db = db.Where("status = ?", info.Status)
|
||||
}
|
||||
|
||||
err := db.Count(&total).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
offset := (info.Current - 1) * info.PageSize
|
||||
err = db.Offset(offset).Limit(info.PageSize).Order("sort ASC").Find(&list).Error
|
||||
return list, total, err
|
||||
}
|
||||
|
||||
func (s *CategoryService) GetAllCategory() ([]radio.RadioCategory, error) {
|
||||
var res []radio.RadioCategory
|
||||
err := global.DB.Find(&res).Preload(":Icon").Preload("Cover").Error
|
||||
return res, err
|
||||
}
|
||||
|
||||
// GetCategoryById 获取分类详情
|
||||
func (s *CategoryService) GetCategoryById(id string) (*radio.RadioCategory, error) {
|
||||
var category radio.RadioCategory
|
||||
err := global.DB.Where("id = ?", id).Preload("Icon").Preload("Cover").First(&category).Error
|
||||
return &category, err
|
||||
}
|
||||
|
||||
// SaveCategory 保存分类
|
||||
func (s *CategoryService) SaveCategory(req radioReq.SaveCategory) error {
|
||||
category := radio.RadioCategory{
|
||||
Name: req.Name,
|
||||
Description: req.Description,
|
||||
IconId: req.IconId,
|
||||
CoverId: req.CoverId,
|
||||
Sort: req.Sort,
|
||||
Status: req.Status,
|
||||
}
|
||||
return global.DB.Create(&category).Error
|
||||
}
|
||||
|
||||
// UpdateCategory 更新分类
|
||||
func (s *CategoryService) UpdateCategory(req radioReq.UpdateCategory) error {
|
||||
updates := map[string]interface{}{
|
||||
"name": req.Name,
|
||||
"description": req.Description,
|
||||
"icon_id": req.IconId,
|
||||
"cover_id": req.CoverId,
|
||||
"sort": req.Sort,
|
||||
"status": req.Status,
|
||||
}
|
||||
return global.DB.Model(&radio.RadioCategory{}).Where("id = ?", req.Id).Updates(updates).Error
|
||||
}
|
||||
|
||||
// DeleteCategory 删除分类
|
||||
func (s *CategoryService) DeleteCategory(id string) error {
|
||||
return global.DB.Transaction(func(tx *gorm.DB) error {
|
||||
// 检查是否有频道使用此分类
|
||||
var count int64
|
||||
tx.Model(&radio.RadioChannel{}).Where("category_id = ?", id).Count(&count)
|
||||
if count > 0 {
|
||||
return errors.New("该分类下存在频道,无法删除")
|
||||
}
|
||||
return tx.Where("id = ?", id).Delete(&radio.RadioCategory{}).Error
|
||||
})
|
||||
}
|
||||
@@ -0,0 +1,127 @@
|
||||
package radio
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
||||
"sundynix-go/global"
|
||||
"sundynix-go/model/radio"
|
||||
radioReq "sundynix-go/model/radio/request"
|
||||
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
type ChannelService struct{}
|
||||
|
||||
// GetChannelList 获取频道列表
|
||||
func (s *ChannelService) GetChannelList(userId string, info radioReq.GetChannelList) ([]radio.RadioChannel, int64, error) {
|
||||
db := global.DB.Model(&radio.RadioChannel{})
|
||||
var list []radio.RadioChannel
|
||||
var total int64
|
||||
|
||||
if info.CategoryId != "" {
|
||||
db = db.Where("category_id = ?", info.CategoryId)
|
||||
}
|
||||
if info.Name != "" {
|
||||
db = db.Where("name LIKE ?", "%"+info.Name+"%")
|
||||
}
|
||||
if info.Status > 0 {
|
||||
db = db.Where("status = ?", info.Status)
|
||||
}
|
||||
|
||||
err := db.Count(&total).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
offset := (info.Current - 1) * info.PageSize
|
||||
err = db.Offset(offset).Limit(info.PageSize).Order("sort ASC").Find(&list).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
// 批量查询用户订阅的频道,避免N+1问题
|
||||
if userId != "" {
|
||||
subService := &SubscriptionService{}
|
||||
subscribedChannelIds, _ := subService.GetUserSubscriptionHistory(userId)
|
||||
// 转换为map以便快速查找
|
||||
subscribedMap := make(map[string]bool)
|
||||
for _, cid := range subscribedChannelIds {
|
||||
subscribedMap[cid] = true
|
||||
}
|
||||
// 填充HasSubscribed字段
|
||||
for i := range list {
|
||||
if subscribedMap[list[i].Id] {
|
||||
list[i].HasSubscribed = 1
|
||||
} else {
|
||||
list[i].HasSubscribed = 0
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return list, total, nil
|
||||
}
|
||||
|
||||
// GetChannelById 获取频道详情
|
||||
func (s *ChannelService) GetChannelById(userId, id string) (radio.RadioChannel, error) {
|
||||
var channel radio.RadioChannel
|
||||
err := global.DB.Where("id = ?", id).Preload("Cover").First(&channel).Error
|
||||
if err != nil {
|
||||
return channel, err
|
||||
}
|
||||
|
||||
// 填充HasSubscribed字段
|
||||
if userId != "" {
|
||||
subService := &SubscriptionService{}
|
||||
hasSub, _ := subService.HasSubscription(userId, channel.Id)
|
||||
if hasSub {
|
||||
channel.HasSubscribed = 1
|
||||
} else {
|
||||
channel.HasSubscribed = 0
|
||||
}
|
||||
}
|
||||
|
||||
return channel, nil
|
||||
}
|
||||
|
||||
// SaveChannel 保存频道
|
||||
func (s *ChannelService) SaveChannel(req radioReq.SaveChannel) error {
|
||||
channel := radio.RadioChannel{
|
||||
CategoryId: req.CategoryId,
|
||||
Name: req.Name,
|
||||
Description: req.Description,
|
||||
CoverId: req.CoverId,
|
||||
Tags: req.Tags,
|
||||
IsVipOnly: req.IsVipOnly,
|
||||
Sort: req.Sort,
|
||||
Status: req.Status,
|
||||
}
|
||||
return global.DB.Create(&channel).Error
|
||||
}
|
||||
|
||||
// UpdateChannel 更新频道
|
||||
func (s *ChannelService) UpdateChannel(req radioReq.UpdateChannel) error {
|
||||
updates := map[string]interface{}{
|
||||
"category_id": req.CategoryId,
|
||||
"name": req.Name,
|
||||
"description": req.Description,
|
||||
"cover_id": req.CoverId,
|
||||
"tags": req.Tags,
|
||||
"is_vip_only": req.IsVipOnly,
|
||||
"sort": req.Sort,
|
||||
"status": req.Status,
|
||||
}
|
||||
return global.DB.Model(&radio.RadioChannel{}).Where("id = ?", req.Id).Updates(updates).Error
|
||||
}
|
||||
|
||||
// DeleteChannel 删除频道
|
||||
func (s *ChannelService) DeleteChannel(id string) error {
|
||||
return global.DB.Transaction(func(tx *gorm.DB) error {
|
||||
// 检查是否有节目使用此频道
|
||||
var count int64
|
||||
tx.Model(&radio.RadioProgram{}).Where("channel_id = ?", id).Count(&count)
|
||||
if count > 0 {
|
||||
return errors.New("该频道下存在节目,无法删除")
|
||||
}
|
||||
return tx.Where("id = ?", id).Delete(&radio.RadioChannel{}).Error
|
||||
})
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
package radio
|
||||
|
||||
type ServiceGroup struct {
|
||||
CategoryService
|
||||
ChannelService
|
||||
ProgramService
|
||||
SubscriptionService
|
||||
InteractionService
|
||||
}
|
||||
|
||||
var GroupApp = new(ServiceGroup)
|
||||
@@ -0,0 +1,176 @@
|
||||
package radio
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"sundynix-go/global"
|
||||
"sundynix-go/model/radio"
|
||||
radioReq "sundynix-go/model/radio/request"
|
||||
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
type InteractionService struct{}
|
||||
|
||||
// AddHistory 添加收听历史
|
||||
func (s *InteractionService) AddHistory(userId string, req radioReq.AddHistory) error {
|
||||
// 先查找是否已存在记录
|
||||
var history radio.RadioHistory
|
||||
err := global.DB.Where("user_id = ? AND program_id = ?", userId, req.ProgramId).First(&history).Error
|
||||
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
// 不存在,创建新记录
|
||||
history = radio.RadioHistory{
|
||||
UserId: userId,
|
||||
ProgramId: req.ProgramId,
|
||||
Progress: req.Progress,
|
||||
Duration: req.Duration,
|
||||
}
|
||||
return global.DB.Create(&history).Error
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// 存在,更新进度
|
||||
return global.DB.Model(&history).Updates(map[string]interface{}{
|
||||
"progress": req.Progress,
|
||||
"duration": req.Duration,
|
||||
}).Error
|
||||
}
|
||||
|
||||
// GetHistoryList 获取收听历史列表
|
||||
func (s *InteractionService) GetHistoryList(userId string, info radioReq.GetHistoryList) ([]radio.RadioHistory, int64, error) {
|
||||
db := global.DB.Model(&radio.RadioHistory{}).Where("user_id = ?", userId)
|
||||
var list []radio.RadioHistory
|
||||
var total int64
|
||||
|
||||
err := db.Count(&total).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
offset := (info.Current - 1) * info.PageSize
|
||||
err = db.Offset(offset).Limit(info.PageSize).Order("created_at DESC").Find(&list).Error
|
||||
return list, total, err
|
||||
}
|
||||
|
||||
// ToggleLike 切换点赞状态
|
||||
func (s *InteractionService) ToggleLike(userId, programId string) (bool, error) {
|
||||
var like radio.RadioLike
|
||||
err := global.DB.Where("user_id = ? AND program_id = ?", userId, programId).First(&like).Error
|
||||
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
// 未点赞,添加点赞
|
||||
like = radio.RadioLike{
|
||||
UserId: userId,
|
||||
ProgramId: programId,
|
||||
}
|
||||
if err := global.DB.Create(&like).Error; err != nil {
|
||||
return false, err
|
||||
}
|
||||
// 增加节目点赞数
|
||||
global.DB.Model(&radio.RadioProgram{}).Where("id = ?", programId).
|
||||
UpdateColumn("like_count", gorm.Expr("like_count + ?", 1))
|
||||
return true, nil
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
|
||||
// 已点赞,取消点赞
|
||||
if err := global.DB.Delete(&like).Error; err != nil {
|
||||
return false, err
|
||||
}
|
||||
// 减少节目点赞数
|
||||
global.DB.Model(&radio.RadioProgram{}).Where("id = ?", programId).
|
||||
UpdateColumn("like_count", gorm.Expr("like_count - ?", 1))
|
||||
return false, nil
|
||||
}
|
||||
|
||||
// IsLiked 检查是否已点赞
|
||||
func (s *InteractionService) IsLiked(userId, programId string) (bool, error) {
|
||||
var count int64
|
||||
err := global.DB.Model(&radio.RadioLike{}).Where("user_id = ? AND program_id = ?", userId, programId).Count(&count).Error
|
||||
return count > 0, err
|
||||
}
|
||||
|
||||
// AddFavorite 添加收藏
|
||||
func (s *InteractionService) AddFavorite(userId, programId string) error {
|
||||
// 检查是否已收藏
|
||||
var existing radio.RadioFavorite
|
||||
err := global.DB.Where("user_id = ? AND program_id = ?", userId, programId).First(&existing).Error
|
||||
if err == nil {
|
||||
return errors.New("已经收藏过该节目")
|
||||
}
|
||||
if !errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return err
|
||||
}
|
||||
|
||||
favorite := radio.RadioFavorite{
|
||||
UserId: userId,
|
||||
ProgramId: programId,
|
||||
}
|
||||
return global.DB.Create(&favorite).Error
|
||||
}
|
||||
|
||||
// RemoveFavorite 取消收藏
|
||||
func (s *InteractionService) RemoveFavorite(userId, programId string) error {
|
||||
return global.DB.Where("user_id = ? AND program_id = ?", userId, programId).Delete(&radio.RadioFavorite{}).Error
|
||||
}
|
||||
|
||||
// GetFavoriteList 获取收藏列表
|
||||
func (s *InteractionService) GetFavoriteList(userId string, info radioReq.GetFavoriteList) ([]radio.RadioFavorite, int64, error) {
|
||||
db := global.DB.Model(&radio.RadioFavorite{}).Where("user_id = ?", userId)
|
||||
var list []radio.RadioFavorite
|
||||
var total int64
|
||||
|
||||
err := db.Count(&total).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
offset := (info.Current - 1) * info.PageSize
|
||||
err = db.Offset(offset).Limit(info.PageSize).Order("created_at DESC").Find(&list).Error
|
||||
return list, total, err
|
||||
}
|
||||
|
||||
// IsFavorited 检查是否已收藏
|
||||
func (s *InteractionService) IsFavorited(userId, programId string) (bool, error) {
|
||||
var count int64
|
||||
err := global.DB.Model(&radio.RadioFavorite{}).Where("user_id = ? AND program_id = ?", userId, programId).Count(&count).Error
|
||||
return count > 0, err
|
||||
}
|
||||
|
||||
// AddComment 添加评论
|
||||
func (s *InteractionService) AddComment(userId string, req radioReq.AddComment) error {
|
||||
comment := radio.RadioComment{
|
||||
ProgramId: req.ProgramId,
|
||||
UserId: userId,
|
||||
ParentId: req.ParentId,
|
||||
Content: req.Content,
|
||||
}
|
||||
return global.DB.Create(&comment).Error
|
||||
}
|
||||
|
||||
// DeleteComment 删除评论
|
||||
func (s *InteractionService) DeleteComment(userId, commentId string) error {
|
||||
return global.DB.Where("id = ? AND user_id = ?", commentId, userId).Delete(&radio.RadioComment{}).Error
|
||||
}
|
||||
|
||||
// GetCommentList 获取评论列表
|
||||
func (s *InteractionService) GetCommentList(programId string, info radioReq.GetCommentList) ([]radio.RadioComment, int64, error) {
|
||||
db := global.DB.Model(&radio.RadioComment{}).Where("program_id = ?", programId)
|
||||
var list []radio.RadioComment
|
||||
var total int64
|
||||
|
||||
err := db.Count(&total).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
offset := (info.Current - 1) * info.PageSize
|
||||
err = db.Offset(offset).Limit(info.PageSize).Order("created_at DESC").Find(&list).Error
|
||||
return list, total, err
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
package radio
|
||||
|
||||
import (
|
||||
"sundynix-go/global"
|
||||
"sundynix-go/model/radio"
|
||||
radioReq "sundynix-go/model/radio/request"
|
||||
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
type ProgramService struct{}
|
||||
|
||||
// GetProgramList 获取节目列表
|
||||
func (s *ProgramService) GetProgramList(info radioReq.GetProgramList) ([]radio.RadioProgram, int64, error) {
|
||||
db := global.DB.Model(&radio.RadioProgram{}).Preload("Cover").Preload("Audio")
|
||||
var list []radio.RadioProgram
|
||||
var total int64
|
||||
|
||||
if info.ChannelId != "" {
|
||||
db = db.Where("channel_id = ?", info.ChannelId)
|
||||
}
|
||||
if info.Title != "" {
|
||||
db = db.Where("title LIKE ?", "%"+info.Title+"%")
|
||||
}
|
||||
if info.Status > 0 {
|
||||
db = db.Where("status = ?", info.Status)
|
||||
}
|
||||
|
||||
err := db.Count(&total).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
offset := (info.Current - 1) * info.PageSize
|
||||
err = db.Offset(offset).Limit(info.PageSize).Order("created_at DESC").Find(&list).Error
|
||||
return list, total, err
|
||||
}
|
||||
|
||||
// GetProgramById 获取节目详情
|
||||
func (s *ProgramService) GetProgramById(id string) (*radio.RadioProgram, error) {
|
||||
var program radio.RadioProgram
|
||||
err := global.DB.Where("id = ?", id).Preload("Cover").Preload("Audio").First(&program).Error
|
||||
return &program, err
|
||||
}
|
||||
|
||||
// SaveProgram 保存节目
|
||||
func (s *ProgramService) SaveProgram(req radioReq.SaveProgram) error {
|
||||
program := radio.RadioProgram{
|
||||
ChannelId: req.ChannelId,
|
||||
Title: req.Title,
|
||||
Description: req.Description,
|
||||
Content: req.Content,
|
||||
CoverId: req.CoverId,
|
||||
AudioId: req.AudioId,
|
||||
Duration: req.Duration,
|
||||
Tags: req.Tags,
|
||||
Status: req.Status,
|
||||
}
|
||||
return global.DB.Create(&program).Error
|
||||
}
|
||||
|
||||
// UpdateProgram 更新节目
|
||||
func (s *ProgramService) UpdateProgram(req radioReq.UpdateProgram) error {
|
||||
updates := map[string]interface{}{
|
||||
"channel_id": req.ChannelId,
|
||||
"title": req.Title,
|
||||
"description": req.Description,
|
||||
"content": req.Content,
|
||||
"cover_id": req.CoverId,
|
||||
"audio_id": req.AudioId,
|
||||
"duration": req.Duration,
|
||||
"tags": req.Tags,
|
||||
"status": req.Status,
|
||||
}
|
||||
return global.DB.Model(&radio.RadioProgram{}).Where("id = ?", req.Id).Updates(updates).Error
|
||||
}
|
||||
|
||||
// DeleteProgram 删除节目
|
||||
func (s *ProgramService) DeleteProgram(ids []string) error {
|
||||
return global.DB.Transaction(func(tx *gorm.DB) error {
|
||||
// 删除相关的收藏记录
|
||||
tx.Where("program_id in ?", ids).Delete(&radio.RadioFavorite{})
|
||||
// 删除相关的点赞记录
|
||||
tx.Where("program_id in ?", ids).Delete(&radio.RadioLike{})
|
||||
// 删除相关的历史记录
|
||||
tx.Where("program_id in ?", ids).Delete(&radio.RadioHistory{})
|
||||
// 删除相关的评论
|
||||
tx.Where("program_id in ?", ids).Delete(&radio.RadioComment{})
|
||||
// 删除节目
|
||||
return tx.Where("id in ?", ids).Delete(&radio.RadioProgram{}).Error
|
||||
})
|
||||
}
|
||||
|
||||
// IncrementPlayCount 增加播放次数
|
||||
func (s *ProgramService) IncrementPlayCount(id string) error {
|
||||
return global.DB.Model(&radio.RadioProgram{}).Where("id = ?", id).
|
||||
UpdateColumn("play_count", gorm.Expr("play_count + ?", 1)).Error
|
||||
}
|
||||
@@ -0,0 +1,144 @@
|
||||
package radio
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"sundynix-go/global"
|
||||
common "sundynix-go/model/commom/request"
|
||||
"sundynix-go/model/radio"
|
||||
"time"
|
||||
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
type SubscriptionService struct{}
|
||||
|
||||
const MaxFreeSubscription = 2
|
||||
|
||||
// GetUserSubscription 获取用户订阅列表
|
||||
func (s *SubscriptionService) GetUserSubscription(userId string, info common.PageInfo) ([]radio.RadioSubscription, int64, error) {
|
||||
db := global.DB.Model(&radio.RadioSubscription{}).Where("user_id = ?", userId)
|
||||
var list []radio.RadioSubscription
|
||||
var total int64
|
||||
|
||||
err := db.Count(&total).Error
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
offset := (info.Current - 1) * info.PageSize
|
||||
err = db.Offset(offset).Limit(info.PageSize).Order("created_at DESC").Find(&list).Error
|
||||
return list, total, err
|
||||
}
|
||||
|
||||
// GetUserSubscriptionHistory 获取用户历史订阅过的频道ID列表
|
||||
func (s *SubscriptionService) GetUserSubscriptionHistory(userId string) ([]string, error) {
|
||||
var channelIds []string
|
||||
err := global.DB.Model(&radio.RadioSubscription{}).
|
||||
Where("user_id = ?", userId).
|
||||
Pluck("channel_id", &channelIds).Error
|
||||
return channelIds, err
|
||||
}
|
||||
|
||||
// HasEverSubscribed 检查用户是否曾经订阅过该频道(包括已取消的)
|
||||
func (s *SubscriptionService) HasEverSubscribed(userId, channelId string) (bool, error) {
|
||||
var count int64
|
||||
// 使用Unscoped查询包括已软删除的记录
|
||||
err := global.DB.Unscoped().Model(&radio.RadioSubscription{}).
|
||||
Where("user_id = ? AND channel_id = ?", userId, channelId).
|
||||
Count(&count).Error
|
||||
return count > 0, err
|
||||
}
|
||||
|
||||
// HasSubscription 检查用户当前是否订阅该频道(未取消的)
|
||||
func (s *SubscriptionService) HasSubscription(userId, channelId string) (bool, error) {
|
||||
var count int64
|
||||
err := global.DB.Model(&radio.RadioSubscription{}).
|
||||
Where("user_id = ? AND channel_id = ?", userId, channelId).
|
||||
Count(&count).Error
|
||||
return count > 0, err
|
||||
}
|
||||
|
||||
// CanSubscribe 检查是否可以订阅
|
||||
// 规则:
|
||||
// 1. 如果用户是VIP且未过期,可以订阅任意频道
|
||||
// 2. 如果用户曾经订阅过该频道(取消后再订阅),可以免费订阅
|
||||
// 3. 否则检查当前有效订阅数量是否达到上限(2个)
|
||||
func (s *SubscriptionService) CanSubscribe(userId, channelId string) (bool, string, error) {
|
||||
// 检查是否已经是订阅用户(未取消的订阅)
|
||||
var existing radio.RadioSubscription
|
||||
err := global.DB.Where("user_id = ? AND channel_id = ?", userId, channelId).First(&existing).Error
|
||||
if err == nil {
|
||||
return false, "您已订阅该频道", nil
|
||||
}
|
||||
if !errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return false, "", err
|
||||
}
|
||||
|
||||
// 获取radio_user检查VIP状态
|
||||
var radioUser radio.RadioUser
|
||||
err = global.DB.Where("user_id = ?", userId).First(&radioUser).Error
|
||||
if err == nil && radioUser.IsVip == 1 {
|
||||
// 检查VIP是否过期
|
||||
if radioUser.VipExpireAt != nil && *radioUser.VipExpireAt > time.Now().Unix() {
|
||||
return true, "", nil
|
||||
}
|
||||
}
|
||||
|
||||
// 检查用户是否曾经订阅过该频道(取消后又订阅的情况)
|
||||
hasEverSubscribed, err := s.HasEverSubscribed(userId, channelId)
|
||||
if err != nil {
|
||||
return false, "", err
|
||||
}
|
||||
if hasEverSubscribed {
|
||||
// 曾今订阅过,可以免费再次订阅
|
||||
return true, "", nil
|
||||
}
|
||||
|
||||
// 非VIP用户,检查当前有效订阅数量(排除已取消的)
|
||||
var count int64
|
||||
err = global.DB.Model(&radio.RadioSubscription{}).Where("user_id = ?", userId).Count(&count).Error
|
||||
if err != nil {
|
||||
return false, "", err
|
||||
}
|
||||
if count >= MaxFreeSubscription {
|
||||
return false, "免费订阅数量已达上限(2个),请开通VIP或订阅付费频道", nil
|
||||
}
|
||||
|
||||
return true, "", nil
|
||||
}
|
||||
|
||||
// Subscribe 订阅频道
|
||||
func (s *SubscriptionService) Subscribe(userId, channelId string, subType int) error {
|
||||
subscription := radio.RadioSubscription{
|
||||
UserId: userId,
|
||||
ChannelId: channelId,
|
||||
}
|
||||
return global.DB.Create(&subscription).Error
|
||||
}
|
||||
|
||||
// Unsubscribe 退订频道(逻辑删除,更新删除时间表示已取消)
|
||||
func (s *SubscriptionService) Unsubscribe(userId, channelId string) error {
|
||||
// 软删除:将DeletedAt设置为当前时间,表示已取消订阅
|
||||
// 这样用户可以再次免费订阅该频道
|
||||
return global.DB.Model(&radio.RadioSubscription{}).
|
||||
Where("user_id = ? AND channel_id = ?", userId, channelId).
|
||||
Update("deleted_at", time.Now()).Error
|
||||
}
|
||||
|
||||
// GetVipStatus 获取VIP状态
|
||||
func (s *SubscriptionService) GetVipStatus(userId string) (bool, int64, error) {
|
||||
var radioUser radio.RadioUser
|
||||
err := global.DB.Where("user_id = ?", userId).First(&radioUser).Error
|
||||
if err != nil {
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return false, 0, nil
|
||||
}
|
||||
return false, 0, err
|
||||
}
|
||||
|
||||
if radioUser.IsVip == 1 && radioUser.VipExpireAt != nil && *radioUser.VipExpireAt > time.Now().Unix() {
|
||||
return true, *radioUser.VipExpireAt, nil
|
||||
}
|
||||
|
||||
return false, 0, nil
|
||||
}
|
||||
Reference in New Issue
Block a user