recheck.go 6.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255
  1. /*
  2. * @Descripttion:实名认证
  3. * @version:
  4. * @Author: Neo,Huang
  5. * @Date: 2021-04-17 11:04:16
  6. * @LastEditors: Neo,Huang
  7. * @LastEditTime: 2022-04-12 20:27:24
  8. */
  9. package nppa
  10. import (
  11. "bufio"
  12. "encoding/json"
  13. "fmt"
  14. "io"
  15. "log"
  16. "os"
  17. "strconv"
  18. "strings"
  19. "time"
  20. "box-3rdServer/utils"
  21. "github.com/astaxie/beego"
  22. "github.com/bitly/go-simplejson"
  23. "github.com/garyburd/redigo/redis"
  24. )
  25. func getNextTime(now time.Time, startTime string) time.Time {
  26. arr := strings.Split(startTime, ":")
  27. hour, _ := strconv.Atoi(arr[0])
  28. min, _ := strconv.Atoi(arr[1])
  29. next := time.Date(now.Year(), now.Month(), now.Day(), hour, min, 0, 0, now.Location())
  30. if now.Before(next) {
  31. return next
  32. }
  33. next = now.Add(time.Hour * 24)
  34. next = time.Date(next.Year(), next.Month(), next.Day(), hour, min, 0, 0, next.Location())
  35. return next
  36. }
  37. // 备份程序初始化
  38. func InitRecheckProc() {
  39. title := "存量用户实名认证数据检验"
  40. timeBackup := utils.GetKeyConf("nppa", "recheck_time")
  41. if timeBackup == "" {
  42. // 不开启存量用户同步
  43. return
  44. }
  45. go func() {
  46. for {
  47. now := time.Now()
  48. //返回一个指定时间的下次执行的时间戳
  49. next := getNextTime(now, timeBackup)
  50. t := time.NewTimer(next.Sub(now))
  51. log.Printf("下一次【麻将】 [%s] 开始时间为[%s]", title, next.String())
  52. <-t.C
  53. log.Printf("%s--> 神手麻将", title)
  54. RecheckTimeout()
  55. }
  56. }()
  57. }
  58. // 存量用户 - 重新校验玩家列表key
  59. func RecheckDataKey(isAddDay bool) string {
  60. now := time.Now()
  61. if isAddDay {
  62. now = now.Add(time.Hour * 24)
  63. }
  64. keyRecheck := fmt.Sprintf("idRecheck:%d%02d%02d", now.Year(), now.Month(), now.Day())
  65. return keyRecheck
  66. }
  67. // 通知游戏服 - 存量用户验证结果
  68. func UpdatePlayerIdentifyInfo(uid int, m map[string]interface{}) {
  69. idInfo := utils.GetPlayerInfoFromRedis(uid, utils.GetKeyConf("nppa", "key_id_info"))
  70. if idInfo == "" {
  71. idInfo = "{}"
  72. }
  73. j, err := simplejson.NewJson([]byte(idInfo))
  74. if err != nil {
  75. log.Println("UpdatePlayerIdentifyInfo err:", err)
  76. return
  77. }
  78. if m["status"] == 0 || m["status"] == 1 {
  79. j.Set("nppaStatus", m["status"])
  80. j.Set("pi", m["pi"])
  81. j.Set("jmIDName", m["name"])
  82. j.Set("jmIDCard", m["idNum"])
  83. j.Set("lastCheckTime", time.Now().Unix())
  84. j.Set("award", true)
  85. } else {
  86. j.Del("nppaStatus")
  87. j.Del("birthType")
  88. j.Del("jmBirthDate")
  89. j.Del("jmName")
  90. j.Del("jmIDCard")
  91. }
  92. buff, _ := json.Marshal(j)
  93. idInfo = string(buff)
  94. utils.SetPlayerInfoFromRedis(uid, utils.GetKeyConf("nppa", "key_id_info"), idInfo)
  95. }
  96. // 存量玩家重新实名认证
  97. func RecheckPlayerId(uid int) {
  98. // 玩家信息是否已备份
  99. if !utils.IsPlayerExistInRedis(uid) {
  100. return
  101. }
  102. // 根据项目获取玩家已实名认证数据
  103. // name:玩家实名认证姓名
  104. // idNum:玩家实名认证身份证号码
  105. idInfo := GetJiamiIdInfo(uid)
  106. if idInfo["name"] == "" || idInfo["idNum"] == "" || idInfo["chn"] == "" {
  107. return
  108. }
  109. ret := NppaCheckPlayerId(utils.StringToInt(idInfo["chn"]), fmt.Sprintf("%032d", uid), idInfo["name"], idInfo["idNum"])
  110. // log.Printf("RecheckPlayerId uid[%d] ret[%v]", uid, ret)
  111. keyRecheck := RecheckDataKey(true)
  112. // 认证中 - 放入重新校验列表
  113. if ret["code"] == 200 {
  114. if ret["status"] == 1 {
  115. utils.Sadd(keyRecheck, utils.IntToString(uid))
  116. } else {
  117. ret["name"] = idInfo["name"]
  118. ret["idNum"] = idInfo["idNum"]
  119. UpdatePlayerIdentifyInfo(uid, ret)
  120. }
  121. }
  122. }
  123. // 存量玩家重新实名认证
  124. func RecheckQueryPlayerId(uid int) {
  125. // 根据项目获取玩家已实名认证数据
  126. // name:玩家实名认证姓名
  127. // idNum:玩家实名认证身份证号码
  128. idInfo := GetJiamiIdInfo(uid)
  129. if idInfo["name"] == "" || idInfo["idNum"] == "" || idInfo["chn"] == "" {
  130. // 旧数据已删除
  131. return
  132. }
  133. ret := NppaQueryPlayerId(fmt.Sprintf("%032d", uid), utils.StringToInt(idInfo["chn"]))
  134. keyRecheck := RecheckDataKey(true)
  135. // 失败 - 放入重新校验列表
  136. if ret["code"] == 200 {
  137. if ret["status"] == 1 {
  138. utils.Sadd(keyRecheck, utils.IntToString(uid))
  139. } else {
  140. ret["name"] = idInfo["name"]
  141. ret["idNum"] = idInfo["idNum"]
  142. UpdatePlayerIdentifyInfo(uid, ret)
  143. }
  144. }
  145. }
  146. // 获取玩家uid列表 - 文件形式
  147. func RecheckPlayersFromFile() {
  148. // 已经跑过文件
  149. if utils.GetAccountKeyInfo("idRecheck") != "" {
  150. return
  151. }
  152. project := utils.GetConfigPath()
  153. sFile := fmt.Sprintf("%srecheck_uids.txt", project)
  154. if beego.AppConfig.String("runmode") == "test" {
  155. sFile = fmt.Sprintf("%srecheck_uids_test.txt", project)
  156. }
  157. // 重新创建
  158. f, err2 := os.OpenFile(sFile, os.O_CREATE|os.O_RDONLY, 0666)
  159. if err2 != nil {
  160. log.Println("打开配置文件失败 ", sFile)
  161. return
  162. }
  163. defer f.Close()
  164. title := "重新验证玩家实名认证数据"
  165. log.Printf("开始 - %s - 文件", title)
  166. buff := bufio.NewReader(f)
  167. pos := 0
  168. for {
  169. // line, err := buff.ReadString('\n')
  170. line, _, err := buff.ReadLine()
  171. if err != nil || io.EOF == err {
  172. break
  173. }
  174. // line = strings.TrimSpace(line)
  175. uid := utils.StringToInt(strings.TrimSpace(string(line)))
  176. log.Printf("%s uid[%d]", title, uid)
  177. pos += 1
  178. if uid >= 1000000 {
  179. RecheckPlayerId(uid)
  180. time.Sleep(100 * time.Millisecond)
  181. }
  182. }
  183. utils.SetAccountKeyInfo("idRecheck", time.Now().Format("2006-01-02"))
  184. log.Printf("结束 - %s - 文件", title)
  185. }
  186. // key数据是否存在
  187. func IsKeyExistInRedis(key string) bool {
  188. pool := utils.GetAccountRedisPool()
  189. if pool == nil {
  190. fmt.Println("get redis pool fail")
  191. return false
  192. }
  193. rd := pool.Get()
  194. defer rd.Close()
  195. is_key_exit, _ := redis.Bool(rd.Do("EXISTS", key))
  196. return is_key_exit
  197. }
  198. // 定时器 - 结束
  199. func RecheckTimeout() {
  200. keyRecheck := RecheckDataKey(false)
  201. if IsKeyExistInRedis(keyRecheck) {
  202. pool := utils.GetAccountRedisPool()
  203. if pool == nil {
  204. fmt.Println("get redis pool fail")
  205. return
  206. }
  207. rd := pool.Get()
  208. defer rd.Close()
  209. title := "查询结果玩家实名认证数据"
  210. log.Printf("开始 - %s - 查询结果", title)
  211. result, _ := redis.Values(rd.Do("smembers", keyRecheck))
  212. for _, v2 := range result {
  213. uid := utils.StringToInt(string(v2.([]byte)))
  214. log.Printf("%s uid[%d]", title, uid)
  215. RecheckQueryPlayerId(uid)
  216. time.Sleep(100 * time.Millisecond)
  217. }
  218. log.Printf("结束 - %s - 查询结果", title)
  219. } else {
  220. RecheckPlayersFromFile()
  221. }
  222. }