Files
huangguo_server/models/v/collectmod/collect.go
T
rootandClaude Opus 5 8679200f41 Initial commit
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-15 13:57:10 +08:00

388 lines
11 KiB
Go

package collectmod
import (
"91porn-server/common/constant"
"91porn-server/common/db"
"91porn-server/common/log"
"91porn-server/models"
"91porn-server/models/commod"
"fmt"
"go.mongodb.org/mongo-driver/bson"
"go.mongodb.org/mongo-driver/bson/primitive"
"go.mongodb.org/mongo-driver/mongo"
"go.mongodb.org/mongo-driver/mongo/options"
"time"
)
var mdb *db.MongoDB
var maxCollectTagsSize = 30
const table = models.Collect
func coll(t *db.MongoTool) *db.MongoTool {
if t == nil {
return mdb.Coll(table)
}
return t.Coll(table)
}
// initCollectIndex 初始化索引
func initIndex() {
many := []mongo.IndexModel{
{
Keys: bson.D{{"uid", 1}, {"type", 1}},
},
{
Keys: bson.D{{"uid", 1}, {"type", 1}, {"objID", 1}},
Options: options.Index().SetUnique(true),
},
{
Keys: bson.D{{"uniq", 1}},
Options: options.Index().SetUnique(true),
},
}
_, err := coll(nil).CreateIndex(many)
if err != nil {
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
}
return
}
// CollInsertOne 插入收藏消息记录
func CollInsertOne(c *Collect) (err error) {
c.Uniq = Unique(c.UID, c.Type, c.ObjID)
c.CreatedAt = time.Now()
if _, err = coll(nil).InsertOne(c); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollInsertOne", table, "InsertOne", err))
return
}
return
}
// CollInsertMany 插入收藏消息记录
func CollInsertMany(c *[]Collect) (err error) {
if _, err = coll(nil).InsertMany(c); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollInsertMany", table, "InsertMany", err))
return
}
return
}
// CollDeleteOne 取消收藏
func CollDeleteOne(uid uint64, cType string, objID primitive.ObjectID) (err error) {
var query = bson.M{"uid": uid, "type": cType, "objID": objID}
if _, err = coll(nil).DeleteOne(query); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollDeleteOne", table, "DeleteOne", err),
log.Any("uid", uid),
log.Any("cType", cType),
log.Any("objID", objID),
)
return
}
return
}
// CollDeleteMany 取消收藏
func CollDeleteMany(ids []string) (err error) {
var query = bson.M{"uniq": bson.M{"$in": ids}}
if _, err = coll(nil).DeleteMany(query); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollDeleteMany", table, "DeleteMany", err),
log.Any("ids", ids),
)
return
}
return
}
// CollFindOneByUidAndObjID 获取单条收藏信息 用于验证是否已经收藏
func CollFindOneByUidAndObjID(uid uint64, objID primitive.ObjectID) (data Collect, err error) {
var query = bson.M{"uid": uid, "objID": objID}
if err = coll(nil).FindOne(&data, query); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindOneByUidAndObjID", table, "FindOne", err),
log.Any("uid", uid),
log.Any("objID", objID),
)
return
}
return
}
// CollFindOneByUidAndObjIds 获取多条收藏信息 用于验证是否已经收藏
func CollFindOneByUidAndObjIds(uid uint64, objIDS []primitive.ObjectID) (data []Collect, err error) {
var query = bson.M{"uid": uid, "objID": bson.M{"$in": objIDS}}
if err = coll(nil).Find(&data, query); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindOneByUidAndObjIds", table, "Find", err),
log.Any("uid", uid),
log.Any("objIDS", objIDS),
)
return
}
return
}
// CollFindCollects 获取收藏列表
func CollFindCollects(uid uint64, cType string, stdQuery commod.StdQuery) (data []Collect, err error) {
*stdQuery.Order = append(*stdQuery.Order, commod.OrderBy{Key: "createdAt", Desc: true})
var query = bson.M{"uid": uid, "type": cType}
if err = coll(nil).Find(&data, query, commod.ConvertToListQuery(stdQuery)); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindOneByUidAndObjID", table, "FindOne", err),
log.Any("uid", uid),
log.Any("objID", cType),
)
return
}
return
}
// CollFindCollectsByUIDAndObjIDs 获取包含指定对象收藏列表
func CollFindCollectsByUIDAndObjIDs(uid uint64, cType string, objIDs []primitive.ObjectID) (data []Collect, err error) {
var query = bson.M{"uid": uid, "type": cType, "objID": bson.M{"$in": objIDs}}
if err = coll(nil).Find(&data, query); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindOneByUidAndObjID", table, "FindOne", err),
log.Any("uid", uid),
log.Any("objID", cType),
)
return
}
return
}
// CollFindCollectsByUIDAndObjId 获取包含指定对象收藏列表
func CollFindCollectsByUIDAndObjId(uid uint64, objId primitive.ObjectID) (data Collect, err error) {
var query = bson.M{"uid": uid, "objID": objId}
if err = coll(nil).FindOne(&data, query); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindCollectsByUIDAndObjId", table, "FindOne", err),
log.Any("uid", uid),
)
return
}
return
}
func QuickList(uid uint64, cType string, skip, limit int64) ([]Collect, int64, error) {
filter := bson.M{"uid": uid, "type": cType}
const maxLimit = 450 //iphone 11 一屏显示3项 1页3屏 1页9项 50页450项
opt := (&options.FindOptions{}).SetLimit(maxLimit)
var totalList []Collect
err := coll(nil).Find(&totalList, filter, opt) //取总共的数据 最多1000条
if err != nil {
return nil, 0, err
}
total := int64(len(totalList))
if total == 0 {
return []Collect{}, 0, nil
}
//内存中分页 skip + limit ∈ [0, total)
if skip+limit > total {
if skip > total {
return []Collect{}, 0, nil
}
limit = total - skip
}
list := make([]Collect, 0, limit)
for i := skip; i < skip+limit; i++ {
list = append(list, totalList[i])
}
return list, total, err
}
// CollFindCountByUID 获取收藏数量
func CollFindCountByUID(uid uint64) (data int64, err error) {
data, err = coll(nil).Count(bson.M{"uid": uid})
if err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindCountByUID", table, "Count", err), log.Any("uid", uid))
return
}
return
}
// CollFindCountByUidAndType 更具uid/type获取标签数量
func CollFindCountByUidAndType(uid uint64, cType string) (data int64, err error) {
var query = bson.M{"uid": uid, "type": cType, "videoCount": bson.M{"$gt": 0}}
if data, err = coll(nil).Count(query); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindCountByUidAndType", table, "Count", err),
log.Any("uid", uid),
log.Any("cType", cType),
)
return
}
return
}
// CollFindCollectByTypeAndUID 我的收藏
func CollFindCollectByTypeAndUID(uid uint64, cType string) (cIDs []primitive.ObjectID, total int64, err error) {
var opt options.FindOptions
opt.SetSort(bson.M{"_id": -1}).SetLimit(4)
query := bson.M{"uid": uid, "type": cType}
var collects []*Collect
if err = coll(nil).Find(&collects, query, &opt); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindCollectByTypeAndUID", table, "Find", err),
log.Any("uid", uid),
log.Any("cType", cType),
)
return
}
for _, v := range collects {
cIDs = append(cIDs, v.ObjID)
}
total, err = coll(nil).Count(query)
if err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "CollFindCollectByTypeAndUID", table, "Count", err),
log.Any("uid", uid),
log.Any("cType", cType),
)
return
}
return
}
// CollIsExisted 是否收藏
func CollIsExisted(uid uint64, cType string, objID primitive.ObjectID) (isExists bool, err error) {
cnt, err := coll(nil).Count(bson.M{"uid": uid, "type": cType, "objID": objID})
isExists = false
if err != nil || cnt == 0 {
return
}
isExists = true
return
}
// 从给定的uniq列表中获取收藏状态映射:uniq->Statue
// uniq通过uniq()获取
func CltStatueMap(uniqList []string) (map[string]bool, error) {
if len(uniqList) == 0 {
return make(map[string]bool), nil
}
filter := bson.M{
"uniq": bson.M{"$in": uniqList},
}
existCltList := make([]Collect, 0, len(uniqList))
err := coll(nil).Find(&existCltList, filter)
if err != nil {
return nil, err
}
m := make(map[string]bool, len(existCltList))
//初始化
for _, uniq := range uniqList {
m[uniq] = false
}
//已经收藏的
for _, v := range existCltList {
m[v.Uniq] = true
}
return m, nil
}
// IsCollectVideos 是否收藏视频
func IsCollectVideos(uid uint64, videoIDs []primitive.ObjectID) (map[primitive.ObjectID]bool, error) {
m := make(map[primitive.ObjectID]bool)
videoIDs = uniqueVideoIDs(videoIDs)
if len(videoIDs) == 0 {
return m, nil
}
var infos []Collect
query := collectVideoStatusFilter(uid, videoIDs)
opts := options.Find().SetProjection(bson.M{"_id": 0, "objID": 1})
if err := coll(nil).Find(&infos, query, opts); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "IsCollectVideos", table, "Find", err),
log.Any("uid", uid),
log.Any("videoIDs", videoIDs),
)
return m, err
}
for _, i := range infos {
m[i.ObjID] = true
}
return m, nil
}
func collectVideoStatusFilter(uid uint64, videoIDs []primitive.ObjectID) bson.M {
return bson.M{
"uid": uid,
"type": bson.M{"$in": []string{
constant.CollectTypeSP,
constant.CollectTypeShort,
constant.CollectTypeCover,
constant.CollectTypePIC,
constant.CollectTypeSEED_LINK,
constant.CollectTypeAiPlaza,
}},
"objID": bson.M{"$in": videoIDs},
}
}
func uniqueVideoIDs(ids []primitive.ObjectID) []primitive.ObjectID {
if len(ids) < 2 {
return ids
}
seen := make(map[primitive.ObjectID]struct{}, len(ids))
unique := make([]primitive.ObjectID, 0, len(ids))
for _, id := range ids {
if _, ok := seen[id]; ok {
continue
}
seen[id] = struct{}{}
unique = append(unique, id)
}
return unique
}
// GetLocsCollectCnt2Map 获取位置的收藏数
func GetLocsCollectCnt2Map(locIDs []primitive.ObjectID) (map[primitive.ObjectID]int, error) {
if locIDs == nil {
locIDs = []primitive.ObjectID{}
}
m := make(map[primitive.ObjectID]int)
var data []CityCount
p := []bson.M{
{"$match": bson.M{"type": constant.CollectTypeLocation, "objID": bson.M{"$in": locIDs}}},
{"$group": bson.M{"_id": "$objID", "count": bson.M{"$sum": 1}}},
}
if err := coll(nil).Aggregate(&data, p); err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetLocsCollectCnt2Map", table, "Aggregate", err), log.Any("locIDs", locIDs))
return nil, err
}
for _, d := range data {
m[d.ID] = d.Count
}
return m, nil
}
// MyCollectTags 获取收藏标签
func MyCollectTags(uid uint64, top int) ([]primitive.ObjectID, error) {
var ids []primitive.ObjectID
stdQuery := commod.StdQuery{Page: &commod.PageBy{Num: 1, Size: uint64(top)}, Order: &[]commod.OrderBy{}}
data, err := CollFindCollects(uid, constant.CollectTypeTag, stdQuery)
if err != nil {
return ids, nil
}
for _, d := range data {
ids = append(ids, d.ObjID)
}
return ids, nil
}
// 根据标签id获取收藏列表
func GetCollectTagList(uid uint64, tagsID []primitive.ObjectID) (data []Collect, err error) {
if tagsID == nil || uid == 0 {
return
}
var query = bson.M{
"uid": uid,
"type": constant.CollectTypeTag,
"objID": bson.M{"$in": tagsID},
}
err = coll(nil).Find(&data, query)
if err != nil {
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetCollectTagList", table, "Find", err),
log.Any("uid", uid),
log.Any("tagsID", tagsID),
)
return
}
return
}