123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244 |
- package model
- import (
- "bytes"
- "crypto/md5"
- "encoding/json"
- "fmt"
- "math"
- "net/url"
- "strconv"
- "strings"
- "time"
- "go-common/library/log"
- "github.com/dgryski/go-farm"
- )
- // SplitInts splts string to int-slice by ,
- func SplitInts(s string) (res []int) {
- if s == "" {
- return
- }
- ints := strings.Split(s, ",")
- for _, v := range ints {
- i, _ := strconv.Atoi(v)
- res = append(res, i)
- }
- return
- }
- // JoinInts merges int slice to string.
- func JoinInts(ints []int) string {
- if len(ints) == 0 {
- return ""
- }
- if len(ints) == 1 {
- return strconv.Itoa(ints[0])
- }
- buf := bytes.Buffer{}
- for _, v := range ints {
- buf.WriteString(strconv.Itoa(v))
- buf.WriteString(",")
- }
- if buf.Len() > 0 {
- buf.Truncate(buf.Len() - 1)
- }
- return buf.String()
- }
- // ExistsInt judge if item in the ints.
- func ExistsInt(ints []int, item int) (exists bool) {
- for _, i := range ints {
- if i == item {
- return true
- }
- }
- return false
- }
- // HashToken gets token's hash value.
- func HashToken(token string) int64 {
- return int64(farm.Hash64([]byte(token)) % math.MaxInt64)
- }
- // RealTime culculates real time by timezone.
- func RealTime(reportZone int) time.Time {
- now := time.Now()
- _, offset := now.Zone()
- return now.Add(time.Duration(reportZone-offset/3600) * time.Hour)
- }
- // Scheme gets uri scheme.
- func Scheme(typ int8, val string, platform, build int) (uri string) {
- switch typ {
- case LinkTypeBangumi: // 番剧
- if platform == PlatformAndroid {
- uri = SchemeBangumiSeasonAndroid + val
- } else {
- uri = SchemeBangumiSeasonIOS + val
- }
- case LinkTypeVideo: // 视频
- if platform == PlatformAndroid {
- uri = SchemeVideoAndroid + val
- } else {
- uri = SchemeVideoIOS + val
- }
- case LinkTypeLive:
- var (
- param string
- parts = strings.Split(val, ",") // 值可能为 1 或者 1,0
- )
- if len(parts) == 2 {
- param = "?broadcast_type=" + parts[1]
- }
- uri = SchemeLive + parts[0] + param
- if platform == PlatformAndroid && build < 5290000 {
- uri = SchemeLiveAndroid + parts[0]
- }
- case LinkTypeSplist: // 专题
- uri = SchemeSplist + val
- case LinkTypeAuthor: // 个人空间
- if platform == PlatformAndroid {
- uri = SchemeAuthorAndroid + val
- } else {
- uri = SchemeAuthorIOS + val
- }
- case LinkTypeSearch: // 搜索
- if platform == PlatformAndroid {
- uri = SchemeSearchAndroid + val
- } else {
- uri = SchemeSearchIOS + val
- }
- case LinkTypeBrowser: // H5
- if platform == PlatformAndroid {
- uri = SchemeBrowserAndroid + url.QueryEscape(val)
- } else {
- // 容错逻辑,标准写法是 SchemeBrowserIOS + val,且 val 需要业务方进行 urlencode
- // 但是老客户端有bug,客户端会强制encode,客户端从 5.28 开始修了这个bug
- // 版本覆盖完全后,可改成标准写法
- uri = val
- }
- case LinkTypeVipBuy:
- uri = SchemeVipBuy + val
- case LinkTypeCustom:
- uri = val
- default:
- uri = ""
- }
- return
- }
- // ParseBuild parses string to build struct.
- func ParseBuild(s string) (builds map[int]*Build) {
- builds = make(map[int]*Build)
- if s == "" {
- return
- }
- temp := make(map[string]*Build)
- if err := json.Unmarshal([]byte(s), &temp); err != nil {
- log.Error("json.Unmarshal(%s) error(%v)", s, err)
- return
- }
- for plat, build := range temp {
- p, _ := strconv.Atoi(plat)
- builds[p] = build
- }
- return
- }
- // TempTaskID gen temporary task ID.
- func TempTaskID() string {
- n := time.Now().UnixNano()
- m := md5.Sum([]byte(strconv.FormatInt(n, 10)))
- return TempTaskPrefix + fmt.Sprintf("%x", m)[:8] // 要把taskid当作jobkey参数,jobkey要求长度最多9位, 1位prefix+8位时间hash值前段
- }
- // JobName gen job name.
- func JobName(timestamp int64, content, linkValue, group string) int64 {
- s := []byte(fmt.Sprintf("%d%s%s%s%s", timestamp, time.Now().Format("20060102"), content, linkValue, group))
- return int64(farm.Hash64(s) % math.MaxInt64)
- }
- // Hash gen hash value by solt.
- func Hash(salt string) string {
- s := salt + strconv.FormatInt(time.Now().UnixNano(), 10)
- return fmt.Sprintf("%x", md5.Sum([]byte(s)))
- }
- // 免打扰时间默认值
- const (
- _defaultSilentBeginHour = 22
- _defaultSilentEndHour = 8
- _defaultSilentBeginMinute = 0
- _defaultSilentEndMinute = 0
- )
- // ParseSilentTime .
- func ParseSilentTime(s string) (st BusinessSilentTime) {
- st = BusinessSilentTime{
- BeginHour: _defaultSilentBeginHour,
- EndHour: _defaultSilentEndHour,
- BeginMinute: _defaultSilentBeginMinute,
- EndMinute: _defaultSilentEndMinute,
- }
- s = strings.Trim(s, " ")
- if s == "" {
- return
- }
- r := strings.Split(s, "-")
- if len(r) != 2 {
- return
- }
- begin := strings.Split(r[0], ":")
- if len(begin) == 2 {
- st.BeginHour, _ = strconv.Atoi(begin[0])
- st.BeginMinute, _ = strconv.Atoi(begin[1])
- }
- end := strings.Split(r[1], ":")
- if len(end) == 2 {
- st.EndHour, _ = strconv.Atoi(end[0])
- st.EndMinute, _ = strconv.Atoi(end[1])
- }
- return st
- }
- // IsAndroid .
- func IsAndroid(platformID int) bool {
- m := map[int]bool{
- PlatformIPhone: true,
- PlatformIPad: true,
- }
- return !m[platformID]
- }
- // ValidateBuild checks token&platform valid.
- func ValidateBuild(platform, build int, builds map[int]*Build) bool {
- if len(builds) == 0 {
- return true
- }
- if IsAndroid(platform) {
- platform = PlatformAndroid
- }
- if builds[platform] == nil {
- return true
- }
- c := builds[platform].Condition
- b := builds[platform].Build
- switch c {
- case "gt":
- return build > b
- case "gte":
- return build >= b
- case "lt":
- return build < b
- case "lte":
- return build <= b
- case "eq":
- return build == b
- case "ne":
- return build != b
- }
- return false
- }
|