Create & Init Project...

This commit is contained in:
2019-04-22 18:49:16 +08:00
commit fc4fa37393
25440 changed files with 4054998 additions and 0 deletions

View File

@@ -0,0 +1,84 @@
load(
"@io_bazel_rules_go//proto:def.bzl",
"go_proto_library",
)
package(default_visibility = ["//visibility:public"])
load(
"@io_bazel_rules_go//go:def.bzl",
"go_library",
)
proto_library(
name = "model_proto",
srcs = ["dm.proto"],
tags = ["automanaged"],
deps = ["@gogo_special_proto//github.com/gogo/protobuf/gogoproto"],
)
go_proto_library(
name = "model_go_proto",
compilers = ["@io_bazel_rules_go//proto:gogofast_proto"],
importpath = "go-common/app/interface/main/dm2/model",
proto = ":model_proto",
tags = ["automanaged"],
deps = [
"//library/time:go_default_library",
"@com_github_gogo_protobuf//gogoproto:go_default_library",
],
)
go_library(
name = "go_default_library",
srcs = [
"action.go",
"advance.go",
"advert.go",
"bangumi.go",
"dm.go",
"dm_seg.go",
"dm_special_location.go",
"filter.go",
"history.go",
"mask.go",
"member.go",
"params.go",
"rpc.go",
"subject.go",
"subtitle.go",
"thumbup.go",
"ugcpay.go",
"view.go",
"workflow.go",
],
embed = [":model_go_proto"],
importpath = "go-common/app/interface/main/dm2/model",
tags = ["automanaged"],
visibility = ["//visibility:public"],
deps = [
"//app/interface/main/dm2/model/oplog:go_default_library",
"//library/ecode:go_default_library",
"//library/time:go_default_library",
"//library/xstr:go_default_library",
"@com_github_gogo_protobuf//gogoproto:go_default_library",
"@com_github_gogo_protobuf//proto:go_default_library",
],
)
filegroup(
name = "package-srcs",
srcs = glob(["**"]),
tags = ["automanaged"],
visibility = ["//visibility:private"],
)
filegroup(
name = "all-srcs",
srcs = [
":package-srcs",
"//app/interface/main/dm2/model/oplog:all-srcs",
],
tags = ["automanaged"],
visibility = ["//visibility:public"],
)

View File

@@ -0,0 +1,44 @@
package model
import (
"encoding/json"
)
// Action actions sent to job
const (
ActionIdx = "idx"
ActionFlush = "flush"
ActAddDM = "dm_add" // 新增弹幕
ActFlushDMSeg = "dm_seg_flush" // 刷新分段弹幕缓存
)
// Action job msg.
type Action struct {
Action string `json:"action"`
Data json.RawMessage `json:"data"`
}
// JobParam job param.
type JobParam struct {
Type int32 `json:"type,omitempty"`
Pid int64 `json:"pid,omitempty"`
Oid int64 `json:"oid,omitempty"`
Cnt int64 `json:"cnt,omitempty"`
Num int64 `json:"num,omitempty"`
Duration int64 `json:"duration,omitempty"`
}
// Flush flush msg
type Flush struct {
Type int32 `json:"type,omitempty"`
Oid int64 `json:"oid,omitempty"`
Force bool `json:"force,omitempty"`
}
// ActionFlushDMSeg flush segment dm cache
type ActionFlushDMSeg struct {
Type int32 `json:"type"`
Oid int64 `json:"oid"`
Force bool `json:"force"`
Page *Page `json:"page"`
}

View File

@@ -0,0 +1,81 @@
package model
// all variable used in advance dm
const (
// mode
AdvSpeMode = "sp" // mode 7
AdvMode = "advance" // mode8 mode9
// type
AdvTypeRequest = "request"
AdvTypeAccept = "accept"
AdvTypeBuy = "buy"
AdvTypeDeny = "deny"
// coin
AdvSPCoin = 2
AdvCoin = 5
// reason
AdvSPCoinReason = "购买特殊弹幕"
AdvCoinReason = "购买高级弹幕"
AdvSPCoinCancelReason = "购买特殊弹幕被取消"
AdvCoinCancelReason = "购买高级弹幕被取消"
// confirm state
AdvStatConfirmDefault = 0
AdvStatConfirmAgree = 1
AdvStatConfirmRequest = 2
AdvStatConfirmDeny = 3
// 高级弹幕申请权限控制
AdvPermitAll = int8(0) // 任何人
AdvPermitFollower = int8(1) // 仅限粉丝
AdvPermitAttention = int8(2) // 仅限相互关注
AdvPermitForbid = int8(3) // 始终拒绝
)
// BuyAdv user buy adv
type BuyAdv struct {
CID int64
Owner int64
Mid int64
Type string
Timestamp int64
Mode string
Refund int
}
// ArgAdvBuy buy adv data
type ArgAdvBuy struct {
Mid int64
Owner int64
Type string
Reason string
Cid int64
Coin float64
Mode string
Cookie string
AccessKey string
Refund int
IsCoin bool
}
// AdvState state
type AdvState struct {
Coins int `json:"coins"`
Confirm int `json:"confirm"`
Accept bool `json:"accept"`
HasBuy bool `json:"hasBuy"`
}
// Advance dm_advancecomment
type Advance struct {
ID int64 `json:"id"`
Owner int64 `json:"owner"`
Cid int64 `json:"cid"`
Aid int64 `json:"aid"`
Type string `json:"type"`
Mode string `json:"mode"`
Mid int64 `json:"mid"`
Timestamp int64 `json:"timestamp"`
Refund int8 `json:"refund"`
Uname string `json:"uname"`
Title string `json:"title"`
Cover string `json:"cover"`
}

View File

@@ -0,0 +1,94 @@
package model
import (
"encoding/json"
"fmt"
)
// resource id defined by advert
const (
adRscIDIphone = 2630
adRscIDAndrod = 2631
adRscIDIphoneIcon = 2642
adRscIDAndroidIcon = 2643
)
// Resource get resource by mobi_app.
func Resource(mobiApp string) (rsc string) {
if mobiApp == "iphone" || mobiApp == "ipad" || mobiApp == "iphone_i" {
rsc = fmt.Sprintf("%d,%d", adRscIDIphone, adRscIDIphoneIcon)
} else {
rsc = fmt.Sprintf("%d,%d", adRscIDAndrod, adRscIDAndroidIcon)
}
return
}
// ADReq advert request params
type ADReq struct {
Aid int64 `json:"aid"`
Oid int64 `json:"oid"`
Mid int64 `json:"mid"`
Build int64 `json:"build"`
Buvid string `json:"buvid"`
ClientIP string `json:"ip"`
MobiApp string `json:"mobi_app"`
ADExtra string `json:"ad_extra"`
}
// ADResp advert response
type ADResp struct {
Icon *ADInfo `json:"icon,omitempty"`
ADs []*ADInfo `json:"ads_info,omitempty"`
}
// AD advert struct
type AD struct {
RequestID string `json:"request_id,omitempty"`
ADsInfo map[int64]map[int64]*ADInfo `json:"ads_info,omitempty"` // resource_id --> source_id --> adinfo
}
// ADInfo advert info.
type ADInfo struct {
// filed response from advert api
Index int `json:"index,omitempty"`
IsAd bool `json:"is_ad,omitempty"`
CmMark int `json:"cm_mark,omitempty"`
CardIndex int `json:"card_index,omitempty"`
ADInfo json.RawMessage `json:"ad_info,omitempty"`
// filed used in app
RequestID string `json:"request_id,omitempty"`
ResourceID int64 `json:"resource_id,omitempty"`
SourceID int64 `json:"source_id,omitempty"`
ClientIP string `json:"client_ip,omitempty"`
IsADLoc bool `json:"is_ad_loc,omitempty"`
}
// Convert convert AD to ADResp.
func (a *AD) Convert(clientIP string) (res *ADResp) {
res = new(ADResp)
for rscID, adInfoMap := range a.ADsInfo {
for srcID, adInfo := range adInfoMap {
v := new(ADInfo)
v.RequestID = a.RequestID
v.ResourceID = rscID
v.SourceID = srcID
v.ClientIP = clientIP
v.IsADLoc = true // 该字段服务端代码写死为true
if adInfo != nil {
v.Index = adInfo.Index
v.IsAd = adInfo.IsAd
v.CmMark = adInfo.CmMark
v.CardIndex = adInfo.CardIndex
}
if len(adInfo.ADInfo) > 0 {
v.ADInfo = adInfo.ADInfo
}
if v.ResourceID == adRscIDIphoneIcon || v.ResourceID == adRscIDAndroidIcon { // icon resouce id
res.Icon = v
continue
}
res.ADs = append(res.ADs, v)
}
}
return
}

View File

@@ -0,0 +1,24 @@
package model
import "encoding/json"
// Season 番剧季度对象
type Season struct {
AllowDownload string `json:"allow_download,omitempty"`
SeasonID string `json:"season_id"`
IsJump int `json:"is_jump"`
EpisodeStatus int `json:"episode_status"`
Title string `json:"title"`
Cover string `json:"cover"`
IsFinish string `json:"is_finish"`
IsStarted int `json:"is_started"`
NewestEpID string `json:"newest_ep_id"`
NewestEpIndex string `json:"newest_ep_index"`
TotalCount string `json:"total_count"`
Weekday string `json:"weekday"`
Evaluate string `json:"evaluate"`
Bp json.RawMessage `json:"rank,omitempty"`
UserSeason *struct {
Attention string `json:"attention"`
} `json:"user_season,omitempty"`
}

View File

@@ -0,0 +1,298 @@
package model
import (
"fmt"
"hash/crc32"
"strconv"
"go-common/library/time"
"go-common/library/xstr"
)
var (
bAmp = []byte(`&`)
bGt = []byte(`>`)
bLt = []byte(`<`)
bSp = []byte(` `)
// LimitPerMin 每个rank权限允许的发送速度
LimitPerMin = map[int32]int64{
0: 10,
10000: 30,
15000: 30,
20000: 300,
25000: 60,
30000: 300,
32000: 300,
}
)
// All const variable used in dm2
const (
// <d p="播放时间弹幕模式字体大小颜色发送时间弹幕池用户hash弹幕id">弹幕内容</d>
_xmlFmt = `<d p="%.5f,%d,%d,%d,%d,%d,%s,%d">%s</d>`
// <d p="播放时间弹幕模式字体大小颜色发送时间弹幕池用户hash弹幕id用户id">弹幕内容</d>
_rnameFmt = `<d p="%.5f,%d,%d,%d,%d,%d,%s,%d,%d">%s</d>`
AttrNo = int32(0) // 属性位为0
AttrYes = int32(1) // 属性位为1
AttrProtect = uint(0) // 保护弹幕
StateNormal = int32(0) // 普通状态
StateDelete = int32(1) // 删除状态
StateHide = int32(2) // 隐藏状态
StateBlock = int32(3) // 屏蔽状态
StateFilter = int32(4) // 过滤状态
StateMonitorBefore = int32(5) // 先审后发
StateMonitorAfter = int32(6) // 先发后审
StateSystemFilter = int32(7) // 敏感词过滤
StateReportDelete = int32(8) // 举报删除
StateAdminDelete = int32(9) // 弹幕管理删除
StateUserDelete = int32(10) // 用户删除
StateScriptDelete = int32(11) // 举报脚本删除
StateTaskDel = int32(12) //弹幕任务删除
StateAiDelete = int32(13) // ai删除
PoolNormal = int32(0) // 普通弹幕池
PoolSubtitle = int32(1) // 字幕弹幕池
PoolSpecial = int32(2) // 特殊弹幕池
PlatUnknow = int32(0)
PlatWeb = int32(1)
PlatAndroid = int32(2)
PlatIPhone = int32(3)
PlatWpM = int32(4) // wp mobile
PlatIPad = int32(5)
PlatPadHd = int32(6) // ipad hd
PlatWpPc = int32(7) // win10
MaxLenDefMsg = 100
MaxLen7Msg = 300
// 弹幕模式
ModeRolling = int32(1)
ModeBottom = int32(4)
ModeTop = int32(5)
ModeReverse = int32(6)
ModeSpecial = int32(7)
ModeCode = int32(8)
ModeBAS = int32(9)
SpamBlack = 52001
SpamOverflow = 52002
SpamRestrict = 52005
)
// AdvanceCmt struct
type AdvanceCmt struct {
ID int64
Owner int64
Oid int64
Type string // request:申请中buy:已购买accept:已通过deny:拒绝
Mode string // 枚举类型sp:高级弹幕advance:pool2特殊弹幕
Timestamp int64
Mid int64
Refund int
}
// DailyLimiter daily limiter
type DailyLimiter struct {
Date string
Count int64
}
// Limiter retrun
type Limiter struct {
Allowance int64
Timestamp int64
}
// AttrVal return val of index'attr
func (d *DM) AttrVal(bit uint) int32 {
return (d.Attr >> bit) & int32(1)
}
// AttrSet set val of index'attr
func (d *DM) AttrSet(v int32, bit uint) {
d.Attr = d.Attr&(^(1 << bit)) | (v << bit)
}
// DMSlice dm slice
type DMSlice []*DM
func (d DMSlice) Len() int { return len(d) }
func (d DMSlice) Swap(i, j int) { d[i], d[j] = d[j], d[i] }
func (d DMSlice) Less(i, j int) bool { return d[i].ID < d[j].ID }
// DMSlice2 sort dm slice by progress
type DMSlice2 []*DM
func (d DMSlice2) Len() int { return len(d) }
func (d DMSlice2) Swap(i, j int) { d[i], d[j] = d[j], d[i] }
func (d DMSlice2) Less(i, j int) bool { return d[i].Progress < d[j].Progress }
// JudgeDMList dm list of judge
type JudgeDMList struct {
List []*JDM `json:"list"`
Index []int64 `json:"index"`
}
// JDM judge dm
type JDM struct {
ID int64 `json:"id"`
Msg string `json:"msg"`
Mid int64 `json:"mid"`
Progress string `json:"progress"`
CTime time.Time `json:"ctime"`
}
// FilterData filter-service data
type FilterData struct {
Level int64 `json:"level"`
Limit int64 `json:"limit"`
Msg string `json:"msg"`
TypeID []int64 `json:"typeid"`
Hit []string `json:"hit"`
}
// ToXMLSpecialSeg .
func (d *DM) ToXMLSpecialSeg(realname bool) (s string) {
if d.Content == nil || d.Pool != PoolSpecial {
return
}
msg := d.Content.Msg
if d.ContentSpe != nil {
msg = d.ContentSpe.Msg
}
if len(msg) == 0 {
return
}
s = fmt.Sprintf(`<d id="%d">%s</d>`, d.ID, xmlReplace([]byte(msg)))
return
}
// ToXMLSeg convert dm struct to xml.
func (d *DM) ToXMLSeg(realname bool) (s string) {
if d.Content == nil {
return
}
msg := d.Content.Msg
if d.ContentSpe != nil {
msg = d.ContentSpe.Msg
}
if len(msg) == 0 {
return
}
if d.Pool == PoolSpecial {
msg = ""
}
if realname {
// <d p="弹幕ID,弹幕属性,播放时间,弹幕模式,字体大小,颜色,发送时间,弹幕池,用户hash id,用户mid">弹幕内容</d>
s = fmt.Sprintf(_xmlSegRealnameFmt, d.ID, d.Attr, d.Progress, d.Content.Mode, d.Content.FontSize, d.Content.Color, d.Ctime, d.Pool, Hash(d.Mid, uint32(d.Content.IP)), d.Mid, xmlReplace([]byte(msg)))
} else {
// <d p="弹幕ID,弹幕属性,播放时间,弹幕模式,字体大小,颜色,发送时间,弹幕池,用户id">弹幕内容</d>
s = fmt.Sprintf(_xmlSegFmt, d.ID, d.Attr, d.Progress, d.Content.Mode, d.Content.FontSize, d.Content.Color, d.Ctime, d.Pool, Hash(d.Mid, uint32(d.Content.IP)), xmlReplace([]byte(msg)))
}
return
}
// ToXML convert dm struct to xml.
func (d *DM) ToXML(realname bool) (s string) {
if d.Content == nil {
return
}
msg := d.Content.Msg
if d.ContentSpe != nil {
msg = d.ContentSpe.Msg
}
if len(msg) == 0 {
return
}
if realname {
// <d p="播放时间弹幕模式字体大小颜色发送时间弹幕池用户hash弹幕id用户id">弹幕内容</d>
s = fmt.Sprintf(_rnameFmt, float64(d.Progress)/1000.0, d.Content.Mode, d.Content.FontSize, d.Content.Color, d.Ctime, d.Pool, Hash(d.Mid, uint32(d.Content.IP)), d.ID, d.Mid, xmlReplace([]byte(msg)))
} else {
// <d p="播放时间弹幕模式字体大小颜色发送时间弹幕池用户hash弹幕id">弹幕内容</d>
s = fmt.Sprintf(_xmlFmt, float64(d.Progress)/1000.0, d.Content.Mode, d.Content.FontSize, d.Content.Color, d.Ctime, d.Pool, Hash(d.Mid, uint32(d.Content.IP)), d.ID, xmlReplace([]byte(msg)))
}
return
}
// xmlReplace replace special char in xml.
func xmlReplace(bi []byte) (bo []byte) {
for _, b := range bi {
if b == 0 {
continue
} else if b == '&' {
bo = append(bo, bAmp...)
continue
} else if b == '>' {
bo = append(bo, bGt...)
continue
} else if b == '<' {
bo = append(bo, bLt...)
continue
} else if (b >= 0x01 && b <= 0x08) || (b >= 0x0b && b <= 0x0c) || (b >= 0x0e && b <= 0x1f) || (b == 0x7f) {
// 替换掉控制字符,保留空格、回车、制表符
bo = append(bo, bSp...)
} else {
bo = append(bo, b)
}
}
return
}
// Hash return mid hash string.
func Hash(mid int64, ip uint32) string {
var s uint32
if mid != 0 {
s = crc32.ChecksumIEEE([]byte(strconv.FormatInt(mid, 10)))
return strconv.FormatInt(int64(s), 16)
}
s = crc32.ChecksumIEEE([]byte(strconv.FormatInt(int64(ip), 10)))
return "D" + strconv.FormatInt(int64(s), 16)
}
// IsDMVisible dm can visible
func IsDMVisible(state int32) bool {
if state == StateNormal || state == StateMonitorAfter {
return true
}
return false
}
// IsDMEditAble dm can edit
func IsDMEditAble(state int32) bool {
if state == StateNormal || state == StateHide || state == StateMonitorAfter {
return true
}
return false
}
// AttrNtoA convert uint to string format,eg:5-->101-->1,3.
func (d *DM) AttrNtoA() string {
if d.Attr == 0 {
return ""
}
var bits []int64
for k, v := range strconv.FormatInt(int64(d.Attr), 2) {
if v == 49 {
bits = append(bits, int64(k+1))
}
}
return xstr.JoinInts(bits)
}
// DMAttrNtoA convert uint to string format,eg:5-->101-->1,3.
func DMAttrNtoA(attr int32) string {
if attr == 0 {
return ""
}
var bits []int64
for k, v := range strconv.FormatInt(int64(attr), 2) {
if v == 49 {
bits = append(bits, int64(k+1))
}
}
return xstr.JoinInts(bits)
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,53 @@
syntax = "proto3";
package model;
import "github.com/gogo/protobuf/gogoproto/gogo.proto";
option (gogoproto.goproto_enum_prefix_all) = false;
option (gogoproto.goproto_getters_all) = false;
option (gogoproto.unmarshaler_all) = true;
option (gogoproto.marshaler_all) = true;
option (gogoproto.sizer_all) = true;
message DM {
int64 ID = 1 [(gogoproto.jsontag) = "id"];
int32 Type = 2 [(gogoproto.jsontag) = "type"];
int64 Oid = 3 [(gogoproto.jsontag) = "oid"];
int64 Mid = 4 [(gogoproto.jsontag) = "mid"];
int32 Progress = 5 [(gogoproto.jsontag) = "progress"];
int32 Pool = 6 [(gogoproto.jsontag) = "pool"];
int32 Attr = 7 [(gogoproto.jsontag) = "attr"];
int32 State = 8 [(gogoproto.jsontag) = "state"];
int64 Ctime = 9 [(gogoproto.jsontag) = "ctime", (gogoproto.casttype) = "go-common/library/time.Time"];
int64 Mtime = 10 [(gogoproto.jsontag) = "mtime", (gogoproto.casttype) = "go-common/library/time.Time"];
Content Content = 11 [(gogoproto.jsontag) = "content,omitempty"];
ContentSpecial ContentSpe = 12 [(gogoproto.jsontag) = "content_special,omitempty"];
}
message Content {
int64 ID = 1 [(gogoproto.jsontag) = "id"];
int32 FontSize = 2 [(gogoproto.jsontag) = "fontsize"];
int64 Color = 3 [(gogoproto.jsontag) = "color"];
int32 Mode = 4 [(gogoproto.jsontag) = "mode"];
int64 IP = 5 [(gogoproto.jsontag) = "ip"];
int32 Plat = 6 [(gogoproto.jsontag) = "plat"];
string Msg = 7 [(gogoproto.jsontag) = "msg"];
int64 Ctime = 8 [(gogoproto.jsontag) = "ctime", (gogoproto.casttype) = "go-common/library/time.Time"];
int64 Mtime = 9 [(gogoproto.jsontag) = "mtime", (gogoproto.casttype) = "go-common/library/time.Time"];
}
message ContentSpecial {
int64 ID = 1 [(gogoproto.jsontag) = "id"];
string Msg = 2 [(gogoproto.jsontag) = "msg"];
int64 Ctime = 3 [(gogoproto.jsontag) = "ctime", (gogoproto.casttype) = "go-common/library/time.Time"];
int64 Mtime = 4 [(gogoproto.jsontag) = "mtime", (gogoproto.casttype) = "go-common/library/time.Time"];
}
message Elem {
string Attribute = 1 [(gogoproto.jsontag) = "attribute,omitempty"];
string Content = 2 [(gogoproto.jsontag) = "content,omitempty"];
}
message DMSeg {
repeated Elem Elems = 1 [(gogoproto.jsontag) = "dms"];
repeated string SpecialURL = 2 [(gogoproto.jsontag) = "special_url,omitempty"];
}

View File

@@ -0,0 +1,154 @@
package model
import (
"bytes"
"compress/gzip"
"encoding/binary"
"encoding/json"
"fmt"
"io/ioutil"
)
var (
_defaultSeg = &Segment{Start: 0, End: defaultVideoEnd, Cnt: 1, Num: 1, Duration: 0}
// DefaultFlag default dm flag if bigdata downgrade.
DefaultFlag = []byte(`{"rec_flag":2,"rec_text":"开启后,全站视频将按等级等优化弹幕","rec_switch":1,"dmflags":[]}`)
)
const (
// segmentLength 分段长度,6分钟
segmentLength = 60 * 6 * 1000
// defaultVideoEnd 当视频时长不存在或者为0时的默认视频结尾时间点
defaultVideoEnd = int64(10 * 60 * 60 * 1000)
// DefaultVideoEnd 当视频时长不存在或者为0时的默认视频结尾时间点
DefaultVideoEnd = int64(3 * 60 * 60 * 1000)
// DefaultPageSize 默认分段长度
DefaultPageSize = 60 * 6 * 1000
// NotFound nothing found flag
NotFound = int64(-1)
// DefaultPage default page info
// <d p="弹幕ID,弹幕属性,播放时间,弹幕模式,字体大小,颜色,发送时间,弹幕池,用户hash id">弹幕内容</d>
_xmlSegFmt = `<d p="%d,%d,%d,%d,%d,%d,%d,%d,%s">%s</d>`
// <d p="弹幕ID,弹幕属性,播放时间,弹幕模式,字体大小,颜色,发送时间,弹幕池,用户hash id,用户mid">弹幕内容</d>
_xmlSegRealnameFmt = `<d p="%d,%d,%d,%d,%d,%d,%d,%d,%s,%d">%s</d>`
_xmlSegHeader = `<?xml version="1.0" encoding="UTF-8"?><i><oid>%d</oid><ps>%d</ps><pe>%d</pe><pc>%d</pc><pn>%d</pn><state>%d</state><real_name>%d</real_name>`
)
// JudgeSlice sort for dm judgement
type JudgeSlice []*DM
func (d JudgeSlice) Len() int { return len(d) }
func (d JudgeSlice) Swap(i, j int) { d[i], d[j] = d[j], d[i] }
func (d JudgeSlice) Less(i, j int) bool { return d[i].Progress < d[j].Progress }
// Segment dm segment struct
type Segment struct {
Start int64 `json:"ps"` // 分段起始时间
End int64 `json:"pe"` // 分段结束时间
Cnt int64 `json:"cnt"` // 总分段数
Num int64 `json:"num"` // 当前第几段
Duration int64 `json:"duration"` // 视频总时长
}
// DMSegResp segment dm list response
type DMSegResp struct {
Dms []*Elem `json:"dms"`
Flag json.RawMessage `json:"flags,omitempty"`
}
// Page page info.
type Page struct {
Num int64 `json:"num"`
Size int64 `json:"size"`
Total int64 `json:"total"`
}
// ToXMLHeader convert segment to xml header format.
func (s *Segment) ToXMLHeader(oid int64, state, realname int32) string {
return fmt.Sprintf(_xmlSegHeader, oid, s.Start, s.End, s.Cnt, s.Num, state, realname)
}
// SegmentInfo get segment info by start time and video duration.
func SegmentInfo(ps, duration int64) (s *Segment) {
var cnt, num, pe int64
if duration == 0 {
s = _defaultSeg
return
}
cnt = duration / segmentLength
if duration%segmentLength > 0 {
cnt++
}
for i := int64(0); i < cnt; i++ {
if ps >= i*segmentLength && ps < (i+1)*segmentLength {
ps = i * segmentLength
pe = (i + 1) * segmentLength
num = i + 1
}
}
if pe > duration {
pe = duration
}
s = &Segment{
Start: ps,
End: pe,
Cnt: cnt,
Num: num,
Duration: duration,
}
return
}
// Encode dm ecode.
func Encode(flag, xml []byte) (res []byte) {
var (
fl = uint32(len(flag))
xl = uint32(len(xml))
)
res = make([]byte, 4+fl+xl)
binary.BigEndian.PutUint32(res[0:4], fl)
copy(res[4:], flag)
copy(res[4+fl:], xml)
return
}
// Decode decode dm proto.
func Decode(buf []byte) (flag, xml []byte, err error) {
var (
zr *gzip.Reader
)
fl := binary.BigEndian.Uint32(buf[0:4])
flag = buf[4 : 4+fl]
if zr, err = gzip.NewReader(bytes.NewBuffer(buf[4+fl:])); err != nil {
return
}
zr.Close()
if xml, err = ioutil.ReadAll(zr); err != nil {
return
}
return
}
// ToElem convert dm struct to element.
func (d *DM) ToElem() (e *Elem) {
if d.Content == nil {
return
}
msg := d.Content.Msg
if d.ContentSpe != nil {
msg = d.ContentSpe.Msg
}
if len(msg) == 0 {
return
}
if d.Pool == PoolSpecial {
msg = ""
}
// "弹幕ID,弹幕属性,播放时间,弹幕模式,字体大小,颜色,发送时间,弹幕池,用户hash id
e = &Elem{
Attribute: fmt.Sprintf(`"%d,%d,%d,%d,%d,%d,%d,%d,%s"`, d.ID, d.Attr, d.Progress, d.Content.Mode, d.Content.FontSize, d.Content.Color, d.Ctime, d.Pool, Hash(d.Mid, uint32(d.Content.IP))),
Content: msg,
}
return
}

View File

@@ -0,0 +1,23 @@
package model
import (
"strings"
)
// DmSpecial special dm bfs location
type DmSpecial struct {
ID int64
Type int32
Oid int64
Locations string
}
// Split .
func (d *DmSpecial) Split() []string {
return strings.Split(d.Locations, ",")
}
// Join .
func (d *DmSpecial) Join(s []string) {
d.Locations = strings.Join(s, ",")
}

View File

@@ -0,0 +1,64 @@
package model
import (
"go-common/library/time"
)
// all const variable used in dm filter
const (
FilterUnActive int8 = 0
FilterActive int8 = 1
FilterTypeText int8 = 0 // 文本类型
FilterTypeRegex int8 = 1 // 正则类型
FilterTypeID int8 = 2 // 用户ID类型
FilterTypeBottom int8 = 4
FilterTypeTop int8 = 5
FilterTypeRev int8 = 6
FilterLenText = 50 // 文本类型最大字符长度
FilterLenRegex = 200 // 正则类型最大字符长度
FilterMaxUserText = 1000 // 用户关键字最大条数
FilterMaxUserReg = 100 // 用户正则最大条数
FilterMaxUserID = 1000 // 用户黑名单最大条数
FilterMaxUpText = 500 // up主关键字最大条数
FilterMaxUpReg = 100 // up主正则最大条数
FilterMaxUpID = 1000 // up主黑名单最大条数
FilterNotExist = -1000000
FilterContent = "10000,20000,25000,30000"
)
// UserFilter define a new struct, consistent with table "dm_filter_user_%"
type UserFilter struct {
ID int64 `json:"id"`
Mid int64 `json:"mid"`
Type int8 `json:"type"`
Filter string `json:"filter"`
Comment string `json:"comment"`
Ctime time.Time `json:"-"`
Mtime time.Time `json:"-"`
}
// UpFilter filter of upper
type UpFilter struct {
ID int64 `json:"id"`
Mid int64 `json:"mid"`
Type int8 `json:"type"`
Filter string `json:"filter"`
Active int8 `json:"active"`
Comment string `json:"comment"`
Ctime time.Time `json:"ctime"`
Mtime time.Time `json:"mtime"`
}
// GlobalFilter define a new struct, consistent with table "dm_sys_filter"
type GlobalFilter struct {
ID int64 `json:"id"`
Type int8 `json:"type"`
Filter string `json:"filter"`
Ctime time.Time `json:"-"`
Mtime time.Time `json:"-"`
}

View File

@@ -0,0 +1,24 @@
package model
// SearchPage page struct from search
type SearchPage struct {
Num int64 `json:"num"`
Size int64 `json:"size"`
Total int64 `json:"total"`
}
// SearchHistoryResult history dm from search
type SearchHistoryResult struct {
Page *SearchPage `json:"page"`
Result []*struct {
ID int64 `json:"id"`
} `json:"result"`
}
// SearchHistoryIdxResult history date index
type SearchHistoryIdxResult struct {
Page *SearchPage `json:"page"`
Result []*struct {
Date string `json:"date"`
} `json:"result"`
}

View File

@@ -0,0 +1,25 @@
package model
// all const variable used in mask
const (
MaskPlatWeb int8 = 0
MaskPlatMbl int8 = 1
)
// MaskLists mask lists
type MaskLists struct {
Onoff int64 `json:"onoff"`
Cid int64 `json:"cid,omitempty"`
Fps int64 `json:"fps,omitempty"`
Time int64 `json:"time,omitempty"`
Lists []string `json:"list,omitempty"`
}
// Mask mask info
type Mask struct {
Cid int64 `json:"cid,omitempty"`
Plat int8 `json:"plat,omitempty"`
FPS int32 `json:"fps,omitempty"`
Time int64 `json:"time,omitempty"`
MaskURL string `json:"mask_url,omitempty"`
}

View File

@@ -0,0 +1,137 @@
package model
import (
"go-common/library/time"
)
//CondIntNil cond int nil
const CondIntNil = -10516
// DmRecentResponse .
type DmRecentResponse struct {
Page *Page `json:"page"`
Data []*DMMember `json:"result"`
}
// Recent recent dm
type Recent struct {
ID int64 `json:"id"`
Type int32 `json:"type"`
Aid int64 `json:"pid"`
Oid int64 `json:"oid"`
Mid int64 `json:"mid"`
Pool int32 `json:"pool"`
Attr int32 `json:"attr"`
Progress int32 `json:"progress"`
Mode int32 `json:"mode"`
Msg string `json:"msg"`
State int32 `json:"state"`
FontSize int32 `json:"fontsize"`
Color int32 `json:"color"`
Ctime string `json:"ctime"`
}
// DMMember dm struct used in member
type DMMember struct {
ID int64 `json:"id"`
IDStr string `json:"id_str"`
Type int32 `json:"type"`
Aid int64 `json:"aid"`
Oid int64 `json:"oid"`
Mid int64 `json:"mid"`
MidHash string `json:"mid_hash"`
Pool int32 `json:"pool"`
Attrs string `json:"attrs"`
Progress int32 `json:"progress"`
Mode int32 `json:"mode"`
Msg string `json:"msg"`
State int32 `json:"state"`
FontSize int32 `json:"fontsize"`
Color string `json:"color"`
Ctime time.Time `json:"ctime"`
Uname string `json:"uname"`
Title string `json:"title"`
}
// SearchDMParams dm search params
type SearchDMParams struct {
Type int32
Oid int64
Keyword string
Mids string
Mode string
Pool string
Attrs string
ProgressFrom int64
ProgressTo int64
CtimeFrom string
CtimeTo string
Pn int64
Ps int64
Sort string
Order string
State string
}
// SearchRecentDMParam .
type SearchRecentDMParam struct {
Type int32
UpMid int64
States []int32
Ps int
Pn int
Sort string
Field string
}
// SearchRecentDMResult .
type SearchRecentDMResult struct {
Page *Page `json:"page"`
Result []*Recent `json:"result"`
}
// SearchDMData dm meta data from search
type SearchDMData struct {
Result []*struct {
ID int64 `json:"id"`
} `json:"result"`
Page *SearchPage
}
//SearchDMResult dm list
type SearchDMResult struct {
Page struct {
Num int64 `json:"num"`
Size int64 `json:"size"`
Total int64 `json:"total"`
} `json:"page"`
Result []*DMMember `json:"result"`
}
// UptSearchDMState update search dm state
type UptSearchDMState struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
Type int32 `json:"type"`
State int32 `json:"state"`
Mtime string `json:"mtime"`
}
// UptSearchDMPool update search dm pool
type UptSearchDMPool struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
Type int32 `json:"type"`
Pool int32 `json:"pool"`
Mtime string `json:"mtime"`
}
// UptSearchDMAttr update search dm attr
type UptSearchDMAttr struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
Type int32 `json:"type"`
Attr int32 `json:"attr"`
Mtime string `json:"mtime"`
AttrFormat []int64 `json:"attr_format"`
}

View File

@@ -0,0 +1,29 @@
package(default_visibility = ["//visibility:public"])
load(
"@io_bazel_rules_go//go:def.bzl",
"go_library",
)
go_library(
name = "go_default_library",
srcs = ["oplog.go"],
importpath = "go-common/app/interface/main/dm2/model/oplog",
tags = ["automanaged"],
visibility = ["//visibility:public"],
deps = ["//library/log:go_default_library"],
)
filegroup(
name = "package-srcs",
srcs = glob(["**"]),
tags = ["automanaged"],
visibility = ["//visibility:private"],
)
filegroup(
name = "all-srcs",
srcs = [":package-srcs"],
tags = ["automanaged"],
visibility = ["//visibility:public"],
)

View File

@@ -0,0 +1,79 @@
package oplog
import (
"go-common/library/log"
)
// Infoc operation log for administrator
type Infoc struct {
Oid int64 `json:"oid"`
Type int `json:"type"`
DMIds []int64 `json:"dmids"`
Subject string `json:"subject"`
OriginVal string `json:"origin_val"`
CurrentVal string `json:"current_val"`
OperationTime string `json:"optime"`
OperatorType OperatorType `json:"operator_type"`
Operator int64 `json:"operator"`
Source Source `json:"source"`
Remark string `json:"remark"`
}
// Source enum integer value
type Source int
// Source enum definition list
const (
_ Source = iota
SourceManager
SourceUp
SourcePlayer
)
// String returns the Source enmu description
func (source Source) String() string {
var text string
switch source {
case SourceManager:
text = "运营后台"
case SourceUp:
text = "创作中心"
case SourcePlayer:
text = "播放器"
default:
log.Warn("String() Unknow Source, warn(%v)", int(source))
text = "未知来源"
}
return text
}
// OperatorType enum integer value
type OperatorType int
// OperatorType enum definition list
const (
_ OperatorType = iota
OperatorAdmin
OperatorMember
OperatorUp
OperatorSystem
)
// String returns the Source enmu description
func (opType OperatorType) String() string {
var text string
switch opType {
case OperatorAdmin:
text = "管理员"
case OperatorMember:
text = "用户"
case OperatorUp:
text = "UP主"
case OperatorSystem:
text = "系统"
default:
log.Warn("String() Unknow Source, warn(%v)", int(opType))
text = "未知来源"
}
return text
}

View File

@@ -0,0 +1,12 @@
package model
// SubtitleReportAddParam .
type SubtitleReportAddParam struct {
Oid int64 `form:"oid" validate:"required"`
SubtitleID int64 `form:"subtitle_id" validate:"required"`
Tid int64 `form:"tid" validate:"required"`
MetaData string `form:"metadata" validate:"lt=300"`
From float64 `form:"from"`
To float64 `form:"to" validate:"required"`
Content string `form:"content" validate:"required"`
}

View File

@@ -0,0 +1,163 @@
package model
import "go-common/app/interface/main/dm2/model/oplog"
// ArgOids arguments passed by rpc client
type ArgOids struct {
Type int32
Plat int8
Oids []int64
RealIP string
}
// ArgEditDMState arguments passed by rpc client
type ArgEditDMState struct {
Type int32
Oid int64
Mid int64
State int32
Dmids []int64
Source oplog.Source
OperatorType oplog.OperatorType
}
// ArgEditDMPool arguments passed by rpc client
type ArgEditDMPool struct {
Type int32
Oid int64
Mid int64
Pool int32
Dmids []int64
Source oplog.Source
OperatorType oplog.OperatorType
}
// ArgEditDMAttr edit dm attr,bit: AttrXXX defined in model,value:AttrYes/AttrNo
type ArgEditDMAttr struct {
Type int32
Oid int64
Mid int64
Bit uint
Value int32
Dmids []int64
Source oplog.Source
OperatorType oplog.OperatorType
}
// ArgAdvance arguments passed by rpc client
type ArgAdvance struct {
Mid int64
Cid int64
Mode string
}
// ArgMid arguments passed by rpc client
type ArgMid struct {
Mid int64
}
// ArgUpAdvance arguments passed by rpc client
type ArgUpAdvance struct {
Mid int64
ID int64
}
// ArgAddUserFilters add user filters
type ArgAddUserFilters struct {
Type int8
Mid int64
Filters []string
Comment string
}
// ArgDelUserFilters delete user filter
type ArgDelUserFilters struct {
Mid int64
IDs []int64
}
// ArgAddUpFilters add up filters
type ArgAddUpFilters struct {
Type int8
Mid int64
Filters []string
}
// ArgUpFilters up filters
type ArgUpFilters struct {
Mid int64
}
// ArgEditUpFilters edit up filter
type ArgEditUpFilters struct {
Type int8
Mid int64
Active int8
Filters []string
}
// ArgAddGlobalFilter add global filter
type ArgAddGlobalFilter struct {
Type int8
Filter string
}
// ArgGlobalFilters get global filter
type ArgGlobalFilters struct {
}
// ArgDelGlobalFilters delete global filters
type ArgDelGlobalFilters struct {
IDs []int64
}
// ArgBanUsers ban users
type ArgBanUsers struct {
Mid int64
Oid int64
DMIDs []int64
}
// ArgCancelBanUsers cancel banned users
type ArgCancelBanUsers struct {
Mid int64
Aid int64
Filters []string
}
// ArgCid arg cid
type ArgCid struct {
Cid int64
}
// ArgSubtitleGet .
type ArgSubtitleGet struct {
Aid int64
Oid int64
Type int32
}
// ArgSubtitleAllowSubmit .
type ArgSubtitleAllowSubmit struct {
Aid int64
AllowSubmit bool
Lan string
}
// SubtitleSubjectReply .
type SubtitleSubjectReply struct {
AllowSubmit bool
Lan string
LanDoc string
}
// ArgArchiveID .
type ArgArchiveID struct {
Aid int64
}
// ArgMask .
type ArgMask struct {
Cid int64
Plat int8
}

View File

@@ -0,0 +1,86 @@
package model
import (
"go-common/library/time"
)
// All const variable used in dm subject
const (
SubTypeVideo = int32(1) // 主题类型
SubStateOpen = int32(0) // 主题打开
SubStateClosed = int32(1) // 主题关闭
AttrSubGuest = uint(0) // 允许游客弹幕
AttrSubSpolier = uint(1) // 允许剧透弹幕
AttrSubMission = uint(2) // 允许活动弹幕
AttrSubAdvance = uint(3) // 允许高级弹幕
AttrSubMonitorBefore = uint(4) // 先审后发视频
AttrSubMonitorAfter = uint(5) // 先发后审视频
AttrSubMaskOpen = uint(6) // 开启蒙版
AttrSubMblMaskReady = uint(7) // 移动端蒙版生产完成
AttrSubWebMaskReady = uint(8) // web端蒙版生产完成
)
// Subject dm_subject
type Subject struct {
ID int64 `json:"id"`
Type int32 `json:"type"`
Oid int64 `json:"oid"`
Pid int64 `json:"pid"`
Mid int64 `json:"mid"`
State int32 `json:"state"`
Attr int32 `json:"attr"`
ACount int64 `json:"acount"`
Count int64 `json:"count"`
MCount int64 `json:"mcount"`
MoveCnt int64 `json:"move_count"`
Maxlimit int64 `json:"maxlimit"`
Childpool int32 `json:"childpool"`
Ctime time.Time `json:"ctime"`
Mtime time.Time `json:"mtime"`
}
// ViewVideoSubtitle .
type ViewVideoSubtitle struct {
Author *ViewAuthor `json:"author,omitempty"`
ID int64 `json:"id"`
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
SubtitleURL string `json:"subtitle_url"`
}
// ViewAuthor .
type ViewAuthor struct {
Mid int64 `json:"mid"`
Name string `json:"name"`
Sex string `json:"sex"`
Face string `json:"face"`
Sign string `json:"sign"`
Rank int32 `json:"rank"`
}
// AttrVal return val of subject'attr
func (s *Subject) AttrVal(bit uint) int32 {
return (s.Attr >> bit) & int32(1)
}
// AttrSet set val of subject'attr
func (s *Subject) AttrSet(v int32, bit uint) {
s.Attr = s.Attr&(^(1 << bit)) | (v << bit)
}
// SubjectInfo dm subject info
type SubjectInfo struct {
Closed bool `json:"closed"`
Realname bool `json:"real_name"`
Count int64 `json:"count"`
MaskList Mask `json:"mask"`
VideoSubtitle []*ViewVideoSubtitle `json:"subtitles"`
}
// IsMonitoring check if the subject is monitoring or not.
func (s *Subject) IsMonitoring() bool {
return s.AttrVal(AttrSubMonitorBefore) == AttrYes ||
s.AttrVal(AttrSubMonitorAfter) == AttrYes
}

View File

@@ -0,0 +1,406 @@
package model
import (
"go-common/library/ecode"
)
// SubtitleLocation .
const (
SubtitleLocationLeftBottom = uint8(1) //左下角
SubtitleLocationBottomMid = uint8(2) //底部居中
SubtitleLocationRightBottom = uint8(3) //右下角
SubtitleLocationLeftUp = uint8(7) //左上角
SubtitleLocationUpMid = uint8(8) //顶部居中
SubtitleLocationRightUp = uint8(9) //右上角
SubtitleContentSizeLimit = 300
)
var (
// SubtitleLocationMap .
SubtitleLocationMap = map[uint8]struct{}{
SubtitleLocationLeftBottom: {},
SubtitleLocationBottomMid: {},
SubtitleLocationRightBottom: {},
SubtitleLocationLeftUp: {},
SubtitleLocationUpMid: {},
SubtitleLocationRightUp: {},
}
)
// SubtitleStatus .
type SubtitleStatus uint8
// SubtitleStatus
const (
SubtitleStatusUnknown SubtitleStatus = iota
SubtitleStatusDraft
SubtitleStatusToAudit
SubtitleStatusAuditBack
SubtitleStatusRemove
SubtitleStatusPublish
SubtitleStatusCheckToAudit
SubtitleStatusCheckPublish
SubtitleStatusManagerBack
SubtitleStatusManagerRemove
)
// UpperStatus .
type UpperStatus uint8
// UpperStatus
const (
UpperStatusUnknow UpperStatus = iota
UpperStatusUpper
)
// AuthorStatus .
type AuthorStatus uint8
// AuthorStatus
const (
AuthorStatusUnknow AuthorStatus = iota
AuthorStatusAuthor
)
// WaveFormStatus .
type WaveFormStatus uint8
//WaveFormStatus
const (
WaveFormStatusWaitting WaveFormStatus = iota
WaveFormStatusSuccess
WaveFormStatusFailed
WaveFormStatusError // this status need retry
)
// Subtitle .
type Subtitle struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
Type int32 `json:"type"`
Lan uint8 `json:"lan"`
Aid int64 `json:"aid"`
Mid int64 `json:"mid"`
AuthorID int64 `json:"author_id"`
UpMid int64 `json:"up_mid"`
IsSign bool `json:"is_sign"`
IsLock bool `json:"is_lock"`
Status SubtitleStatus `json:"status"`
CheckSum string `json:"-"`
SubtitleURL string `json:"subtitle_url"`
PubTime int64 `json:"pub_time"`
RejectComment string `json:"reject_comment"`
Mtime int64 `json:"mtime"`
Empty bool `json:"empty"`
}
// SubtitleShow .
type SubtitleShow struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
Type int32 `json:"type"`
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
Mid int64 `json:"mid"`
Author string `json:"author"`
Aid int64 `json:"aid"`
ArchiveName string `json:"archive_name"`
IsSign bool `json:"is_sign"`
IsLock bool `json:"is_lock"`
Status SubtitleStatus `json:"status"`
SubtitleURL string `json:"subtitle_url"`
RejectComment string `json:"reject_comment"`
AuthorStatus AuthorStatus `json:"author_status"` // 1:作者
UpperStatus UpperStatus `json:"upper_status"` // 1:up主
}
// SubtitlePub .
type SubtitlePub struct {
Oid int64 `json:"oid"`
Type int32 `json:"type"`
Lan uint8 `json:"lan"`
SubtitleID int64 `json:"subtitle_id"`
IsDelete bool `json:"is_delete"`
}
// VideoSubtitles .
type VideoSubtitles struct {
AllowSubmit bool `json:"allow_submit"`
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
Subtitles []*VideoSubtitle `json:"subtitles"`
}
// VideoSubtitleCache .
type VideoSubtitleCache struct {
VideoSubtitles []*VideoSubtitle `json:"video_subtitles"`
}
// VideoSubtitle .
type VideoSubtitle struct {
ID int64 `json:"id"`
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
IsLock bool `json:"is_lock"`
AuthorMid int64 `json:"author_mid,omitempty"`
SubtitleURL string `json:"subtitle_url"`
}
// Language .
type Language struct {
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
Pub *LanguagePub `json:"pub,omitempty"`
Draft *LanguageID `json:"draft,omitempty"`
Audit *LanguageID `json:"audit,omitempty"`
AuditBack *LanguageID `json:"audit_back,omitempty"`
}
// LanguagePub .
type LanguagePub struct {
SubtitleID int64 `json:"subtitle_id"`
IsLock bool `json:"is_lock"`
IsPub bool `json:"is_pub"`
}
// LanguageID .
type LanguageID struct {
SubtitleID int64 `json:"subtitle_id"`
}
// SubtitlePageResult .
type SubtitlePageResult struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
}
// CountSubtitleResult .
type CountSubtitleResult struct {
Draft int64
ToAudit int64
AuditBack int64
Publish int64
}
// SearchSubtitleResult .
type SearchSubtitleResult struct {
Page *SearchPage `json:"page"`
Results []*SubtitlePageResult `json:"result"`
}
// SearchSubtitle .
type SearchSubtitle struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
Aid int64 `json:"aid"`
Type int32 `json:"type"`
ArchiveName string `json:"archive_name"`
VideoName string `json:"video_name"`
ArchivePic string `json:"archive_pic"`
AuthorID int64 `json:"author_id"`
Author string `json:"author"`
AuthorPic string `json:"author_pic"`
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
Status int32 `json:"status"`
IsSign bool `json:"is_sign"`
IsLock bool `json:"is_lock"`
RejectComment string `json:"reject_comment"`
Mtime int64 `json:"mtime"`
}
// SearchSubtitleResponse .
type SearchSubtitleResponse struct {
Page *SearchPage `json:"page"`
Subtitles []*SearchSubtitle `json:"subtitles"`
}
// SearchSubtitleAuthorItem .
type SearchSubtitleAuthorItem struct {
ID int64 `json:"id"`
Oid int64 `json:"oid"`
Aid int64 `json:"aid"`
Type int32 `json:"type"`
ArchiveName string `json:"archive_name"`
VideoName string `json:"video_name"`
ArchivePic string `json:"archive_pic"`
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
Status int32 `json:"status"`
IsSign bool `json:"is_sign"`
IsLock bool `json:"is_lock"`
RejectComment string `json:"reject_comment"`
Mtime int64 `json:"mtime"`
}
// SearchSubtitleAuthor .
type SearchSubtitleAuthor struct {
Page *SearchPage `json:"page"`
Subtitles []*SearchSubtitleAuthorItem `json:"subtitles"`
Total int64 `json:"total"`
DraftCount int64 `json:"draft_count"`
AuditCount int64 `json:"audit_count"`
BackCount int64 `json:"back_count"`
PublishCount int64 `json:"publish_count"`
}
// SearchSubtitleAssit .
type SearchSubtitleAssit struct {
Page *SearchPage `json:"page"`
Subtitles []*SearchSubtitle `json:"subtitles"`
Total int64 `json:"total"`
AuditCount int64 `json:"audit_count"`
PublishCount int64 `json:"publish_count"`
}
// Subtitle state
const (
AttrSubtitleClose = uint(1) // 关闭稿件字幕
)
// SubtitleSubject .
type SubtitleSubject struct {
Aid int64 `json:"aid"`
Allow bool `json:"allow"`
Attr int32 `json:"attr"`
Lan uint8 `json:"lan"`
Empty bool `json:"empty"`
}
// AttrVal return val of subtitle subject'attr
func (s *SubtitleSubject) AttrVal(bit uint) int32 {
return (s.Attr >> bit) & int32(1)
}
// AttrSet set val of subtitle subject'attr
func (s *SubtitleSubject) AttrSet(v int32, bit uint) {
s.Attr = s.Attr&(^(1 << bit)) | (v << bit)
}
// SubtitleItem .
type SubtitleItem struct {
From float64 `json:"from"`
To float64 `json:"to"`
Location uint8 `json:"location"`
Content string `json:"content"`
}
// SubtitleBody .
type SubtitleBody struct {
FontSize float64 `json:"font_size,omitempty"`
FontColor string `json:"font_color,omitempty"`
BackgroundAlpha float64 `json:"background_alpha,omitempty"`
BackgroundColor string `json:"background_color,omitempty"`
Stroke string `json:"Stroke,omitempty"`
Bodys []*SubtitleItem `json:"body"`
}
// CheckItem .
// err 兼容老接口error等创作中心上线后去掉error返回
func (s *SubtitleBody) CheckItem(duration int64) (detectErrs []*SubtitleDetectError, err error) {
var (
maxDuration = float64(duration) / float64(1000)
)
maxDuration = maxDuration + 1 // 时间刻度上线兼容1
for idx, item := range s.Bodys {
if len(item.Content) > SubtitleContentSizeLimit {
detectErrs = append(detectErrs, &SubtitleDetectError{
Line: int32(idx),
ErrorMsg: ecode.SubtitleSizeLimit.Message(),
})
err = ecode.SubtitleSizeLimit
continue
}
if _, ok := SubtitleLocationMap[item.Location]; !ok {
detectErrs = append(detectErrs, &SubtitleDetectError{
Line: int32(idx),
ErrorMsg: ecode.SubtitleLocationUnValid.Message(),
})
err = ecode.SubtitleSizeLimit
continue
}
if item.From >= item.To {
detectErrs = append(detectErrs, &SubtitleDetectError{
Line: int32(idx),
ErrorMsg: ecode.SubtitleDuarionMustThanZero.Message(),
})
err = ecode.SubtitleSizeLimit
continue
}
if item.From > maxDuration || item.To > maxDuration {
detectErrs = append(detectErrs, &SubtitleDetectError{
Line: int32(idx),
ErrorMsg: ecode.SubtitleVideoDurationOverFlow.Message(),
})
err = ecode.SubtitleSizeLimit
continue
}
}
return
}
// WaveForm .
type WaveForm struct {
Oid int64 `json:"oid"`
Type int32 `json:"type"`
State WaveFormStatus `json:"state"`
WaveFromURL string `json:"wave_form_url"`
Mtime int64 `json:"mtime"`
Empty bool
}
// WaveFormResp .
type WaveFormResp struct {
State WaveFormStatus `json:"state"`
WaveFromURL string `json:"wave_form_url"`
}
// SubtitleLans .
type SubtitleLans []*SubtitleLan
// SubtitleLan .
type SubtitleLan struct {
Code int64 `json:"-"`
Lan string `json:"lan"`
DocZh string `json:"doc_zh"`
DocEn string `json:"-"`
IsDelete bool `json:"-"`
}
// GetByLan .
func (ss SubtitleLans) GetByLan(lan string) (code int64) {
for _, s := range ss {
if s.Lan == lan {
return s.Code
}
}
return 0
}
// GetByID .
func (ss SubtitleLans) GetByID(lanID int64) (lan string, doc string) {
for _, s := range ss {
if s.Code == lanID {
return s.Lan, s.DocZh
}
}
return
}
// SubtitleCheckMsg .
type SubtitleCheckMsg struct {
SubtitleID int64 `json:"subtitle_id"`
Oid int64 `json:"oid"`
}
// FilterCheckResp .
type FilterCheckResp struct {
Hits map[string]string `json:"hits"`
}
// SubtitleDetectError .
type SubtitleDetectError struct {
Line int32 `json:"line"`
ErrorMsg string `json:"error_msg"`
}

View File

@@ -0,0 +1,23 @@
package model
// All const variable used in thumbup
const (
ThumbupLike int8 = 1 // 点赞
ThumbupLikeCancel int8 = 2 // 取消赞
ThumbupHate int8 = 3 // 点踩
ThumbupHateCancel int8 = 4 // 取消踩
)
// ThumbupStat thumbup state
type ThumbupStat struct {
Likes int64 `json:"likes"`
UserLike int8 `json:"user_like"`
}
// CheckThumbup check thumbup.
func CheckThumbup(Thumbup int8) bool {
if Thumbup == ThumbupLikeCancel || Thumbup == ThumbupLike || Thumbup == ThumbupHateCancel || Thumbup == ThumbupHate {
return true
}
return false
}

View File

@@ -0,0 +1,12 @@
package model
// ugc pay type
const (
UgcPayTypeArchive = "archive"
)
// ugc pay relation state
const (
UgcPayRelationStatePaid = "paid"
UgcPayRelationStateNone = "none"
)

View File

@@ -0,0 +1,28 @@
package model
import (
"encoding/json"
)
// ViewDm .
type ViewDm struct {
Closed bool `json:"closed"`
ViewDmSeg *ViewDmSeg `json:"dm_seg"` // 分段弹幕规则
Flag json.RawMessage `json:"flag"` // flag
Subtitle *ViewSubtitle `json:"subtitle,omitempty"` // 字幕
ViewDmMask *Mask `json:"mask,omitempty"` // 蒙版
SpecialDms []string `json:"special_dms,omitempty"` // 高级弹幕
}
// ViewDmSeg .
type ViewDmSeg struct {
PageSize int64 `json:"page_size"`
Total int64 `json:"total"`
}
// ViewSubtitle .
type ViewSubtitle struct {
Lan string `json:"lan"`
LanDoc string `json:"lan_doc"`
Subtitles []*ViewVideoSubtitle `json:"subtitles"`
}

View File

@@ -0,0 +1,87 @@
package model
import (
"encoding/json"
"net/url"
"strconv"
)
const (
_subtitleReportTagReasonID = 5
)
// WorkFlowTagListResp .
type WorkFlowTagListResp struct {
Code int `json:"code"`
Message string `json:"message"`
Data []*WorkFlowTag `json:"data"`
}
// WorkFlowTag .
type WorkFlowTag struct {
Bid int64 `json:"bid"`
TagID int64 `json:"tag_id"`
Rid int64 `json:"rid"`
Name string `json:"name"`
}
// CommonResponse .
type CommonResponse struct {
Code int `json:"code"`
Message string `json:"message"`
}
// WorkFlowAppealAddReq .
type WorkFlowAppealAddReq struct {
Business int64 // 14
LanCode int64 // 语言code
Rid int64 // workflow rid
SubtitleID int64 // 字幕id
Score int32 // 举报人得分
Tid int64 // workflow tag id
Oid int64 // 视频cid
Aid int64 // 稿件id
Mid int64 // 举报人mid
BusinessTypeID int32 // 分区id
BusinessTitle string // 举报内容
BusinessMid int64 // 被举报人mid
Description string // 投诉的具体描述
Extra *WorkFlowAppealAddExtra // 附加信息
}
// WorkFlowAppealAddExtra .
type WorkFlowAppealAddExtra struct {
SubtitleStatus int64 `json:"subtitle_status"`
SubtitleURL string `json:"subtitle_url"`
ArchiveName string `json:"arcvhive_name"`
}
// Params .
func (w *WorkFlowAppealAddReq) Params() (params url.Values) {
var (
err error
bs []byte
)
params = url.Values{}
params.Set("business", strconv.FormatInt(w.Business, 10))
params.Set("fid", strconv.FormatInt(w.LanCode, 10))
params.Set("rid", strconv.FormatInt(w.Rid, 10))
params.Set("eid", strconv.FormatInt(w.SubtitleID, 10))
params.Set("score", strconv.Itoa(int(w.Score)))
params.Set("tid", strconv.FormatInt(w.Tid, 10))
params.Set("oid", strconv.FormatInt(w.Oid, 10))
params.Set("aid", strconv.FormatInt(w.Aid, 10))
params.Set("mid", strconv.FormatInt(w.Mid, 10))
if w.Tid == _subtitleReportTagReasonID {
params.Set("description", w.Description)
}
params.Set("business_typeid", strconv.Itoa(int(w.BusinessTypeID)))
params.Set("business_title", w.BusinessTitle)
params.Set("business_mid", strconv.FormatInt(w.BusinessMid, 10))
if w.Extra != nil {
if bs, err = json.Marshal(w.Extra); err == nil {
params.Set("business_extra", string(bs))
}
}
return
}