@@ -0,0 +1,74 @@
|
||||
package adsclicklogmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/models"
|
||||
|
||||
"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"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.AdsClickLog
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
|
||||
// InitIndex 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}, {Key: "adsType", Value: 1}, {Key: "createdAt", Value: 1}},
|
||||
Options: options.Index().SetUnique(true),
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
type AdsClick struct {
|
||||
ID primitive.ObjectID `json:"-" bson:"_id,omitempty"`
|
||||
UID uint64 `json:"uid" bson:"uid"`
|
||||
ClickId primitive.ObjectID `json:"clickId" bson:"clickId"`
|
||||
ObjType string `json:"objType" bson:"objType"`
|
||||
AdsType int64 `json:"adsType" bson:"adsType"` // 0 默认; 1 金主楼凤广告
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
UpdatedAt time.Time `json:"updatedAt" bson:"updatedAt"`
|
||||
}
|
||||
|
||||
func AddClick(uid uint64, clickId primitive.ObjectID, objType string, adsType int64) error {
|
||||
now := time.Now()
|
||||
_, err := coll(nil).InsertOne(AdsClick{
|
||||
UID: uid,
|
||||
ClickId: clickId,
|
||||
ObjType: objType,
|
||||
AdsType: adsType,
|
||||
CreatedAt: now,
|
||||
UpdatedAt: now,
|
||||
})
|
||||
return err
|
||||
}
|
||||
|
||||
func GetDailyClickCount(uid uint64) (uint64, error) {
|
||||
year, month, day := time.Now().Date()
|
||||
start := time.Date(year, month, day, 0, 0, 0, 0, time.Local)
|
||||
end := time.Date(year, month, day+1, 0, 0, 0, 0, time.Local)
|
||||
res, err := coll(nil).Distinct("clickId", bson.M{"uid": uid, "adsType": 1, "createdAt": bson.M{"$gte": start, "$lt": end}})
|
||||
return uint64(len(res)), err
|
||||
}
|
||||
@@ -0,0 +1,121 @@
|
||||
package exchlogmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"91porn-server/common"
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
"91porn-server/models/commod"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.ExchLog
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{ //batch set indexes //value is the type 1 or -1
|
||||
{
|
||||
Keys: bson.D{{Key: "code", Value: 1}, {Key: "createdAt", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "userID", Value: 1}, {Key: "createdAt", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "userID", Value: 1}, {Key: "batchNum", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "channel", Value: 1}, {Key: "createdAt", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "authority", Value: 1}, {Key: "createdAt", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: 1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func Insert(doc ExchangeLog) error {
|
||||
if _, err := coll(nil).InsertOne(doc); err != nil {
|
||||
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "Insert", table, "InsertOne", err),
|
||||
log.Any("doc", doc),
|
||||
)
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func GetExchangeLogList(filterParams FilterDoc, page commod.Page) (total int64, data []ExchangeLog, err error) {
|
||||
filter, _ := common.ToBsonM(filterParams)
|
||||
var skip = int64((page.PageNumber - 1) * page.PageSize)
|
||||
var limit = int64(page.PageSize)
|
||||
var opts = options.Find()
|
||||
opts.SetSort(bson.D{{Key: "createdAt", Value: -1}}).SetSkip(skip).SetLimit(limit)
|
||||
if err = coll(nil).Find(&data, filter, opts); err != nil {
|
||||
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetExchangeLogList", table, "Find", err),
|
||||
log.Any("filterParams", filterParams),
|
||||
log.Any("page", page),
|
||||
)
|
||||
return
|
||||
}
|
||||
if total, err = coll(nil).Count(filter); err != nil {
|
||||
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetExchangeLogList", table, "Count", err),
|
||||
log.Any("filterParams", filterParams),
|
||||
log.Any("page", page),
|
||||
)
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// 获取用户兑换日志
|
||||
func GetLogByUIDAndBatchNum(uid uint64, batchNum string) (data ExchangeLog, err error) {
|
||||
if err = coll(nil).FindOne(&data, bson.M{"userID": uid, "batchNum": batchNum}); err != nil {
|
||||
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetExchangeLogList", table, "Find", err),
|
||||
log.Any("uid", uid),
|
||||
log.Any("batchNum", batchNum),
|
||||
)
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// 获取用户兑换日志
|
||||
func GetLogByUIDAndAuthority(uid uint64, authority string) (data ExchangeLog, err error) {
|
||||
if err = coll(nil).FindOne(&data, bson.M{"userID": uid, "authority": authority}); err != nil {
|
||||
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetExchangeLogList", table, "Find", err),
|
||||
log.Any("uid", uid),
|
||||
log.Any("authority", authority),
|
||||
)
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// 获取用户兑换
|
||||
func GetLogByUIDAndCode(uid uint64, code string) (data ExchangeLog, err error) {
|
||||
if err = coll(nil).FindOne(&data, bson.M{"userID": uid, "code": code}); err != nil {
|
||||
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetLogByUIDAndCode", table, "Find", err),
|
||||
log.Any("uid", uid),
|
||||
log.Any("code", code),
|
||||
)
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
package exchlogmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
type ObjectID = primitive.ObjectID
|
||||
|
||||
// Init 初始化索引
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
|
||||
type ExchangeLog struct {
|
||||
ID ObjectID `json:"id" bson:"_id,omitempty"`
|
||||
Code string `json:"code" bson:"code"` // 兑换码
|
||||
UserID uint64 `json:"userID" bson:"userID"` // 兑换者
|
||||
BatchNum string `json:"batchNum" bson:"batchNum"` // 批次号
|
||||
Channel string `json:"channel" bson:"channel"` // 所属渠道
|
||||
Authority string `json:"authority" bson:"authority"` // 兑换权限
|
||||
Desc string `json:"desc" bson:"-"` // 说明
|
||||
Reward int `json:"reward" bson:"reward"` // 奖励值
|
||||
RewardCount int `json:"rewardCount" bson:"rewardCount"` // 奖励量
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"` // 创建时间/兑换时间
|
||||
}
|
||||
|
||||
type FilterDoc struct {
|
||||
Code *string `bson:"code,omitempty"` // 兑换码
|
||||
UserID *uint64 `bson:"userID,omitempty"` // 兑换者
|
||||
Channel *string `bson:"channel,omitempty"` // 所属渠道
|
||||
Authority *string `bson:"authority,omitempty"` // 兑换权限
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package exchlogmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/models/commod"
|
||||
)
|
||||
|
||||
type ListReqParam struct {
|
||||
Code *string `form:"code" json:"code"` // 兑换码
|
||||
UserID *uint64 `form:"userID" json:"userID"` // 兑换者
|
||||
Channel *string `form:"channel" json:"channel"` // 所属渠道
|
||||
Authority *string `form:"authority" json:"authority"` // 兑换权限
|
||||
Page commod.Page
|
||||
}
|
||||
|
||||
type ListResp struct {
|
||||
Code string `json:"code"` // 兑换码
|
||||
UserID uint64 `json:"userID"` // 兑换者
|
||||
Channel string `json:"channel"` // 所属渠道
|
||||
Authority string `json:"authority"` // 兑换权限
|
||||
Reward int `json:"reward"` // 奖励值
|
||||
RewardCount int `json:"rewardCount"` // 奖励量
|
||||
CreatedAt time.Time `json:"createdAt"` // 创建时间/兑换时间
|
||||
}
|
||||
@@ -0,0 +1,127 @@
|
||||
package loginlgmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"math"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.LoginLog
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// initIndex 设置index
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{ //batch set indexes //value is the type 1 or -1
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "devID", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "loginTime", Value: 1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func InsertLoginLog(l *LoginLog) error {
|
||||
if _, err := coll(nil).InsertOne(l); err != nil {
|
||||
log.Error("loginlog insert err", log.E(err))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func WebGetDayActivity(uids []uint64, start time.Time, end time.Time) (data []LoginLog, err error) {
|
||||
if err = coll(nil).Find(
|
||||
&data,
|
||||
bson.M{
|
||||
"loginTime": bson.M{
|
||||
"$and": []bson.M{
|
||||
bson.M{"$gte": start},
|
||||
bson.M{"$lte": end},
|
||||
},
|
||||
},
|
||||
"uid": bson.M{
|
||||
"$in": uids,
|
||||
},
|
||||
},
|
||||
); err != nil {
|
||||
log.ZapLog.Error(fmt.Sprintf("model record login WebGetDayActivity fail error:%+v:", err))
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// GetTotalCnt 获取查询总数总数
|
||||
func getLoginLogTotalCnt(cond bson.M) (int64, error) {
|
||||
total, err := coll(nil).Count(cond)
|
||||
if err != nil {
|
||||
e := fmt.Sprintf("get total Cnt error: %+v\n", err)
|
||||
log.ZapLog.Error(e)
|
||||
return 0, err
|
||||
}
|
||||
return total, nil
|
||||
}
|
||||
|
||||
// GetSkipSize 计算跳转
|
||||
func getLoginLogSkipSize(page int, size int, cond bson.M) (int, int, int64, error) {
|
||||
total, err := getLoginLogTotalCnt(cond)
|
||||
if err != nil {
|
||||
return 0, 0, 0, err
|
||||
}
|
||||
totalpages := int(math.Ceil(float64(total) / float64(size)))
|
||||
if page > totalpages {
|
||||
page = totalpages
|
||||
}
|
||||
if page < 1 {
|
||||
page = 1
|
||||
}
|
||||
return (page - 1) * size, totalpages, total, nil
|
||||
}
|
||||
|
||||
// FindLoginLog 查找登陆日志
|
||||
func FindLoginLogList(page int, size int, cond bson.M, sort bson.D) ([]*LoginLog, int, int64, error) {
|
||||
skip, totalPages, total, err := getLoginLogSkipSize(page, size, cond)
|
||||
if err != nil {
|
||||
return nil, 0, 0, err
|
||||
}
|
||||
var back []*LoginLog
|
||||
if err = coll(nil).Aggregate(
|
||||
&back,
|
||||
[]bson.M{
|
||||
bson.M{"$match": cond},
|
||||
bson.M{"$sort": sort},
|
||||
bson.M{"$skip": skip},
|
||||
bson.M{"$limit": size},
|
||||
},
|
||||
); err != nil {
|
||||
e := fmt.Sprintf("get login logs error: %+v\n", err)
|
||||
log.ZapLog.Error(e)
|
||||
return nil, totalPages, total, err
|
||||
}
|
||||
return back, totalPages, total, nil
|
||||
}
|
||||
|
||||
func DeleteBeforeLoginTime(t *db.MongoTool, tm time.Time) error {
|
||||
_, err := coll(t).DeleteMany(bson.M{"loginTime": bson.M{"$lt": tm}})
|
||||
return err
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
package loginlgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/models/commod"
|
||||
)
|
||||
|
||||
// LoginLog 登陆记录
|
||||
type LoginLog struct {
|
||||
UID uint64 `json:"uid" bson:"uid"`
|
||||
IP string `json:"ip" bson:"ip"`
|
||||
SysType string `json:"sysType" bson:"sysType"` //操作系统类型 安卓 IOS
|
||||
Ver string `json:"ver" bson:"ver"` //APP版本号
|
||||
DevType string `json:"devType" bson:"devType"` //设备型号
|
||||
DevID string `json:"devID" bson:"devID"`
|
||||
BuildID string `json:"buildID" bson:"buildID"` //app构建ID(包ID)
|
||||
LoginTime time.Time `json:"loginTime" bson:"loginTime,omitempty"`
|
||||
LogoutTime time.Time `json:"logoutTime" bson:"logoutTime,omitempty"`
|
||||
Logout bool `json:"logout" bson:"logout"` //是否退出登陆
|
||||
}
|
||||
|
||||
// LogListResp 登陆日志查询列表
|
||||
type LogListResp struct {
|
||||
Logs []*LoginLog `json:"logs"`
|
||||
Total int64 `json:"total"`
|
||||
}
|
||||
|
||||
// QueryReq 登陆日志查询请求参数
|
||||
type QueryReq struct {
|
||||
commod.Page
|
||||
UID uint64 `form:"uid" json:"uid"`
|
||||
Start time.Time `form:"start" json:"start"`
|
||||
End time.Time `form:"end" json:"end"`
|
||||
Sort string `form:"sort" json:"sort"`
|
||||
Desc int `form:"desc" json:"desc"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,108 @@
|
||||
package lotterylgmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/common/timeutil/timerange"
|
||||
"91porn-server/models"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
const table = models.LotteryLog
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// initIndexAds 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}, {Key: "createdAt", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "code", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: 1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
// InsertLog 记录一个抽奖号行为
|
||||
func InsertLog(uid uint64, code int, gateName string) error {
|
||||
ll := LotteryLog{
|
||||
UID: uid,
|
||||
Code: code,
|
||||
GateName: gateName,
|
||||
CreatedAt: time.Now(),
|
||||
}
|
||||
if _, err := coll(nil).InsertOne(ll); err != nil {
|
||||
log.Error("InsertClickLog error", log.Any("ll", ll), log.E(err))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// UserTodayChances 获取用户当日抽奖号数量
|
||||
func UserTodayChances(uid uint64) (int, error) {
|
||||
sumDate := timerange.LocDayRange(time.Now()).Head
|
||||
ll := []LotteryLog{}
|
||||
cond := bson.M{"uid": uid, "createdAt": bson.M{"$gte": sumDate}}
|
||||
if err := coll(nil).Find(&ll, cond); err != nil {
|
||||
log.Error("UserTodayChances error", log.Any("uid", uid), log.E(err))
|
||||
return 0, err
|
||||
}
|
||||
return len(ll), nil
|
||||
}
|
||||
|
||||
// LottnumList 获取摇号列表
|
||||
func LottnumList(page, size uint64, start *time.Time, end *time.Time, uid *uint64, code *int) ([]LotteryLog, int64, error) {
|
||||
back := []LotteryLog{}
|
||||
cond := bson.M{}
|
||||
if uid != nil {
|
||||
cond["uid"] = *uid
|
||||
}
|
||||
if code != nil {
|
||||
cond["code"] = *code
|
||||
}
|
||||
if start != nil && end != nil {
|
||||
cond["createdAt"] = bson.M{"$gte": *start, "$lt": *end}
|
||||
}
|
||||
sort := bson.D{{Key: "createdAt", Value: -1}}
|
||||
skip := (page - 1) * size
|
||||
opts := options.FindOptions{}
|
||||
opts.SetSort(sort).SetSkip(int64(skip)).SetLimit(int64(size))
|
||||
if err := coll(nil).Find(&back, bson.M(cond), &opts); err != nil {
|
||||
log.Error("LottnumList error", log.Any("page", page), log.Any("size", size), log.Any("cond", cond), log.E(err))
|
||||
return back, 0, err
|
||||
}
|
||||
total, _ := coll(nil).Count(cond)
|
||||
return back, total, nil
|
||||
}
|
||||
|
||||
// UserTodayNum 获取用户当日抽奖号
|
||||
func UserTodayNum(uid uint64) ([]LotteryLog, error) {
|
||||
sumDate := timerange.LocDayRange(time.Now()).Head
|
||||
ll := []LotteryLog{}
|
||||
cond := bson.M{"uid": uid, "createdAt": bson.M{"$gte": sumDate}}
|
||||
if err := coll(nil).Find(&ll, cond); err != nil {
|
||||
log.Error("UserTodayChances error", log.Any("uid", uid), log.E(err))
|
||||
return ll, err
|
||||
}
|
||||
return ll, nil
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
package lotterylgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
)
|
||||
|
||||
// LotteryLog 活动摇号日志
|
||||
type LotteryLog struct {
|
||||
UID uint64 `json:"uid" bson:"uid"`
|
||||
Code int `json:"code" bson:"code"`
|
||||
GateName string `json:"gateName" bson:"gateName"`
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,50 @@
|
||||
package lotterylgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/models/commod"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
// AdsClickResp 广告点击日志应答
|
||||
type AdsClickResp struct {
|
||||
Logs int `json:"logs"`
|
||||
Total int64 `json:"total"`
|
||||
}
|
||||
|
||||
// AdsCountResp 广告点击统计应答
|
||||
type AdsCountResp struct {
|
||||
ID string `json:"id"`
|
||||
TodayCnt int64 `json:"todayCnt"`
|
||||
YesterdayCnt int64 `json:"yesterdayCnt"`
|
||||
WeekCnt int64 `json:"weekCnt"`
|
||||
MonthCnt int64 `json:"monthCnt"`
|
||||
TotalCnt int64 `json:"totalCnt"`
|
||||
}
|
||||
|
||||
type AdsClickReq struct {
|
||||
UID uint64 `form:"uid" json:"uid"`
|
||||
Start time.Time `form:"start" json:"start"`
|
||||
End time.Time `form:"end" json:"end"`
|
||||
Sort string `form:"sort" json:"sort"`
|
||||
Desc int `form:"desc" json:"desc"`
|
||||
commod.Page
|
||||
}
|
||||
|
||||
// AdsClickInfo
|
||||
type AdsClickInfo struct {
|
||||
AID primitive.ObjectID `json:"aid"` //广告id
|
||||
TodayCount int64 `json:"todayCount"` //今日点击数
|
||||
YesterdayCount int64 `json:"yesterdayCount"` //昨日点击数
|
||||
WeekCount int64 `json:"weekCount"` //本周点击数
|
||||
MonthCount int64 `json:"monthCount"` //本月点击数
|
||||
TotalCount int64 `json:"totalCount"` //总点击数
|
||||
}
|
||||
|
||||
// AdsStatisticResp 广告点击统计应答
|
||||
type AdsStatisticResp struct {
|
||||
Logs []AdsClickInfo `json:"logs"`
|
||||
Total int64 `json:"total"`
|
||||
}
|
||||
@@ -0,0 +1,148 @@
|
||||
package operatorlgmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"math"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
|
||||
"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"
|
||||
)
|
||||
|
||||
const table = models.WebOperatorLog
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// initIndexAds 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "manager", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "uri", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "position", Value: 1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
// RecordOperation 记录操作日志
|
||||
func RecordOperation(manager string, position string, operator string, content string, uri string) error {
|
||||
record := WebOperatorLog{
|
||||
Manager: manager,
|
||||
Position: position,
|
||||
Operator: operator,
|
||||
Content: content,
|
||||
URI: uri,
|
||||
CreatedAt: time.Now(),
|
||||
}
|
||||
if _, err := coll(nil).InsertOne(&record); err != nil {
|
||||
log.Error("RecordOperation error", log.Any("manager", manager), log.Any("position", position),
|
||||
log.Any("operator", operator), log.Any("content", content), log.Any("url", uri), log.E(err))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func backOperatorParam(param OperatorListReq) map[string]interface{} {
|
||||
m := make(map[string]interface{})
|
||||
if len(param.Manager) != 0 {
|
||||
m["manager"] = param.Manager
|
||||
}
|
||||
if len(param.Position) != 0 {
|
||||
m["position"] = param.Position
|
||||
}
|
||||
if len(param.URI) != 0 {
|
||||
m["uri"] = param.URI
|
||||
}
|
||||
if param.Content != "" {
|
||||
param.Content = strings.Trim(param.Content, " ")
|
||||
m["content"] = bson.M{"$regex": primitive.Regex{
|
||||
Pattern: param.Content,
|
||||
Options: "i",
|
||||
}}
|
||||
}
|
||||
if !param.End.IsZero() {
|
||||
i := make(map[string]time.Time)
|
||||
i["$gte"] = param.Start
|
||||
i["$lt"] = param.End
|
||||
m["createdAt"] = i
|
||||
}
|
||||
return m
|
||||
}
|
||||
|
||||
// getTotalCnt 获取后台操作日志总数
|
||||
func getTotalCnt(cond bson.M) (int64, error) {
|
||||
total, err := coll(nil).Count(cond)
|
||||
if err != nil {
|
||||
log.Error("getTotalCnt", log.Any("cond", cond), log.E(err))
|
||||
return 0, err
|
||||
}
|
||||
return total, nil
|
||||
}
|
||||
|
||||
// getSkipSize 计算跳转
|
||||
func getSkipSize(page, size uint64, cond bson.M) (uint64, uint64, int64, error) {
|
||||
total, err := getTotalCnt(cond)
|
||||
if err != nil {
|
||||
return 0, 0, 0, err
|
||||
}
|
||||
totalpages := uint64(math.Ceil(float64(total) / float64(size)))
|
||||
if page > totalpages {
|
||||
page = totalpages
|
||||
}
|
||||
if page < 1 {
|
||||
page = 1
|
||||
}
|
||||
return (page - 1) * size, totalpages, total, nil
|
||||
}
|
||||
|
||||
// GetOperatorLog 获取操作日志
|
||||
func GetOperatorLog(req OperatorListReq) ([]*WebOperatorLog, int64, error) {
|
||||
cond := backOperatorParam(req)
|
||||
sort := bson.D{{Key: "createdAt", Value: -1}}
|
||||
skip, _, total, err := getSkipSize(req.PageNumber, req.PageSize, bson.M(cond))
|
||||
if err != nil {
|
||||
return nil, 0, err
|
||||
}
|
||||
opts := options.FindOptions{}
|
||||
opts.SetSort(sort).SetSkip(int64(skip)).SetLimit(int64(req.PageSize))
|
||||
var back []*WebOperatorLog
|
||||
if err = coll(nil).Find(&back, bson.M(cond), &opts); err != nil {
|
||||
log.Error("GetOperatorLog error", log.Any("req", req), log.E(err))
|
||||
}
|
||||
return back, total, err
|
||||
}
|
||||
|
||||
// EditRemarks 更新备注
|
||||
func EditRemarks(id primitive.ObjectID, remarks string) error {
|
||||
cond := bson.M{"_id": id}
|
||||
update := bson.M{"$set": bson.M{"remarks": remarks}}
|
||||
if _, err := coll(nil).UpdateOne(cond, update); err != nil {
|
||||
log.Error("EditRemarks error", log.Any("id", id), log.Any("remarks", remarks), log.E(err))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
package operatorlgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
// WebOperatorLog 后台操作日志
|
||||
type WebOperatorLog struct {
|
||||
ID primitive.ObjectID `json:"id" bson:"_id,omitempty"`
|
||||
Manager string `json:"manager" bson:"manager"` //管理员账号
|
||||
Position string `json:"position" bson:"position"` //操作位置
|
||||
Operator string `json:"operator" bson:"operator"` //操作动作
|
||||
Content string `json:"content" bson:"content"` //操作内容
|
||||
URI string `json:"uri" bson:"uri"` //操作uri
|
||||
Remarks string `json:"remarks" bson:"remarks"` //备注
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
}
|
||||
|
||||
// Init 初始化索引
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
package operatorlgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/models/commod"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
// OperatorListReq 操作日志查询
|
||||
type OperatorListReq struct {
|
||||
Manager string `form:"manager" json:"manager"`
|
||||
Position string `form:"position" json:"position"`
|
||||
Content string `form:"content" json:"content" binding:"omitempty,min=2,max=100"`
|
||||
URI string `form:"uri" json:"uri"`
|
||||
Start time.Time `form:"start" json:"start"`
|
||||
End time.Time `form:"end" json:"end"`
|
||||
commod.Page
|
||||
}
|
||||
|
||||
// OperatorListResp 操作日志查询应答
|
||||
type OperatorListResp struct {
|
||||
Infos []*WebOperatorLog `json:"infos"`
|
||||
Total int64 `json:"total"`
|
||||
}
|
||||
|
||||
// OperatorModifyReq 操作日志修改
|
||||
type OperatorModifyReq struct {
|
||||
ID primitive.ObjectID `json:"id"`
|
||||
Remarks string `json:"remarks"`
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
package payvidlgmod
|
||||
|
||||
// Pay4VidLogQueryReq Pay4VidLogQueryReq
|
||||
type Pay4VidLogQueryReq struct {
|
||||
PublisherID *uint64 `json:"publisherID,omitempty" bson:"publisherID"` //上传者ID
|
||||
}
|
||||
@@ -0,0 +1,114 @@
|
||||
package payvidlgmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/common/pageopt"
|
||||
"91porn-server/common/ysinterface/disc"
|
||||
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
type DistrictStatKey struct {
|
||||
DiscSeqe `bson:",inline"` //商区码
|
||||
SysType string `bson:"sysType"` //系统类型 iOS Android
|
||||
}
|
||||
|
||||
func (d DistrictStatKey) GetDiscCode() string {
|
||||
return d.DistrictCode
|
||||
}
|
||||
|
||||
func (d DistrictStatKey) GetPromSeqe() string {
|
||||
return d.PromSeqe
|
||||
}
|
||||
|
||||
func (d DistrictStatKey) GetSysType() string {
|
||||
return d.SysType
|
||||
}
|
||||
|
||||
func (d DistrictStatKey) String() string {
|
||||
if d.DiscSeqe.String() == "" {
|
||||
return ""
|
||||
}
|
||||
return strings.ToUpper(strings.Join([]string{d.DiscSeqe.String(), d.SysType}, "-"))
|
||||
}
|
||||
|
||||
type DistrictStater = disc.DistrictStater
|
||||
|
||||
// DiscSeqeTransCount
|
||||
func DiscSeqeBuyVidCount(start, end time.Time, mats ...Matcher) (map[DistrictStater]int64, error) {
|
||||
mats = append(mats, (&CreatedAtGTEAndLTMatch{GTE: &start, LT: &end}).New())
|
||||
filter := pageopt.MergeM(mats)
|
||||
list := []DistrictStatKey{}
|
||||
opt := (&options.FindOptions{}).SetProjection(M{
|
||||
"districtCode": 1,
|
||||
"promSeqe": 1,
|
||||
"sysType": 1,
|
||||
})
|
||||
if err := coll(nil).Find(&list, filter, opt); err != nil {
|
||||
log.Warn(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "DiscSeqeTransCount", table, "Find", err))
|
||||
return nil, err
|
||||
}
|
||||
m := make(map[DistrictStater]int64)
|
||||
for _, v := range list {
|
||||
if v.String() != "" {
|
||||
m[v] += 1
|
||||
}
|
||||
}
|
||||
return m, nil
|
||||
}
|
||||
|
||||
// DiscSeqeBuyVidCoins
|
||||
func DiscSeqeBuyVidCoins(start, end time.Time, mats ...Matcher) (map[DistrictStater]int64, error) {
|
||||
mats = append(mats, (&CreatedAtGTEAndLTMatch{GTE: &start, LT: &end}).New())
|
||||
filter := pageopt.MergeM(mats)
|
||||
list := []struct {
|
||||
DistrictStatKey `bson:",inline"` //商区码
|
||||
Coins int64 `bson:"coins"`
|
||||
}{}
|
||||
opt := (&options.FindOptions{}).SetProjection(M{
|
||||
"districtCode": 1,
|
||||
"promSeqe": 1,
|
||||
"sysType": 1,
|
||||
"coins": 1,
|
||||
})
|
||||
if err := coll(nil).Find(&list, filter, opt); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
m := make(map[DistrictStater]int64, len(list))
|
||||
for _, v := range list {
|
||||
if v.String() != "" {
|
||||
m[v.DistrictStatKey] += v.Coins
|
||||
}
|
||||
}
|
||||
return m, nil
|
||||
}
|
||||
|
||||
// DiscSeqeTaxAmount
|
||||
func DiscSeqeTaxAmount(start, end time.Time, mats ...Matcher) (map[DistrictStater]float64, error) {
|
||||
mats = append(mats, (&CreatedAtGTEAndLTMatch{GTE: &start, LT: &end}).New())
|
||||
filter := pageopt.MergeM(mats)
|
||||
list := []struct {
|
||||
DistrictStatKey `bson:",inline"` //商区码
|
||||
TaxAmount float64 `bson:"taxAmount"` //税额
|
||||
}{}
|
||||
opt := (&options.FindOptions{}).SetProjection(M{
|
||||
"districtCode": 1,
|
||||
"promSeqe": 1,
|
||||
"sysType": 1,
|
||||
"taxAmount": 1,
|
||||
})
|
||||
if err := coll(nil).Find(&list, filter, opt); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
m := make(map[DistrictStater]float64, len(list))
|
||||
for _, v := range list {
|
||||
if v.String() != "" {
|
||||
m[v.DistrictStatKey] += v.TaxAmount
|
||||
}
|
||||
}
|
||||
return m, nil
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
package payvidlgmod
|
||||
|
||||
import (
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/common/pageopt"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
type Matcher = pageopt.Matcher
|
||||
|
||||
// DistrictCodeMatch
|
||||
type DistrictCodeMatch struct {
|
||||
DistrictCode *string
|
||||
}
|
||||
|
||||
func (s *DistrictCodeMatch) New() Matcher {
|
||||
return pageopt.NewAssignMatch("districtCode", s.DistrictCode)
|
||||
}
|
||||
|
||||
// IsDirectMatch
|
||||
type IsDirectMatch struct {
|
||||
IsDirect *bool
|
||||
}
|
||||
|
||||
func (b *IsDirectMatch) New() Matcher {
|
||||
return pageopt.NewAssignMatch("isDirect", b.IsDirect)
|
||||
}
|
||||
|
||||
// PromSeqeMatch
|
||||
type PromSeqeMatch struct {
|
||||
Seqe *string
|
||||
}
|
||||
|
||||
func (d *PromSeqeMatch) New() Matcher {
|
||||
return pageopt.NewAssignMatch("promSeqe", d.Seqe)
|
||||
}
|
||||
|
||||
// SysTypeMatch
|
||||
type SysTypeMatch struct {
|
||||
SysType *string
|
||||
}
|
||||
|
||||
func (d *SysTypeMatch) New() Matcher {
|
||||
return pageopt.NewAssignMatch("sysType", d.SysType)
|
||||
}
|
||||
|
||||
// CreatedAtGTEAndLTMatch
|
||||
type CreatedAtGTEAndLTMatch = pageopt.CreatedAtGTEAndLTMatch
|
||||
|
||||
type Sort = bson.D
|
||||
|
||||
var Sort_CreatedAt_n1 = Sort{{Key: "createdAt", Value: -1}}
|
||||
|
||||
func List(sort Sort, skip, limit *int64, matchers ...Matcher) ([]Pay4VidLog, error) {
|
||||
filter := pageopt.MergeM(matchers)
|
||||
opt := (&options.FindOptions{})
|
||||
if len(sort) != 0 {
|
||||
opt.SetSort(sort)
|
||||
}
|
||||
if skip != nil {
|
||||
opt.SetSkip(*skip)
|
||||
}
|
||||
if limit != nil {
|
||||
opt.SetLimit(*limit)
|
||||
}
|
||||
list := []Pay4VidLog{}
|
||||
if err := coll(nil).Find(&list, filter, opt); err != nil {
|
||||
log.Error("payvidlgmod List error", log.E(err))
|
||||
return nil, err
|
||||
}
|
||||
return list, nil
|
||||
}
|
||||
|
||||
func Count(matchers ...Matcher) (int64, error) {
|
||||
filter := pageopt.MergeM(matchers)
|
||||
count, err := coll(nil).Count(filter)
|
||||
if err != nil {
|
||||
log.Error("payvidlgmod Count error", log.E(err))
|
||||
return 0, err
|
||||
}
|
||||
return count, nil
|
||||
}
|
||||
@@ -0,0 +1,602 @@
|
||||
package payvidlgmod
|
||||
|
||||
import (
|
||||
"91porn-server/models/commod"
|
||||
"fmt"
|
||||
"math"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/common/pageopt"
|
||||
"91porn-server/common/timeutil"
|
||||
"91porn-server/models"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
"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"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.PayVideoLog
|
||||
|
||||
// initIndex 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}, {Key: "videoID", Value: 1}},
|
||||
Options: options.Index().SetUnique(true),
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: -1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "uniq", Value: 1}},
|
||||
Options: options.Index().SetUnique(true),
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "deductType", Value: 1}, {Key: "createdAt", Value: -1}},
|
||||
Options: options.Index().SetSparse(true),
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "videoID", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "publisherID", Value: 1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// InsertVideoPayRecord 插入一条购买记录
|
||||
func InsertVideoPayRecord(t *db.MongoTool, p Pay4VidLog) error {
|
||||
p.Uniq = Unique(p.UID, p.VideoID)
|
||||
p.CreatedAt = time.Now()
|
||||
res, err := coll(t).InsertOne(&p)
|
||||
if err != nil {
|
||||
log.Error("InsertVideoPayRecord error", log.Any("p", p), log.E(err))
|
||||
return err
|
||||
}
|
||||
p.ID = res.InsertedID.(ObjectID)
|
||||
return nil
|
||||
}
|
||||
|
||||
// IsPay4Video 用户是否购买了视频
|
||||
func IsPay4Video(uid uint64, videoID ObjectID) (bool, error) {
|
||||
cnt, err := coll(nil).Count(bson.M{"uid": uid, "videoID": videoID})
|
||||
if err != nil {
|
||||
log.Error("IsPay4Video error", log.Any("uid", uid), log.Any("videoID", videoID), log.E(err))
|
||||
return false, err
|
||||
}
|
||||
return cnt != 0, nil
|
||||
}
|
||||
|
||||
func FindManyPay4VidLogByUID(uid uint64, newsType string) ([]*Pay4VidLog, error) {
|
||||
vl := make([]*Pay4VidLog, 0)
|
||||
err := coll(nil).Find(&vl, bson.M{"uid": uid, "newsType": newsType})
|
||||
if err != nil {
|
||||
log.Error("FindManyPay4VidLogByUID error", log.Any("uid", uid), log.Any("err", err.Error()))
|
||||
return nil, err
|
||||
}
|
||||
return vl, nil
|
||||
}
|
||||
|
||||
// IsPay4Videos 用户是否购买了视频
|
||||
func IsPay4Videos(uid uint64, videoIDs []ObjectID) (map[ObjectID]bool, error) {
|
||||
if videoIDs == nil {
|
||||
videoIDs = []ObjectID{}
|
||||
}
|
||||
m := make(map[ObjectID]bool)
|
||||
var infos []Pay4VidLog
|
||||
query := bson.M{"uid": uid, "videoID": bson.M{"$in": videoIDs}}
|
||||
if err := coll(nil).Find(&infos, query); err != nil {
|
||||
log.Error("IsPay4Videos error", log.Any("uid", uid), log.Any("videoIDs", videoIDs), log.E(err))
|
||||
return m, err
|
||||
}
|
||||
for _, i := range infos {
|
||||
m[i.VideoID] = true
|
||||
}
|
||||
return m, nil
|
||||
}
|
||||
|
||||
// 判断当前视频是否有人购买过
|
||||
func IsVidIfBePay(id primitive.ObjectID) bool {
|
||||
var pay *Pay4VidLog
|
||||
if err := coll(nil).FindOne(&pay, bson.M{"videoID": id}); err != nil {
|
||||
log.Error("IsVidIfBePay error", log.Any("videoID", id), log.E(err))
|
||||
return false
|
||||
}
|
||||
return pay != nil
|
||||
}
|
||||
|
||||
// DelVideoPayRecord 删除一条购买记录
|
||||
func DelVideoPayRecord(videoID primitive.ObjectID, uid uint64) error {
|
||||
if _, err := coll(nil).DeleteOne(bson.M{"videoID": videoID, "uid": uid}); err != nil {
|
||||
log.Error("DelVideoPayRecord DeleteOne error", log.Any("videoID", videoID), log.Any("uid", uid))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// 从给定的hash列表中获取购买状态映射:uniq->Statue
|
||||
// uniq通过Unique()获取
|
||||
func PayStatueMap(uniqList []string) (map[string]bool, error) {
|
||||
filter := bson.M{
|
||||
"uniq": bson.M{"$in": uniqList},
|
||||
}
|
||||
payLogList := make([]Pay4VidLog, 0, len(uniqList))
|
||||
if err := coll(nil).Find(&payLogList, filter); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
m := make(map[string]bool, len(payLogList))
|
||||
//初始化
|
||||
for _, uniq := range uniqList {
|
||||
m[uniq] = false
|
||||
}
|
||||
//已经收藏的
|
||||
for _, v := range payLogList {
|
||||
uniq := v.Uniq
|
||||
m[uniq] = true
|
||||
}
|
||||
return m, nil
|
||||
}
|
||||
|
||||
func GetUIDListByPayTime(start time.Time, end time.Time) ([]uint64, error) {
|
||||
filter := bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
}
|
||||
list := make([]struct {
|
||||
UID uint64 `bson:"uid"`
|
||||
}, 0)
|
||||
if err := coll(nil).Find(&list, filter); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
uidList := make([]uint64, len(list))
|
||||
for i, v := range list {
|
||||
uidList[i] = v.UID
|
||||
}
|
||||
return uidList, nil
|
||||
}
|
||||
|
||||
func GetPayMoneyByTime(start time.Time, end time.Time) (int64, error) {
|
||||
filter := bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
}
|
||||
logs := make([]Pay4VidLog, 0)
|
||||
if err := coll(nil).Find(&logs, filter); err != nil {
|
||||
return 0, fmt.Errorf("table:%s GetPayMoneyByTime err: %s", table, err.Error())
|
||||
}
|
||||
total := int64(0)
|
||||
for _, v := range logs {
|
||||
total += v.PayMoney
|
||||
}
|
||||
return total, nil
|
||||
}
|
||||
|
||||
// FindManyVideoPayRecord 查询所有
|
||||
func FindThreeMonthVideoPayRecord(publisherID uint64, pageNumber, pageSize uint64) (total int64, totalAmount int64, data []*Pay4VidLog, hasNext bool, err error) {
|
||||
data = make([]*Pay4VidLog, 0)
|
||||
startTime := timeutil.NearMonth(time.Now(), 2)
|
||||
f := bson.M{"publisherID": publisherID, "createdAt": bson.M{"$gte": startTime}}
|
||||
skip := int64(pageSize * (pageNumber - 1))
|
||||
limit := int64(pageSize + 1)
|
||||
opts := options.FindOptions{
|
||||
Skip: &skip,
|
||||
Limit: &limit,
|
||||
Sort: bson.D{{Key: "createdAt", Value: -1}},
|
||||
}
|
||||
if err = coll(nil).Find(&data, f, &opts); err != nil {
|
||||
log.Error("FindManyVideoPayRecord error", log.Any("filter", f), log.E(err))
|
||||
}
|
||||
type Res struct {
|
||||
TotalAmount float64 `json:"totalAmount" bson:"totalAmount"`
|
||||
}
|
||||
totalIncome := []bson.M{
|
||||
{"$match": f},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": nil,
|
||||
"totalAmount": bson.M{
|
||||
"$sum": "$publisherIncome",
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
ress := make([]Res, 0)
|
||||
if err = coll(nil).Aggregate(&ress, totalIncome); err != nil {
|
||||
log.Error("FindManyVideoPayRecord error", log.Any("filter", f), log.E(err))
|
||||
}
|
||||
if len(ress) > 0 {
|
||||
totalAmount = int64(math.Floor(ress[0].TotalAmount))
|
||||
}
|
||||
total, err = coll(nil).Count(f)
|
||||
if err != nil {
|
||||
log.Error("FindManyVideoPayRecord Count error", log.Any("filter", f), log.E(err))
|
||||
}
|
||||
if len(data) > int(pageSize) {
|
||||
hasNext = true
|
||||
data = data[:pageSize]
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// GetWorksIncomeList 查询收益列表
|
||||
func GetWorksIncomeList(publisherID uint64, page commod.Page) (data []*Pay4VidLog, hasNext bool, err error) {
|
||||
data = make([]*Pay4VidLog, 0)
|
||||
opt := options.Find().
|
||||
SetLimit(page.Limit64() + 1).
|
||||
SetSkip(page.Skip64()).
|
||||
SetSort(bson.D{{"createdAt", -1}})
|
||||
|
||||
filter := bson.M{
|
||||
"publisherID": publisherID,
|
||||
}
|
||||
|
||||
if err = coll(nil).Find(&data, filter, opt); err != nil {
|
||||
log.Error("FindManyVideoPayRecord error", log.Any("filter", filter), log.E(err))
|
||||
return nil, false, err
|
||||
}
|
||||
hasNext = len(data) > int(page.Limit64())
|
||||
if hasNext {
|
||||
data = data[:page.Limit64()]
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// PayCoinByCreatedTime 金币
|
||||
func PayCoinByCreatedTime(start time.Time, end time.Time) (int64, error) {
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
// createdAt ∈ [startTime, endTime)
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": nil,
|
||||
"totalAmount": bson.M{"$sum": "$payMoney"},
|
||||
},
|
||||
},
|
||||
}
|
||||
var ret struct {
|
||||
TotalAmount int64 `bson:"totalAmount"`
|
||||
}
|
||||
if err := coll(nil).AggregateDecode(&ret, pipeline); err != nil {
|
||||
return 0, fmt.Errorf("table:%s PayCoinByCreatedTime err: %s", table, err.Error())
|
||||
}
|
||||
return ret.TotalAmount, nil
|
||||
}
|
||||
|
||||
// PayCoinMapByTime vid->金币 map
|
||||
func PayCoinMapByTime(start time.Time, end time.Time) (map[ObjectID]int64, error) {
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$videoID",
|
||||
"income": bson.M{
|
||||
"$sum": "$payMoney",
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
var docList []struct {
|
||||
VID ObjectID `bson:"_id"`
|
||||
Income int64 `bson:"income"`
|
||||
}
|
||||
if err := coll(nil).Aggregate(&docList, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("table:%s PayCoinMapByTime err: %s", table, err.Error())
|
||||
}
|
||||
ret := make(map[ObjectID]int64)
|
||||
for _, doc := range docList {
|
||||
ret[doc.VID] = doc.Income
|
||||
}
|
||||
return ret, nil
|
||||
}
|
||||
|
||||
func VideoCoinIncomeGross(start, end time.Time) (int64, error) {
|
||||
matchStage := bson.M{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
}
|
||||
groupStage := bson.M{
|
||||
"$group": bson.M{
|
||||
"_id": nil,
|
||||
"gross": bson.M{
|
||||
"$sum": "$payMoney",
|
||||
},
|
||||
},
|
||||
}
|
||||
var gross struct {
|
||||
Gross int64 `bson:"gross"`
|
||||
}
|
||||
pipeline := []bson.M{matchStage, groupStage}
|
||||
// opts := options.Aggregate()
|
||||
if err := coll(nil).AggregateDecode(&gross, pipeline); err != nil {
|
||||
log.Error("VideoCoinIncomeGross err: " + err.Error())
|
||||
return 0, errors.Wrapf(err, "table:%s VideoCoinIncomeGross", table)
|
||||
}
|
||||
return gross.Gross, nil
|
||||
}
|
||||
|
||||
// VideoCoinIncomeAggregateByVideoIDs 根据视频ID统计视频的售卖总数以及总金币数
|
||||
func VideoCoinIncomeAggregateByVideoIDs(ids []primitive.ObjectID) (list []VideoCoinIncome, err error) {
|
||||
if len(ids) == 0 {
|
||||
return
|
||||
}
|
||||
matchStage := bson.M{
|
||||
"$match": bson.M{
|
||||
"videoID": bson.M{"$in": ids},
|
||||
},
|
||||
}
|
||||
groupStage := bson.M{
|
||||
"$group": bson.M{
|
||||
"_id": "$videoID",
|
||||
"total": bson.M{
|
||||
"$sum": "$payMoney",
|
||||
},
|
||||
"count": bson.M{
|
||||
"$sum": 1,
|
||||
},
|
||||
},
|
||||
}
|
||||
pipeline := []bson.M{matchStage, groupStage}
|
||||
opts := options.Aggregate().SetMaxTime(10 * time.Second)
|
||||
if err := coll(nil).Aggregate(&list, pipeline, opts); err != nil {
|
||||
return nil, errors.Wrapf(err, "table:%s VideoCoinIncomeAggregateByVideoIDs", table)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// VideoCoinIncomeAggregate 聚合统计在给定时间段内视频收入排名前N的视频
|
||||
func VideoCoinIncomeAggregateTopN(topN int, start, end time.Time) (list []VideoCoinIncome, err error) {
|
||||
matchStage := bson.M{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
}
|
||||
groupStage := bson.M{
|
||||
"$group": bson.M{
|
||||
"_id": "$videoID",
|
||||
"total": bson.M{
|
||||
"$sum": "$payMoney",
|
||||
},
|
||||
"count": bson.M{
|
||||
"$sum": 1,
|
||||
},
|
||||
},
|
||||
}
|
||||
sortStage := bson.M{
|
||||
"$sort": bson.M{
|
||||
"total": -1,
|
||||
"count": -1,
|
||||
},
|
||||
}
|
||||
limitStage := bson.M{
|
||||
"$limit": topN,
|
||||
}
|
||||
pipeline := []bson.M{matchStage, groupStage, sortStage, limitStage}
|
||||
opts := options.Aggregate().SetMaxTime(10 * time.Second)
|
||||
if err := coll(nil).Aggregate(&list, pipeline, opts); err != nil {
|
||||
return nil, errors.Wrapf(err, "table:%s VideoCoinIncomeAggregateTopN", table)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// PayCountMapByTime vid->金币 map
|
||||
func PayCountMapByTime(start time.Time, end time.Time) (map[ObjectID]int64, error) {
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$videoID",
|
||||
"count": bson.M{
|
||||
"$sum": 1,
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
var docList []struct {
|
||||
VID ObjectID `bson:"_id"`
|
||||
Count int64 `bson:"count"`
|
||||
}
|
||||
if err := coll(nil).Aggregate(&docList, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("table:%s PayCoinMapByTime err: %s", table, err.Error())
|
||||
}
|
||||
ret := make(map[ObjectID]int64)
|
||||
for _, doc := range docList {
|
||||
ret[doc.VID] = doc.Count
|
||||
}
|
||||
return ret, nil
|
||||
}
|
||||
|
||||
// TaxAmountMapByTime vid->TaxAmount map
|
||||
func TaxAmountMapByTime(start time.Time, end time.Time) (map[ObjectID]float64, error) {
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$videoID",
|
||||
"taxAmount": bson.M{
|
||||
"$sum": "$taxAmount",
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
var docList []struct {
|
||||
VID ObjectID `bson:"_id"`
|
||||
TaxAmount float64 `bson:"taxAmount"`
|
||||
}
|
||||
if err := coll(nil).Aggregate(&docList, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("table:%s PayCoinMapByTime err: %s", table, err.Error())
|
||||
}
|
||||
ret := make(map[ObjectID]float64)
|
||||
for _, doc := range docList {
|
||||
ret[doc.VID] += doc.TaxAmount
|
||||
}
|
||||
return ret, nil
|
||||
}
|
||||
|
||||
func PublisherIncomeMapByTime(start time.Time, end time.Time) (map[uint64]int64, error) {
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$publisherID",
|
||||
"income": bson.M{
|
||||
"$sum": "$payMoney",
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
var docList []struct {
|
||||
PublisherID uint64 `bson:"_id"`
|
||||
Income int64 `bson:"income"`
|
||||
}
|
||||
if err := coll(nil).Aggregate(&docList, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("table:%s PublisherIncomeMapByTime err: %s", table, err.Error())
|
||||
}
|
||||
ret := make(map[uint64]int64)
|
||||
for _, doc := range docList {
|
||||
ret[doc.PublisherID] = doc.Income
|
||||
}
|
||||
return ret, nil
|
||||
}
|
||||
|
||||
// TaxAmountByTime
|
||||
func TaxAmountByTime(start, end time.Time, mats ...Matcher) (float64, error) {
|
||||
mats = append(mats, (&CreatedAtGTEAndLTMatch{GTE: &start, LT: &end}).New())
|
||||
filter := pageopt.MergeM(mats)
|
||||
var list []struct {
|
||||
TaxAmount float64 `bson:"taxAmount"` //税额
|
||||
}
|
||||
opt := (&options.FindOptions{}).SetProjection(M{
|
||||
"taxAmount": 1,
|
||||
})
|
||||
if err := coll(nil).Find(&list, filter, opt); err != nil {
|
||||
return 0, err
|
||||
}
|
||||
var taxAmount float64
|
||||
for _, v := range list {
|
||||
taxAmount += v.TaxAmount
|
||||
}
|
||||
return taxAmount, nil
|
||||
}
|
||||
|
||||
func FindByUID(uid uint64, newsType string, pageNumber int64, pageSize int64) (data []*Pay4VidLog, hasNext bool, err error) {
|
||||
data = make([]*Pay4VidLog, 0)
|
||||
opt := options.Find().
|
||||
SetLimit(pageSize + 1).
|
||||
SetSkip((pageNumber - 1) * pageSize).
|
||||
SetSort(bson.D{{"createdAt", -1}})
|
||||
|
||||
filter := bson.M{
|
||||
"uid": uid,
|
||||
"newsType": newsType,
|
||||
}
|
||||
err = coll(nil).Find(&data, filter, opt)
|
||||
if err != nil {
|
||||
log.Error("FindByUID error", log.Any("uid", uid), log.Any("err", err.Error()))
|
||||
return nil, false, err
|
||||
}
|
||||
if len(data) > int(pageSize) {
|
||||
hasNext = true
|
||||
data = data[:pageSize]
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
func PublisherVideoDeductionRange(uid uint64, start, end time.Time) ([]PublisherDeductionStat, error) {
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
// createdAt ∈ [startTime, endTime)
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
"publisherID": uid,
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$isVideoDeduction",
|
||||
"totalAmount": bson.M{"$sum": "$coins"},
|
||||
"videoCount": bson.M{"$sum": 1},
|
||||
},
|
||||
},
|
||||
}
|
||||
docList := []PublisherDeductionStat{}
|
||||
return docList, coll(nil).Aggregate(&docList, pipeline)
|
||||
}
|
||||
|
||||
func GetPayVidLogsByTime(start time.Time, end time.Time) ([]Pay4VidLogShort, error) {
|
||||
filter := bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
}
|
||||
logs := make([]Pay4VidLogShort, 0)
|
||||
if err := coll(nil).Find(&logs, filter); err != nil {
|
||||
return logs, fmt.Errorf("table:%s GetPayMoneyByTime err: %s", table, err.Error())
|
||||
}
|
||||
return logs, nil
|
||||
}
|
||||
@@ -0,0 +1,78 @@
|
||||
package payvidlgmod
|
||||
|
||||
import (
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/models/commod"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
type (
|
||||
ObjectID = primitive.ObjectID
|
||||
|
||||
M = bson.M
|
||||
|
||||
DiscSeqe = commod.DiscSeqe
|
||||
|
||||
DiscDoc = commod.DiscDoc
|
||||
)
|
||||
|
||||
// Pay4VidLog 购买影片记录
|
||||
type Pay4VidLog struct {
|
||||
ID primitive.ObjectID `json:"id" bson:"_id,omitempty"` // ID
|
||||
UID uint64 `json:"uid" bson:"uid"` // 用户ID
|
||||
Title string `json:"title" bson:"title,required"` // 视频标题
|
||||
NewsType string `json:"newsType" bson:"newsType"` // 类型
|
||||
VideoID primitive.ObjectID `json:"videoID" bson:"videoID"` // 视频id
|
||||
PlayTime uint `json:"playTime" bson:"playTime"` // 影片长度
|
||||
Coins int64 `json:"coins" bson:"coins"` // 定价
|
||||
Tax int64 `json:"tax" bson:"tax"` // 税率
|
||||
TaxAmount float64 `json:"taxAmount" bson:"taxAmount"` // 系统收取的税额 税率*定价
|
||||
PayMoney int64 `json:"payMoney" bson:"payMoney"` // 金币
|
||||
PublisherIncome float64 `json:"publisherIncome" bson:"publisherIncome"` // 上传者实际收益 定价-系统收取的税额
|
||||
PublisherID uint64 `json:"publisherID" bson:"publisherID"` // 上传者ID
|
||||
Uniq string `json:"uniq" bson:"uniq"` // UID.VideoID
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"` // 创建时间
|
||||
SysType string `json:"sysType" bson:"sysType"` // 系统类型
|
||||
IsVideoDeduction bool `json:"isVideoDeduction" bson:"isVideoDeduction"` // 是否扣量
|
||||
DiscDoc `bson:",inline"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
|
||||
func Unique(uid uint64, videoID primitive.ObjectID) string {
|
||||
list := []string{
|
||||
strconv.FormatInt(int64(uid), 10),
|
||||
videoID.Hex(),
|
||||
}
|
||||
s := strings.Join(list, ".")
|
||||
return s
|
||||
}
|
||||
|
||||
type VideoCoinIncome struct {
|
||||
VID ObjectID `bson:"_id" json:"videoID"` //video id
|
||||
Total int64 `bson:"total" json:"total"` //视频总金币
|
||||
Count int64 `bson:"count" json:"count"` //视频购买总次数
|
||||
}
|
||||
|
||||
type PublisherDeductionStat struct {
|
||||
IsVideoDeduction bool `bson:"_id"` // 是否扣量
|
||||
TotalAmount int64 `bson:"totalAmount"` // 视频总售卖(金币)
|
||||
VideoCount int64 `bson:"videoCount"` // 总计视频数
|
||||
}
|
||||
|
||||
// Pay4VidLogShort 购买影片短结构
|
||||
type Pay4VidLogShort struct {
|
||||
ID primitive.ObjectID `json:"id" bson:"_id,omitempty"`
|
||||
VideoID primitive.ObjectID `json:"videoID" bson:"videoID"`
|
||||
PayMoney int64 `json:"payMoney" bson:"payMoney"` //金币
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
}
|
||||
@@ -0,0 +1,426 @@
|
||||
package playlgmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"math"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
|
||||
"github.com/jinzhu/now"
|
||||
"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"
|
||||
)
|
||||
|
||||
const table = models.PlayLog
|
||||
const maxReadVideos = 200
|
||||
|
||||
// initIndex 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "videoID", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: -1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// InsertPlayRecord 记录一个播放行为
|
||||
func InsertPlayRecord(p PlayLog) error {
|
||||
if _, err := coll(nil).InsertOne(&p); err != nil {
|
||||
log.Error("InsertPlayRecord error", log.Any("p", p), log.E(err))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// HasWatchedVideo 已经观看的视频
|
||||
func HasWatchedVideo(uid uint64) ([]primitive.ObjectID, error) {
|
||||
now := time.Now()
|
||||
begin := now.AddDate(0, 0, -7)
|
||||
var logs []*PlayLog
|
||||
opts := options.FindOptions{}
|
||||
opts.SetSort(bson.D{{Key: "createdAt", Value: -1}}).SetLimit(maxReadVideos)
|
||||
if err := coll(nil).Find(&logs, bson.M{"uid": uid, "createdAt": bson.M{"$gt": begin}}, &opts); err != nil {
|
||||
log.Error("HasWatchedVideo error", log.Any("uid", uid), log.E(err))
|
||||
return nil, err
|
||||
}
|
||||
vids := make([]primitive.ObjectID, len(logs))
|
||||
for i, l := range logs {
|
||||
vids[i] = l.VideoID
|
||||
}
|
||||
return vids, nil
|
||||
}
|
||||
|
||||
// HasWatchedVideoCnt 已经观看的视频数
|
||||
func HasWatchedVideoCnt(uids []uint64) ([]UIDCount, error) {
|
||||
now := time.Now()
|
||||
begin := now.AddDate(0, 0, -4)
|
||||
var datas []UIDCount
|
||||
cond := bson.M{"uid": bson.M{"$in": uids}, "createdAt": bson.M{"$gt": begin}}
|
||||
if err := coll(nil).Aggregate(&datas, []bson.M{
|
||||
bson.M{"$match": cond},
|
||||
bson.M{"$group": bson.M{"_id": "$uid", "count": bson.M{"$sum": 1}}},
|
||||
}); err != nil {
|
||||
log.Error("HasWatchedVideoCnt error", log.Any("uids", uids), log.E(err))
|
||||
}
|
||||
return datas, nil
|
||||
}
|
||||
|
||||
// HasWatchedTags 当天已经观看过的标签id
|
||||
func HasWatchedTags(uid uint64, top int) ([]string, error) {
|
||||
tagIDs := []string{}
|
||||
var data []TagIDCount
|
||||
if err := coll(nil).Aggregate(&data, []bson.M{
|
||||
bson.M{"$match": bson.M{"uid": uid, "tagID": bson.M{"$exists": true}, "createdAt": bson.M{"$gte": now.BeginningOfDay()}}},
|
||||
bson.M{"$group": bson.M{"_id": "$tagID", "count": bson.M{"$sum": 1}}},
|
||||
bson.M{"$sort": bson.D{{Key: "count", Value: -1}}},
|
||||
bson.M{"$limit": top},
|
||||
}); err != nil {
|
||||
log.Error("HasWatchedTags error", log.Any("uid", uid), log.Any("top", top), log.E(err))
|
||||
return tagIDs, err
|
||||
}
|
||||
tagIDs = make([]string, len(data))
|
||||
for i, d := range data {
|
||||
tagIDs[i] = d.TagID.Hex()
|
||||
}
|
||||
return tagIDs, nil
|
||||
}
|
||||
|
||||
// getPlayRecordSkipSize 计算跳转
|
||||
func getPlayRecordSkipSize(page, size uint64, cond bson.M) (uint64, uint64, uint64, error) {
|
||||
var total uint64 = 10000
|
||||
totalpages := uint64(math.Ceil(float64(total) / float64(size)))
|
||||
if page > totalpages {
|
||||
page = totalpages
|
||||
}
|
||||
if page < 1 {
|
||||
page = 1
|
||||
}
|
||||
return (page - 1) * size, totalpages, total, nil
|
||||
}
|
||||
|
||||
// GetPlayRecordList 获取播放记录
|
||||
func getPlayRecordList(page, size uint64, cond bson.M, sort bson.D) ([]*PlayLog, uint64, uint64, error) {
|
||||
skip, totalPages, total, err := getPlayRecordSkipSize(page, size, cond)
|
||||
if err != nil {
|
||||
return nil, 0, 0, err
|
||||
}
|
||||
opts := options.FindOptions{}
|
||||
if sort != nil {
|
||||
opts.SetSort(sort)
|
||||
}
|
||||
opts.SetSkip(int64(skip)).SetLimit(int64(size))
|
||||
var back []*PlayLog
|
||||
if err = coll(nil).Find(&back, cond, &opts); err != nil {
|
||||
log.Error("GetPlayRecordList error", log.Any("page", page), log.Any("size", size),
|
||||
log.Any("cond", cond), log.Any("sort", sort), log.E(err))
|
||||
return nil, totalPages, total, err
|
||||
}
|
||||
return back, totalPages, total, nil
|
||||
}
|
||||
|
||||
// GetNearPlayLog 获取用户最近的观影记录
|
||||
func GetNearPlayLog(uid uint64) error {
|
||||
var p PlayLog
|
||||
opts := options.FindOne().SetSort(bson.D{{Key: "createdAt", Value: -1}})
|
||||
return coll(nil).FindOne(&p, bson.M{"uid": uid}, opts)
|
||||
}
|
||||
|
||||
// GetViewLogToday 当天是否看过此视频
|
||||
func GetViewLogToday(uid uint64, vid primitive.ObjectID) bool {
|
||||
cond := bson.M{"uid": uid, "videoID": vid, "createdAt": bson.M{"$gte": now.BeginningOfDay(), "$lte": now.EndOfDay()}}
|
||||
cnt, _ := coll(nil).Count(cond)
|
||||
return cnt > 0
|
||||
}
|
||||
|
||||
// 当天是否观看过视频
|
||||
func IsViewToday(uid uint64) bool {
|
||||
cond := bson.M{"uid": uid, "createdAt": bson.M{"$gte": now.BeginningOfDay(), "$lte": now.EndOfDay()}}
|
||||
cnt, _ := coll(nil).Count(cond)
|
||||
return cnt > 0
|
||||
}
|
||||
|
||||
// PlayCountMapByTime PlayCountMapByTime playWays 0免费 1付费 2.试看
|
||||
func PlayCountMapByTime(start time.Time, end time.Time, playWays []int) (map[primitive.ObjectID]int64, error) {
|
||||
if len(playWays) == 0 {
|
||||
return make(map[primitive.ObjectID]int64), nil
|
||||
}
|
||||
filter := bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
"playWay": bson.M{"$in": playWays}, //0免费 1付费 2.试看
|
||||
}
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": filter,
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$videoID",
|
||||
"count": bson.M{
|
||||
"$sum": 1,
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
list := make([]struct {
|
||||
VID primitive.ObjectID `bson:"_id"`
|
||||
Count int64 `bson:"count"`
|
||||
}, 0)
|
||||
if err := coll(nil).Aggregate(&list, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("PlayLog PlayCountMapByTime err: %s", err.Error())
|
||||
}
|
||||
ret := make(map[primitive.ObjectID]int64)
|
||||
for _, v := range list {
|
||||
ret[v.VID] = v.Count
|
||||
}
|
||||
return ret, nil
|
||||
}
|
||||
|
||||
func GetPayUserCount(vid []primitive.ObjectID) (int64, error) {
|
||||
if len(vid) == 0 {
|
||||
return 0, nil
|
||||
}
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"videoID": bson.M{
|
||||
"$in": vid,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$uid",
|
||||
},
|
||||
},
|
||||
}
|
||||
count, err := coll(nil).Count(pipeline)
|
||||
if err != nil {
|
||||
return 0, fmt.Errorf("GetPatUserCount err: %s", err.Error())
|
||||
}
|
||||
return count, nil
|
||||
}
|
||||
|
||||
// PlayUIDListByTime
|
||||
// playWay 0,免费 1付费 2.试看 ,nil All
|
||||
func PlayUIDListByTime(start time.Time, end time.Time, playWay *int) ([]uint64, error) {
|
||||
match := bson.M{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
},
|
||||
}
|
||||
if playWay != nil {
|
||||
match["playWay"] = *playWay //0,免费 1付费 2.试看
|
||||
}
|
||||
pipeline := []bson.M{match}
|
||||
pipeline = append(pipeline,
|
||||
bson.M{
|
||||
"$group": bson.M{
|
||||
"_id": "$uid",
|
||||
},
|
||||
})
|
||||
list := []struct {
|
||||
UID uint64 `bson:"_id"`
|
||||
}{}
|
||||
if err := coll(nil).Aggregate(&list, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("PlayUIDListByTime err: %s", err.Error())
|
||||
}
|
||||
uidList := make([]uint64, len(list))
|
||||
for i, v := range list {
|
||||
uidList[i] = v.UID
|
||||
}
|
||||
return uidList, nil
|
||||
}
|
||||
|
||||
func backWatchParam(param WatchReq) map[string]interface{} {
|
||||
m := make(map[string]interface{})
|
||||
if param.UID > 0 {
|
||||
m["uid"] = param.UID
|
||||
}
|
||||
if param.PlayWay == 1 {
|
||||
m["playWay"] = 0
|
||||
}
|
||||
if param.PlayWay == 2 {
|
||||
m["playWay"] = 1
|
||||
}
|
||||
if param.PlayWay == 3 {
|
||||
m["playWay"] = 2
|
||||
}
|
||||
if !param.End.IsZero() {
|
||||
i := make(map[string]time.Time)
|
||||
i["$gte"] = param.Start
|
||||
i["$lt"] = param.End
|
||||
m["createdAt"] = i
|
||||
}
|
||||
return m
|
||||
}
|
||||
|
||||
// GetPlayLog 获取播放日志
|
||||
func GetPlayLog(param WatchReq) ([]*PlayLog, uint64, error) {
|
||||
cond := backWatchParam(param)
|
||||
sort := bson.D{{Key: "createdAt", Value: -1}}
|
||||
infos, _, total, err := getPlayRecordList(param.PageNumber, param.PageSize, bson.M(cond), sort)
|
||||
return infos, total, err
|
||||
}
|
||||
|
||||
// GetUIDPlaySecondMap 用户播放时长(秒)map
|
||||
func GetUIDPlaySecondMap(uidList []uint64) (map[uint64]int64, error) {
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"uid": bson.M{
|
||||
"$in": uidList,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$uid",
|
||||
"playSecond": bson.M{
|
||||
"$sum": "$longer",
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
list := []struct {
|
||||
UID uint64 `bson:"_id"`
|
||||
PlaySecond int64 `bson:"playSecond"`
|
||||
}{}
|
||||
if err := coll(nil).Aggregate(&list, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("GetUIDPlayTimeMap err: %s", err.Error())
|
||||
}
|
||||
playSecondMap := make(map[uint64]int64, len(list))
|
||||
for _, v := range list {
|
||||
playSecondMap[v.UID] = v.PlaySecond
|
||||
}
|
||||
return playSecondMap, nil
|
||||
}
|
||||
|
||||
// 根据时间范围获取标签下的视频的播放次数
|
||||
func GetTagPlayByTimeRange(start time.Time, end time.Time) ([]TagPlayCount, error) {
|
||||
list := make([]TagPlayCount, 0)
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"tagID": bson.M{"$exists": true},
|
||||
"createdAt": bson.M{"$gte": start, "$lt": end},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": bson.M{"videoID": "$videoID", "tagID": "$tagID"},
|
||||
"playCount": bson.M{"$sum": 1},
|
||||
},
|
||||
},
|
||||
}
|
||||
if err := coll(nil).Aggregate(&list, pipeline); err != nil {
|
||||
log.Error("models log play log model GetTagPlayByTimeRange error", log.E(err), log.Any("start", start), log.Any("end", end))
|
||||
return nil, err
|
||||
}
|
||||
return list, nil
|
||||
}
|
||||
|
||||
// 获取播放量最多的视频
|
||||
func GetHotVid(start time.Time, end time.Time) ([]TagPlayCount, error) {
|
||||
list := make([]TagPlayCount, 0)
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"tagID": bson.M{"$exists": true},
|
||||
"createdAt": bson.M{"$gte": start, "$lt": end},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": bson.M{"videoID": "$videoID", "tagID": "$tagID"},
|
||||
"playCount": bson.M{"$sum": 1},
|
||||
},
|
||||
},
|
||||
}
|
||||
if err := coll(nil).Aggregate(&list, pipeline); err != nil {
|
||||
log.Error("models log play log model GetTagPlayByTimeRange error", log.E(err), log.Any("start", start), log.Any("end", end))
|
||||
return nil, err
|
||||
}
|
||||
return list, nil
|
||||
}
|
||||
|
||||
// 获取播放量最多的视频
|
||||
func GetHotVidIDs() ([]VidCount, error) {
|
||||
list := make([]VidCount, 0)
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"createdAt": bson.M{
|
||||
"$gte": time.Now().AddDate(0, 0, -1),
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$videoID",
|
||||
"count": bson.M{"$sum": 1},
|
||||
},
|
||||
},
|
||||
{"$sort": bson.M{
|
||||
"count": -1,
|
||||
}},
|
||||
{
|
||||
"$limit": 20,
|
||||
},
|
||||
}
|
||||
return list, coll(nil).Aggregate(&list, pipeline)
|
||||
}
|
||||
|
||||
// 获取播放量最多的视频
|
||||
func GetHotPublishesr() ([]PublisherCount, error) {
|
||||
list := make([]PublisherCount, 0)
|
||||
pipeline := []bson.M{
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$publisher",
|
||||
"count": bson.M{"$sum": 1},
|
||||
},
|
||||
},
|
||||
{"$match": bson.M{
|
||||
"_id": bson.M{"$gt": 0},
|
||||
}},
|
||||
{"$sort": bson.M{
|
||||
"count": -1,
|
||||
}},
|
||||
{
|
||||
"$limit": 20,
|
||||
},
|
||||
}
|
||||
return list, coll(nil).Aggregate(&list, pipeline)
|
||||
}
|
||||
|
||||
func DeleteBeforeCreatedAt(t *db.MongoTool, tm time.Time) error {
|
||||
_, err := coll(t).DeleteMany(bson.M{"createdAt": bson.M{"$lt": tm}})
|
||||
return err
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
package playlgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
// PlayLog 观看记录
|
||||
type PlayLog struct {
|
||||
UID uint64 `json:"uid" bson:"uid"`
|
||||
VideoID primitive.ObjectID `json:"videoID" bson:"videoID"`
|
||||
Longer int `json:"longer" bson:"longer"` //播放时长 单位:秒
|
||||
Progress int `json:"progress" bson:"progress"`
|
||||
Via int `json:"via" bson:"via"`
|
||||
PlayWay int `json:"playWay" bson:"playWay"` //0,免费 1付费 2.试看
|
||||
TagID primitive.ObjectID `json:"tagID" bson:"tagID,omitempty"`
|
||||
Publisher uint64 `json:"publisher" bson:"publisher,omitempty"`
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
}
|
||||
|
||||
type GroupKey struct {
|
||||
VideoID primitive.ObjectID `bson:"videoID"`
|
||||
TagID primitive.ObjectID `bson:"tagID"`
|
||||
}
|
||||
|
||||
type TagPlayCount struct {
|
||||
GroupID GroupKey `bson:"_id"`
|
||||
PlayCount int64 `bson:"playCount"`
|
||||
}
|
||||
|
||||
type TagPlayInfo struct {
|
||||
VideoID primitive.ObjectID
|
||||
TagID primitive.ObjectID
|
||||
PlayCount int64
|
||||
}
|
||||
|
||||
// TagIDCount 观看过的tagID统计
|
||||
type TagIDCount struct {
|
||||
TagID primitive.ObjectID `bson:"_id"`
|
||||
Count int `bson:"count"`
|
||||
}
|
||||
|
||||
// UIDCount 用户观看次数
|
||||
type UIDCount struct {
|
||||
UID uint64 `bson:"_id"`
|
||||
Count int `bson:"count"`
|
||||
}
|
||||
|
||||
// VidCount 视频观看次数
|
||||
type VidCount struct {
|
||||
//视频id
|
||||
VideoID primitive.ObjectID `json:"videoID" bson:"_id"`
|
||||
//次数
|
||||
Count int `bson:"count"`
|
||||
}
|
||||
|
||||
// PublisherCount 博主被观看次数
|
||||
type PublisherCount struct {
|
||||
//上传者id
|
||||
Publisher uint64 `json:"publisher" bson:"_id,omitempty"`
|
||||
//次数
|
||||
Count int `bson:"count"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
package playlgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/models/commod"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
// WatchReq 观看日志查询请求参数
|
||||
type WatchReq struct {
|
||||
PlayWay int `form:"playWay" json:"playWay"`
|
||||
UID uint64 `form:"uid" json:"uid"`
|
||||
Start time.Time `form:"start" json:"start"`
|
||||
End time.Time `form:"end" json:"end"`
|
||||
commod.Page
|
||||
}
|
||||
|
||||
// LogInfo 返回数据
|
||||
type LogInfo struct {
|
||||
UID uint64 `json:"uid"`
|
||||
VideoID primitive.ObjectID `json:"videoID"`
|
||||
Title string `json:"title"`
|
||||
PlayTime uint `json:"playTime"`
|
||||
Longer int `json:"longer" `
|
||||
Progress int `json:"progress"`
|
||||
Via int `json:"via"`
|
||||
PlayWay int `json:"playWay"` //0,免费 1付费 2.试看
|
||||
CreatedAt time.Time `json:"createdAt"`
|
||||
}
|
||||
|
||||
// WatchResp 观看日志查询请求应答
|
||||
type WatchResp struct {
|
||||
Logs []*LogInfo `json:"logs"`
|
||||
Total uint64 `json:"total"`
|
||||
}
|
||||
@@ -0,0 +1,62 @@
|
||||
package pullgmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.PullLog
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// initIndex 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: -1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "newUpdatedAt", Value: -1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
// InsertPullLog InsertPullLog
|
||||
func InsertPullLog(p PullLog) error {
|
||||
_, err := coll(nil).InsertOne(&p)
|
||||
return err
|
||||
}
|
||||
|
||||
// FindPullRecord 查询
|
||||
func FindPullRecord(vidType, newUpdateAt string) (pr *PullLog, err error) {
|
||||
opts := options.FindOne().SetSort(bson.D{{Key: "createdAt", Value: -1}})
|
||||
cond := bson.M{}
|
||||
if vidType != "" {
|
||||
cond["vidType"] = vidType
|
||||
}
|
||||
if newUpdateAt != "" {
|
||||
cond["newUpdatedAt"] = newUpdateAt
|
||||
}
|
||||
if err = coll(nil).FindOne(&pr, cond, opts); err != nil {
|
||||
log.Error("FindPullRecord error", log.E(err))
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
package pullgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
)
|
||||
|
||||
// PullLog 从aws同步视频记录
|
||||
type PullLog struct {
|
||||
LastID string `json:"lastId" bson:"lastId"`
|
||||
Count int `json:"count" bson:"count"`
|
||||
FailCount int `json:"failCount" bson:"failCount"`
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
FailIDs []string `json:"failIDs" bson:"failIDs,omitempty"`
|
||||
VidType string `json:"vidType" bson:"vidType"`
|
||||
NewUpdatedAt string `json:"newUpdatedAt" bson:"newUpdatedAt"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
package registermod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.NewRegister
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// initIndex 设置index
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{ //batch set indexes //value is the type 1 or -1
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}},
|
||||
Options: options.Index().SetUnique(true),
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "ip", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: 1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func InsertRegisterLog(l *NewRegisterLog) error {
|
||||
if _, err := coll(nil).InsertOne(l); err != nil {
|
||||
log.Error("loginlog insert err", log.E(err))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func DeleteBeforeCreatedAt(t *db.MongoTool, tm time.Time) error {
|
||||
_, err := coll(t).DeleteMany(bson.M{"createdAt": bson.M{"$lt": tm}})
|
||||
return err
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package registermod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
)
|
||||
|
||||
// 新注册用户Log 接口调用记录
|
||||
type NewRegisterLog struct {
|
||||
UID uint64 `json:"uid" bson:"uid"`
|
||||
IP string `json:"ip" bson:"ip"`
|
||||
Query []QueryStat `json:"query" bson:"query"` //接口调用次数记录表
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
}
|
||||
|
||||
type QueryStat struct {
|
||||
QueryUrl string `json:"key" bson:"key"`
|
||||
Count int64 `json:"count" bson:"count"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,148 @@
|
||||
package searchlogmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/constant"
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
"91porn-server/models/commod"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.SearchLog
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// InitIndex 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: -1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "realm", Value: 1}}, //不会新建 realm 索引
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "realm", Value: 1}, {Key: "keyword", Value: 1}}, //不会新建 realm 索引
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
// FindHotSearch 根据搜索量获取热搜排行榜
|
||||
func FindHotSearch(realm constant.RealmType, page commod.Page) ([]SearchCount, error) {
|
||||
p := []M{
|
||||
{
|
||||
"$match": M{"realm": realm},
|
||||
},
|
||||
{
|
||||
"$group": M{"_id": "$keyword", "count": M{"$sum": 1}},
|
||||
},
|
||||
{
|
||||
"$match": M{"_id": M{"$ne": ""}},
|
||||
},
|
||||
{
|
||||
"$sort": bson.D{{Key: "count", Value: -1}},
|
||||
},
|
||||
{
|
||||
"$skip": (page.PageNumber - 1) * page.PageSize,
|
||||
},
|
||||
{
|
||||
"$limit": page.PageSize,
|
||||
},
|
||||
}
|
||||
data := make([]SearchCount, 0, page.PageSize)
|
||||
if err := coll(nil).Aggregate(&data, p); err != nil {
|
||||
log.ZapLog.Error(fmt.Sprintf("models record SearchLog FindSearchCountVid fail error:%+v:", err))
|
||||
return nil, err
|
||||
}
|
||||
return data, nil
|
||||
}
|
||||
|
||||
// InsertMany InsertMany
|
||||
func InsertMany(uid uint64, realm constant.RealmType, keyWords []string) error {
|
||||
now := time.Now()
|
||||
searchLogDoc := make([]SearchLogDoc, 0, len(keyWords))
|
||||
for _, keyword := range keyWords {
|
||||
if keyword == "" {
|
||||
continue
|
||||
}
|
||||
searchLogDoc = append(searchLogDoc, SearchLogDoc{
|
||||
Realm: realm,
|
||||
UID: uid,
|
||||
Keyword: keyword,
|
||||
CreatedAt: now,
|
||||
})
|
||||
}
|
||||
if len(searchLogDoc) == 0 {
|
||||
return nil
|
||||
}
|
||||
if _, err := coll(nil).InsertMany(&searchLogDoc); err != nil {
|
||||
log.ZapLog.Error("SearchLog InsertMany error", log.E(err))
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func GetKeywordCountMapByTime(start time.Time, end time.Time, realm constant.RealmType) (map[string]int64, error) {
|
||||
pipeline := []M{
|
||||
{
|
||||
"$match": M{
|
||||
"createdAt": M{
|
||||
"$gte": start,
|
||||
"$lt": end,
|
||||
},
|
||||
"realm": realm,
|
||||
},
|
||||
},
|
||||
{
|
||||
"$sortByCount": "$keyword",
|
||||
},
|
||||
}
|
||||
list := []struct {
|
||||
Keyword string `bson:"_id"`
|
||||
Count int64 `bson:"count"`
|
||||
}{}
|
||||
if err := coll(nil).Aggregate(&list, pipeline); err != nil {
|
||||
return nil, fmt.Errorf("GetKeywordCountMapByTime err: %s", err.Error())
|
||||
}
|
||||
m := make(map[string]int64, len(list))
|
||||
for _, v := range list {
|
||||
m[v.Keyword] = v.Count
|
||||
}
|
||||
return m, nil
|
||||
}
|
||||
|
||||
// 根据时间段获取搜索日志
|
||||
func GetSearchLogByTimeRange(start time.Time, end time.Time) (data []SearchLog, err error) {
|
||||
var query = bson.M{
|
||||
"createdAt": bson.M{"$gte": start, "$lt": end},
|
||||
}
|
||||
if err = coll(nil).Find(&data, query); err != nil {
|
||||
log.Error("models SearchLog model GetSearchLogByTimeRange error", log.E(err))
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
func DeleteBeforeCreatedAt(t *db.MongoTool, tm time.Time) error {
|
||||
_, err := coll(t).DeleteMany(bson.M{"createdAt": bson.M{"$lt": tm}})
|
||||
return err
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
package searchlogmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/constant"
|
||||
"91porn-server/common/db"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
type (
|
||||
SearchLogDoc = SearchLog
|
||||
|
||||
ObjectID = primitive.ObjectID
|
||||
|
||||
M = bson.M
|
||||
)
|
||||
|
||||
// SearchLog 搜索记录
|
||||
type SearchLog struct {
|
||||
ID ObjectID `json:"id" bson:"_id,omitempty"`
|
||||
Realm constant.RealmType `json:"realm" bson:"realm"` //搜索区域 综合:complex 视频:video 用户:user 话题:tag 地点:site
|
||||
UID uint64 `json:"uid" bson:"uid"` //搜索人ID
|
||||
Keyword string `json:"keyword" bson:"keyword"` //搜索的关键字
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"` //搜索的时间
|
||||
}
|
||||
|
||||
// SearchLog 搜索记录
|
||||
type ESSearchLogSource struct {
|
||||
ID ObjectID `json:"id"`
|
||||
Realm constant.RealmType `json:"realm"` //搜索区域 综合:complex 视频:video 用户:user 话题:tag 地点:site
|
||||
UID uint64 `json:"uid"` //搜索人ID
|
||||
Keyword string `json:"keyword"` //搜索的关键字
|
||||
CreatedAt time.Time `json:"createdAt"` //搜索的时间
|
||||
}
|
||||
|
||||
// SearchCount 热搜视频统计最高多搜索次数的视频
|
||||
type SearchCount struct {
|
||||
KeyWord string `json:"keyWord" bson:"_id"` //关键字
|
||||
Count int `json:"count" bson:"count"` //关键字搜索次数
|
||||
}
|
||||
|
||||
// SearchResp SearchResp
|
||||
type SearchResp struct {
|
||||
TagName string `json:"id" bson:"_id,omitempty"`
|
||||
Count int `json:"count" bson:"count,omitempty"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
package synccdnmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.SyncCdnLog
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// initIndex 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: -1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
// InsertSyncCdnLog InsertSyncCdnLog
|
||||
func InsertSyncCdnLog(p SyncCdnLog) error {
|
||||
_, err := coll(nil).InsertOne(&p)
|
||||
return err
|
||||
}
|
||||
|
||||
// FindSyncRecord 查询
|
||||
func FindSyncRecord() (pr []SyncCdnLog, err error) {
|
||||
pr = []SyncCdnLog{}
|
||||
cond := []bson.M{
|
||||
bson.M{
|
||||
"$sort": bson.M{"createdAt": -1},
|
||||
},
|
||||
bson.M{
|
||||
"$limit": 1}}
|
||||
if err = coll(nil).Aggregate(&pr, cond); err != nil {
|
||||
log.Error("FindSyncRecord error", log.E(err))
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
@@ -0,0 +1,51 @@
|
||||
package synccdnmod
|
||||
|
||||
import (
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/stderr"
|
||||
"time"
|
||||
)
|
||||
|
||||
const (
|
||||
AccessKey = "4qQTNUrg9MloxqtykJbkf9BTeJ3liBo5fS7Qg6Nu"
|
||||
SecretKey = "axcamr082kQaJx87ebqkGHNPy-9EBeoTT2XbU6A2"
|
||||
//AccessKey = "MY_ACCESS_KEY"
|
||||
//SecretKey = "MY_SECRET_KEY"
|
||||
URl = "http://rs.qiniu.com/move/bmV3ZG9jczpmaW5kX21hbi50eHQ=/bmV3ZG9jczpmaW5kLm1hbi50eHQ="
|
||||
|
||||
Host string = "http://fusion.qiniuapi.com" //域名
|
||||
FetchUrl string = "/v2/tune/prefetch" //预取接口
|
||||
PreFetchUrl string = "/v2/tune/prefetch/list" //预期查询接口地址
|
||||
|
||||
)
|
||||
|
||||
// SyncHttpResp 返回结构体
|
||||
type SyncHttpResp struct {
|
||||
Code stderr.Code `json:"code"`
|
||||
Error string `json:"error"`
|
||||
RequestId string `json:"requestId"`
|
||||
InvalidUrls []string `json:"invalidUrls"`
|
||||
QuotaDay int `json:"quotaDay"`
|
||||
SurplusDay int `json:"surplusDay"`
|
||||
}
|
||||
|
||||
type SyncCdnLog struct {
|
||||
RequestIds []string `json:"requestIds" bson:"requestIds"`
|
||||
LastID string `json:"lastId" bson:"lastId"`
|
||||
Count int `json:"count" bson:"count"`
|
||||
FailCount int `json:"failCount" bson:"failCount"`
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
FailIDs []string `json:"failIDs" bson:"failIDs,omitempty"`
|
||||
}
|
||||
|
||||
// SyncReq 前端参数传递
|
||||
type SyncReq struct {
|
||||
Token string `json:"token" binding:"required"`
|
||||
Cdn string `json:"cdn"`
|
||||
FilePath string `json:"filePath"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
package userdailytasklogmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/models"
|
||||
"91porn-server/models/v/dailytaskmod"
|
||||
|
||||
"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"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.UserDailyTaskLog
|
||||
|
||||
// InitIndex 设置index
|
||||
func initIndex() {
|
||||
coll := coll(nil)
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}, {Key: "type", Value: 1}, {Key: "date", Value: 1}},
|
||||
Options: options.Index().SetUnique(true),
|
||||
},
|
||||
}
|
||||
if _, err := coll.CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
|
||||
type UserDailyTask struct {
|
||||
ID primitive.ObjectID `json:"_id" bson:"_id"`
|
||||
UID uint64 `json:"uid" bson:"uid"`
|
||||
Type int `json:"type" bson:"type"` // 0 每日广告点击; 1 每日任务
|
||||
Date string `json:"date" bson:"date"` // 日期. 格式 2006-01-02
|
||||
FinishCount uint64 `json:"finishCount" bson:"finishCount"` // 当日完成次数
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
UpdatedAt time.Time `json:"updatedAt" bson:"updatedAt"`
|
||||
}
|
||||
|
||||
func CompleteDailyTask(uid uint64, taskType int64, completeTime uint64) error {
|
||||
_, err := coll(nil).UpsertOne(bson.M{"uid": uid, "type": taskType, "date": time.Now().Format("2006-01-02")}, bson.M{"$inc": bson.M{"finishCount": completeTime}})
|
||||
return err
|
||||
}
|
||||
|
||||
func GetUserFinishCount(uid uint64, taskType dailytaskmod.DailyTaskTypeEnum) (uint64, error) {
|
||||
var udk UserDailyTask
|
||||
if err := coll(nil).FindOne(&udk, bson.M{"uid": uid, "type": taskType, "date": time.Now().Format("2006-01-02")}); err != nil {
|
||||
return 0, err
|
||||
}
|
||||
if udk.ID.IsZero() {
|
||||
return 0, nil
|
||||
}
|
||||
return udk.FinishCount, nil
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
package visitlogmod
|
||||
|
||||
import (
|
||||
"91porn-server/common/pageopt"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
type VisitLogSlice []VisitLog
|
||||
|
||||
func (v VisitLogSlice) ToUIDs() []uint64 {
|
||||
uids := make([]uint64, len(v))
|
||||
for i, l := range v {
|
||||
uids[i] = l.UID
|
||||
}
|
||||
return uids
|
||||
}
|
||||
|
||||
type Matcher = pageopt.Matcher
|
||||
|
||||
// CreatedAtGTEAndLTMatch
|
||||
type CreatedAtGTEAndLTMatch = pageopt.CreatedAtGTEAndLTMatch
|
||||
|
||||
func List(sort bson.D, skip, limit *int64, mats ...Matcher) (VisitLogSlice, error) {
|
||||
opt := (&options.FindOptions{})
|
||||
if len(sort) != 0 {
|
||||
opt.SetSort(sort)
|
||||
}
|
||||
if skip != nil {
|
||||
opt.SetSkip(*skip)
|
||||
}
|
||||
if limit != nil {
|
||||
opt.SetLimit(*limit)
|
||||
}
|
||||
filter := pageopt.MergeM(mats)
|
||||
list := VisitLogSlice{}
|
||||
return list, coll(nil).Find(&list, filter, opt)
|
||||
}
|
||||
|
||||
func Count(matchs ...pageopt.Matcher) (int64, error) {
|
||||
filter := pageopt.MergeM(matchs)
|
||||
return coll(nil).Count(filter)
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
package visitlogmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
// 以天为单位,统计用户的首次访问的日志
|
||||
type VisitLog struct {
|
||||
ID *primitive.ObjectID `json:"id" bson:"_id,omitempty"` //记录Id
|
||||
SumDate time.Time `json:"sumDate" bson:"sumDate"` //每日零点
|
||||
UID uint64 `json:"uid" bson:"uid"` //用户ID
|
||||
IP string `json:"ip" bson:"ip"` //IP
|
||||
SysType string `json:"sysType" bson:"sysType"` //操作系统类型 安卓 IOS
|
||||
Ver string `json:"ver" bson:"ver"` //APP版本号
|
||||
DevType string `json:"devType" bson:"devType"` //设备型号
|
||||
DevID string `json:"devID" bson:"devID"` //设备ID
|
||||
BuildID string `json:"buildID" bson:"buildID"` //app构建ID(包ID)
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"` //创建时间
|
||||
|
||||
IsDirect bool `json:"isDirect" bson:"isDirect"` // true:是直推用户
|
||||
DistrictCode string `json:"districtCode" bson:"districtCode"` // 渠道码
|
||||
RegisterTime time.Time `json:"registerTime" bson:"registerTime"` //用户注册时间
|
||||
IsDeduction bool `json:"isDeduction" bson:"isDeduction"` // true:CPA扣量用户
|
||||
}
|
||||
|
||||
type FilterDoc struct {
|
||||
SumDate time.Time `bson:"sumDate"` //每日零点
|
||||
UID uint64 `bson:"uid"` //用户ID
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
@@ -0,0 +1,187 @@
|
||||
package visitlogmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/common/pageopt"
|
||||
"91porn-server/models"
|
||||
"91porn-server/models/v/usermod"
|
||||
|
||||
"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"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.VisitLog
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// InitIndex 设置index
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{ //batch set indexes //value is the type 1 or -1
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "sumDate", Value: -1}, {Key: "uid", Value: 1}},
|
||||
},
|
||||
{
|
||||
Keys: bson.D{{Key: "createdAt", Value: -1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
func DataClean(deleteAt time.Time) (int64, error) {
|
||||
res, err := coll(nil).DeleteMany(bson.M{"createdAt": bson.M{"$lt": deleteAt}})
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
return res.DeletedCount, nil
|
||||
}
|
||||
|
||||
func UpsertUserVisit(l *VisitLog) (*mongo.UpdateResult, error) {
|
||||
l.CreatedAt = time.Now()
|
||||
b, _ := bson.Marshal(l)
|
||||
m := bson.M{}
|
||||
_ = bson.Unmarshal(b, &m)
|
||||
return coll(nil).UpsertOne(bson.M{"sumDate": l.SumDate, "uid": l.UID}, bson.M{"$setOnInsert": m})
|
||||
}
|
||||
|
||||
func UIDListByCreatedTime(start time.Time, end time.Time, mats ...Matcher) ([]uint64, error) {
|
||||
list := []struct {
|
||||
UID uint64 `bson:"uid"` //用户ID
|
||||
}{}
|
||||
mats = append(mats, (&CreatedAtGTEAndLTMatch{GTE: &start, LT: &end}).New())
|
||||
filter := pageopt.MergeM(mats)
|
||||
opt := (&options.FindOptions{}).SetProjection(bson.M{
|
||||
"uid": 1,
|
||||
})
|
||||
if err := coll(nil).Find(&list, filter, opt); err != nil {
|
||||
log.Error("UIDListByCreatedTime failed", log.Any("filter", filter), log.E(err))
|
||||
return nil, err
|
||||
}
|
||||
uids := make([]uint64, len(list))
|
||||
for i, v := range list {
|
||||
uids[i] = v.UID
|
||||
}
|
||||
return uids, nil
|
||||
}
|
||||
|
||||
func GetSumDateCountMap(uidList []uint64) (map[uint64]int64, error) {
|
||||
if len(uidList) == 0 {
|
||||
return make(map[uint64]int64), nil
|
||||
}
|
||||
pipeLine := []bson.M{
|
||||
{
|
||||
"$match": bson.M{
|
||||
"uid": bson.M{
|
||||
"$in": uidList,
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"$group": bson.M{
|
||||
"_id": "$uid",
|
||||
"count": bson.M{
|
||||
"$sum": 1,
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
list := make([]struct {
|
||||
UID uint64 `bson:"_id"`
|
||||
Count int64 `bson:"count"`
|
||||
}, 0, len(uidList))
|
||||
if err := coll(nil).Aggregate(&list, pipeLine); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
countMap := make(map[uint64]int64, len(list))
|
||||
for _, v := range list {
|
||||
countMap[v.UID] = v.Count
|
||||
}
|
||||
return countMap, nil
|
||||
}
|
||||
|
||||
// RetainUserListByTime 存留user
|
||||
func RetainUserListByTime(createUserStart, createUserEnd, visitStart, visitEnd time.Time, mats ...usermod.Matcher) ([]usermod.User, error) {
|
||||
visitFilter := (&CreatedAtGTEAndLTMatch{GTE: &visitStart, LT: &visitEnd}).New().Filter()
|
||||
visitList := make([]struct {
|
||||
UID uint64 `bson:"uid"`
|
||||
}, 0)
|
||||
visitOpt := (&options.FindOptions{}).SetProjection(bson.M{
|
||||
"uid": 1,
|
||||
})
|
||||
if err := coll(nil).Find(&visitList, visitFilter, visitOpt); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
visitUIDList := make([]uint64, len(visitList))
|
||||
for i, v := range visitList {
|
||||
visitUIDList[i] = v.UID
|
||||
}
|
||||
return usermod.UserListByCreateTimeAndUIDS(createUserStart, createUserEnd, visitUIDList, mats...)
|
||||
}
|
||||
|
||||
// RetainUIDListByTime 存留UID
|
||||
func RetainUIDListByTime(createStart, createEnd, visitStart, visitEnd time.Time, mats ...usermod.Matcher) ([]uint64, error) {
|
||||
visitList := make([]struct {
|
||||
UID uint64 `bson:"uid"`
|
||||
}, 0)
|
||||
visitFilter := (&CreatedAtGTEAndLTMatch{GTE: &visitStart, LT: &visitEnd}).New().Filter()
|
||||
visitOpt := (&options.FindOptions{}).SetProjection(bson.M{
|
||||
"uid": 1,
|
||||
})
|
||||
if err := coll(nil).Find(&visitList, visitFilter, visitOpt); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
visitUIDList := make([]uint64, len(visitList))
|
||||
for i, v := range visitList {
|
||||
visitUIDList[i] = v.UID
|
||||
}
|
||||
return usermod.UIDListByCreateTimeAndUIDS(createStart, createEnd, visitUIDList, mats...)
|
||||
}
|
||||
|
||||
// AccessSyncById 每日访问数据同步
|
||||
func AccessSyncById(Id string, size int64) (data []VisitLog, err error) {
|
||||
id, err := primitive.ObjectIDFromHex(Id)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
endTime := time.Now().Add(-time.Minute * 5)
|
||||
visitFilter := bson.M{"_id": bson.M{"$gt": id}, "createdAt": bson.M{"$lt": endTime}}
|
||||
visitOpt := (&options.FindOptions{}).SetLimit(size).SetSort(bson.M{"_id": 1})
|
||||
err = coll(nil).Find(&data, visitFilter, visitOpt)
|
||||
return
|
||||
}
|
||||
|
||||
func AccessSyncByTime(visitTime time.Time, size int64) (data []VisitLog, err error) {
|
||||
endTime := time.Now().Add(-time.Minute * 5)
|
||||
visitFilter := bson.M{"createdAt": bson.M{"$gt": visitTime, "$lt": endTime}}
|
||||
visitOpt := (&options.FindOptions{}).SetLimit(size).SetSort(bson.M{"createdAt": 1})
|
||||
err = coll(nil).Find(&data, visitFilter, visitOpt)
|
||||
return
|
||||
}
|
||||
|
||||
func GetInfoByCond(cond bson.M, opts ...*options.FindOneOptions) (VisitLog, error) {
|
||||
v := VisitLog{}
|
||||
if err := coll(nil).FindOne(&v, cond, opts...); err != nil {
|
||||
log.Error(fmt.Sprintf("[METHOD-%s]==> Model %s %s fail error:%+v:", "GetInfo", table, "FindOne", err),
|
||||
log.Any("cond", cond),
|
||||
)
|
||||
return v, err
|
||||
}
|
||||
return v, nil
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
package welfarelgmod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"91porn-server/common/db"
|
||||
"91porn-server/common/log"
|
||||
"91porn-server/models"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson"
|
||||
"go.mongodb.org/mongo-driver/mongo"
|
||||
"go.mongodb.org/mongo-driver/mongo/options"
|
||||
)
|
||||
|
||||
var mdb *db.MongoDB
|
||||
|
||||
const table = models.WelfareLog
|
||||
|
||||
func coll(t *db.MongoTool) *db.MongoTool {
|
||||
if t == nil {
|
||||
return mdb.Coll(table)
|
||||
}
|
||||
return t.Coll(table)
|
||||
}
|
||||
|
||||
// initIndex 初始化索引
|
||||
func initIndex() {
|
||||
many := []mongo.IndexModel{
|
||||
{
|
||||
Keys: bson.D{{Key: "uid", Value: -1}, {Key: "fareType", Value: -1}},
|
||||
Options: options.Index().SetUnique(true),
|
||||
}, {
|
||||
Keys: bson.D{{Key: "createdAt", Value: -1}},
|
||||
},
|
||||
}
|
||||
if _, err := coll(nil).CreateIndex(many); err != nil {
|
||||
panic(fmt.Sprintf("%s model set index err ==>[%+v]", table, err))
|
||||
}
|
||||
}
|
||||
|
||||
// InsertWelFareLog InsertWelFareLog
|
||||
func InsertWelFareLog(p WelfareLog) error {
|
||||
_, err := coll(nil).InsertOne(&p)
|
||||
return err
|
||||
}
|
||||
|
||||
// FindWelFareByUid 查询
|
||||
func FindWelFareByUid(uid uint64) (pr *WelfareLog, err error) {
|
||||
if err = coll(nil).FindOne(&pr, bson.M{"uid": uid}); err != nil {
|
||||
log.Error("FindWelFareByUid error", log.E(err))
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
package welfarelgmod
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
"91porn-server/common/db"
|
||||
|
||||
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||
)
|
||||
|
||||
type WelFareType int64
|
||||
|
||||
const (
|
||||
Fare_Vip WelFareType = iota //vip
|
||||
Fare_Coin //金币
|
||||
)
|
||||
|
||||
// 福利添加记录
|
||||
type WelfareLog struct {
|
||||
Id primitive.ObjectID `json:"id,omitempty" bson:"_id,omitempty"`
|
||||
Uid uint64 `json:"uid" bson:"uid"`
|
||||
FareType WelFareType `json:"fareType" bson:"fareType"`
|
||||
FareNum int64 `json:"fareNum" bson:"fareNum"`
|
||||
DailyDate time.Time `json:"dailyDate" bson:"dailyDate"`
|
||||
CreatedAt time.Time `json:"createdAt" bson:"createdAt"`
|
||||
}
|
||||
|
||||
func Init() {
|
||||
mdb = db.Init(table)
|
||||
initIndex()
|
||||
}
|
||||
Reference in New Issue
Block a user