day_new.go 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475
  1. package services
  2. import (
  3. "encoding/json"
  4. "errors"
  5. "fmt"
  6. "github.com/silenceper/wechat/v2/work/msgaudit"
  7. "hongze/hongze_open_api/models/tables/day_new"
  8. "hongze/hongze_open_api/models/tables/yb"
  9. "hongze/hongze_open_api/services/alarm_msg"
  10. "hongze/hongze_open_api/services/wework"
  11. "hongze/hongze_open_api/utils"
  12. "html"
  13. "strconv"
  14. "strings"
  15. "time"
  16. )
  17. func DayNewWeworkMsgRefresh() (err error) {
  18. defer func() {
  19. if err != nil {
  20. go alarm_msg.SendAlarmMsg("企业微信 会议存档消息刷新失败, Err:"+err.Error(), 1)
  21. }
  22. }()
  23. list := make([]msgaudit.TextMessage, 0)
  24. //获取最新的拉取日志,得到seq和limit的值
  25. lastReq, e := day_new.GetLasReqLog()
  26. if e != nil && e.Error() != utils.ErrNoRow() {
  27. err = errors.New(fmt.Sprintf("获取最新请求日志失败 err: %v", e))
  28. return
  29. }
  30. now := time.Now()
  31. seq := uint64(0)
  32. limit := uint64(100)
  33. timeout := 5
  34. seqRes := uint64(0)
  35. if e == nil {
  36. seq = lastReq.Seq
  37. limit = uint64(lastReq.Limit)
  38. }
  39. msgAuditClient := wework.NewWeWorkMsgAuditClient()
  40. list, seqRes, err = msgAuditClient.GetMsgAuditContent(seq, limit, timeout)
  41. if err != nil {
  42. err = errors.New(fmt.Sprintf("查询会话存档信息失败 err: %v", err))
  43. return
  44. }
  45. if len(list) == 0 { //本次无消息更新
  46. return
  47. }
  48. //查询5天内的消息,用来判断消息是否已存在
  49. before5Time := time.Now().Add(-120*time.Hour).Unix() * 1000
  50. cond := " and msg_time > ?"
  51. var pars []interface{}
  52. pars = append(pars, before5Time)
  53. existList, err := day_new.GetWeworkMsgByCondition(cond, pars)
  54. if err != nil {
  55. return
  56. }
  57. existMsgMap := make(map[string]struct{}, 0)
  58. for _, v := range existList {
  59. existMsgMap[v.MsgId] = struct{}{}
  60. }
  61. //如果成功获取到值,则新增一条新的请求日志,是否需要加入事务,防止请求成功后,数据没有正常插入引起
  62. userMap := make(map[string]struct{}, 0) //企业内用户
  63. extendUserMap := make(map[string]struct{}, 0) //企业外联系人
  64. insertList := make([]*day_new.WeworkMsg, 0)
  65. //配置只查询特定群消息
  66. var limitRoomId string
  67. chatConfig, tErr := yb.GetConfigByCode("wework_chat_room_id")
  68. if tErr == nil {
  69. if chatConfig.ConfigValue != "" {
  70. limitRoomId = chatConfig.ConfigValue
  71. }
  72. }
  73. for _, v := range list {
  74. if _, ok := existMsgMap[v.MsgID]; ok {
  75. continue
  76. }
  77. if limitRoomId != "" {
  78. if v.RoomID != limitRoomId {
  79. continue
  80. }
  81. }
  82. toList, _ := json.Marshal(v.ToList)
  83. v.ToList = append(v.ToList, v.From) //把发言者的userid也加入到用户map里
  84. for _, u := range v.ToList {
  85. if len(u) > 10 && strings.HasPrefix(u, "wm") {
  86. if _, ok := extendUserMap[u]; !ok {
  87. extendUserMap[u] = struct{}{}
  88. }
  89. } else {
  90. if _, ok := userMap[u]; !ok {
  91. userMap[u] = struct{}{}
  92. }
  93. }
  94. }
  95. tmp := &day_new.WeworkMsg{
  96. MsgId: v.MsgID,
  97. Action: v.Action,
  98. From: v.From,
  99. ToList: string(toList),
  100. RoomId: v.RoomID,
  101. MsgTime: v.MsgTime,
  102. MsgType: v.MsgType,
  103. Content: v.Text.Content,
  104. ContentEn: "",
  105. ReportId: 0,
  106. CreateTime: now,
  107. IsAdd: 0,
  108. IsDelete: 0,
  109. ModifyTime: now,
  110. }
  111. insertList = append(insertList, tmp)
  112. }
  113. if len(insertList) > 0 {
  114. //批量插入数据库
  115. err = day_new.AddWeworkMsgMulti(insertList)
  116. if err != nil {
  117. err = errors.New(fmt.Sprintf("批量新增消息失败 err: %v", err))
  118. return
  119. }
  120. }
  121. reqLog := &day_new.WeworkMsgLog{
  122. Seq: seqRes,
  123. Limit: int(limit),
  124. Total: len(list),
  125. ReqResult: int8(1),
  126. CreateTime: now,
  127. ModifyTime: now,
  128. }
  129. err = day_new.AddMsgReqLog(reqLog)
  130. if err != nil {
  131. err = errors.New(fmt.Sprintf("新增请求日志失败 err: %v", err))
  132. return
  133. }
  134. //批量插入用户信息
  135. //查询已有的用户信息,判断是否需要新增
  136. allUsers, err := day_new.GetAllWeworkUser()
  137. if err != nil {
  138. err = errors.New(fmt.Sprintf("查询所有企业微信用户失败 err: %v", err))
  139. return
  140. }
  141. insertUserList := make([]*day_new.WeworkUser, 0)
  142. userExistMap := make(map[string]struct{}, 0) //企业内用户
  143. extendUseExistrMap := make(map[string]struct{}, 0) //企业外联系人
  144. for _, v := range allUsers {
  145. if v.WwExtendUserId != "" {
  146. extendUseExistrMap[v.WwExtendUserId] = struct{}{}
  147. }
  148. if v.WwUserId != "" {
  149. userExistMap[v.WwUserId] = struct{}{}
  150. }
  151. }
  152. for k := range extendUserMap {
  153. if _, ok := extendUseExistrMap[k]; !ok {
  154. tmp := &day_new.WeworkUser{
  155. WwUserId: "",
  156. WwExtendUserId: k,
  157. WwNickName: "",
  158. WwDeptId: 0,
  159. CreateTime: now,
  160. ModifyTime: now,
  161. }
  162. insertUserList = append(insertUserList, tmp)
  163. }
  164. }
  165. for k := range userMap {
  166. if _, ok := userExistMap[k]; !ok {
  167. tmp := &day_new.WeworkUser{
  168. WwUserId: k,
  169. WwExtendUserId: "",
  170. WwNickName: "",
  171. WwDeptId: 0,
  172. CreateTime: now,
  173. ModifyTime: now,
  174. }
  175. insertUserList = append(insertUserList, tmp)
  176. }
  177. }
  178. if len(insertUserList) > 0 {
  179. err = day_new.AddWeworkUserMulti(insertUserList)
  180. if err != nil {
  181. err = errors.New(fmt.Sprintf("新增企业微信用户失败 err: %v", err))
  182. return
  183. }
  184. }
  185. //批量翻译
  186. go DayNewTranslateContentByGoogle()
  187. //go GetWeWorkUsersNickName()
  188. return
  189. }
  190. func GetWeWorkUsersNickName() (err error) {
  191. defer func() {
  192. if err != nil {
  193. go alarm_msg.SendAlarmMsg("企业微信 查询用户昵称失败, Err:"+err.Error(), 1)
  194. }
  195. }()
  196. //查询没有昵称的用户库,循环调用查询昵称接口
  197. users, err := day_new.GetEmptyNickNameWeworkUser()
  198. if err != nil {
  199. return
  200. }
  201. if len(users) == 0 {
  202. return
  203. }
  204. multi := ""
  205. needChangeIds := ""
  206. client := wework.NewWeWorkUserNameClient()
  207. ExtendClient := wework.NewWeWorkExternalContactClient()
  208. //设置批量更新
  209. for _, v := range users {
  210. if v.WwUserId != "" {
  211. ret, e := client.GetUser(v.WwUserId)
  212. if e != nil {
  213. err = e
  214. return
  215. }
  216. if ret.Name != "" {
  217. needChangeIds += strconv.Itoa(int(v.Id)) + ","
  218. multi += ` WHEN ` + strconv.Itoa(int(v.Id)) + ` THEN "` + ret.Name + `"`
  219. }
  220. } else if v.WwExtendUserId != "" {
  221. // todo 获取外部联系人姓名
  222. ret1, e := ExtendClient.GetExternalContact(v.WwExtendUserId)
  223. if e != nil {
  224. //err = e
  225. utils.ApiLog.Println("查询外部联系人失败:" + e.Error())
  226. continue
  227. }
  228. if ret1.ExternalContact.Name != "" {
  229. needChangeIds += strconv.Itoa(int(v.Id)) + ","
  230. multi += ` WHEN ` + strconv.Itoa(int(v.Id)) + ` THEN "` + ret1.ExternalContact.Name + `"`
  231. }
  232. }
  233. }
  234. if needChangeIds != "" {
  235. needChangeIds = strings.Trim(needChangeIds, ",")
  236. err = day_new.MultiUpdateWeworkUserName(multi, needChangeIds)
  237. if err != nil {
  238. err = errors.New(fmt.Sprintf("更新企业微信成员姓名失败 err: %v", err))
  239. return
  240. }
  241. }
  242. return
  243. }
  244. func DayNewTranslateContent() (err error) {
  245. defer func() {
  246. if err != nil {
  247. utils.ApiLog.Println("企业微信 阿里云中翻英操作失败, Err:" + err.Error())
  248. go alarm_msg.SendAlarmMsg("企业微信 阿里云中翻英操作失败, Err:"+err.Error(), 1)
  249. }
  250. }()
  251. //查询待翻译的内容列表
  252. condition := ` and (content_en = "" or content_en is null) and is_delete = 0`
  253. var pars []interface{}
  254. list, err := day_new.GetWeworkMsgByConditionLimit(condition, pars, 2000) //默认最多查询2000条
  255. if err != nil {
  256. err = errors.New(fmt.Sprintf("查询未翻译的聊天记录失败 err: %v", err))
  257. return
  258. }
  259. multi := ""
  260. needChangeIds := ""
  261. count := 0
  262. contentMap := make(map[string]string, 0)
  263. contentEnMap := make(map[string]string)
  264. var ups []interface{}
  265. for _, v := range list {
  266. //如果单条翻译的字符数超过1000,则直接翻译,否则批量翻译
  267. if len(v.Content) > 1000 {
  268. en, e := AliTranslate(v.Content)
  269. if e != nil {
  270. err = e
  271. return
  272. }
  273. needChangeIds += strconv.Itoa(int(v.Id)) + ","
  274. multi += ` WHEN ` + strconv.Itoa(int(v.Id)) + ` THEN ?`
  275. ups = append(ups, en)
  276. } else {
  277. if count >= 50 { //待翻译的条数不能超过50; 单条翻译字符数不能超过1000字符
  278. contentEnMap, err = batchTranslateHandler(contentMap)
  279. if err != nil {
  280. return
  281. }
  282. // 拼接更新sql
  283. for rk, rv := range contentEnMap {
  284. needChangeIds += rk + ","
  285. multi += ` WHEN ` + rk + ` THEN ?`
  286. ups = append(ups, rv)
  287. }
  288. contentMap = make(map[string]string, 0)
  289. count = 0
  290. }
  291. contentMap[strconv.Itoa(int(v.Id))] = v.Content
  292. count += 1
  293. }
  294. }
  295. //剩余不满50条的content
  296. if count > 0 {
  297. contentEnMap, err = batchTranslateHandler(contentMap)
  298. if err != nil {
  299. return
  300. }
  301. // 拼接更新sql
  302. for rk, rv := range contentEnMap {
  303. needChangeIds += rk + ","
  304. multi += ` WHEN ` + rk + ` THEN ?`
  305. ups = append(ups, rv)
  306. }
  307. }
  308. if needChangeIds != "" {
  309. needChangeIds = strings.Trim(needChangeIds, ",")
  310. err = day_new.MultiUpdateContentEn(multi, needChangeIds, ups)
  311. if err != nil {
  312. err = errors.New(fmt.Sprintf("更新翻译后的内容失败 err: %v", err))
  313. return
  314. }
  315. }
  316. return
  317. }
  318. func batchTranslateHandler(contentMap map[string]string) (contentEnMap map[string]string, err error) {
  319. contentEnMap = make(map[string]string, 0)
  320. bytes, err := json.Marshal(contentMap)
  321. if err != nil {
  322. err = errors.New("未翻译的内容json.Marshal失败" + err.Error())
  323. return
  324. }
  325. content := string(bytes)
  326. contentEnList, err := AliTranslateBatch(content)
  327. if err != nil {
  328. return
  329. }
  330. for _, v := range contentEnList {
  331. index := ""
  332. en := ""
  333. errorMsg := ""
  334. for key, item := range v {
  335. if key == "index" {
  336. index = item.(string)
  337. } else if key == "errorMsg" {
  338. errorMsg = item.(string)
  339. } else if key == "code" && item != "200" {
  340. err = errors.New("序号" + index + " 翻译失败,errCode: " + item.(string) + " errMsg: " + errorMsg + " ")
  341. return
  342. } else if key == "translated" {
  343. en = item.(string)
  344. }
  345. }
  346. if index != "" && en != "" {
  347. contentEnMap[index] = en
  348. }
  349. }
  350. return
  351. }
  352. func DayNewTranslateContentByGoogle() (err error) {
  353. var errMsg string
  354. defer func() {
  355. if err != nil {
  356. utils.ApiLog.Println("企业微信 谷歌中翻英操作失败, DayNewTranslateContentByGoogle Err:" + err.Error() + "ErrMsg: " + errMsg)
  357. go alarm_msg.SendAlarmMsg("企业微信 谷歌中翻英操作失败, DayNewTranslateContentByGoogle Err:"+err.Error()+"ErrMsg: "+errMsg, 1)
  358. }
  359. }()
  360. //查询待翻译的内容列表
  361. condition := ` and (content_en = "" or content_en is null) and is_delete = 0`
  362. var pars []interface{}
  363. list, err := day_new.GetWeworkMsgByConditionLimit(condition, pars, 2000) //默认最多查询2000条
  364. if err != nil {
  365. err = errors.New(fmt.Sprintf("查询未翻译的聊天记录失败 err: %v", err))
  366. return
  367. }
  368. multi := ""
  369. needChangeIds := ""
  370. count := 0
  371. contentMap := make(map[string]string, 0)
  372. contentEnMap := make(map[string]string)
  373. var ups []interface{}
  374. for _, v := range list {
  375. //如果单条翻译的字符数超过1000,则直接翻译,否则批量翻译
  376. if len(v.Content) >= 600 {
  377. err, errMsg = singleTranslateHandlerByGoogle(v.Id, v.Content)
  378. if err != nil {
  379. return
  380. }
  381. } else {
  382. if count >= 50 { //待翻译的条数不能超过50; 单条翻译字符数不能超过1000字符
  383. contentEnMap, err, errMsg = batchTranslateHandlerByGoogle(contentMap)
  384. if err != nil {
  385. return
  386. }
  387. // 拼接更新sql
  388. for rk, rv := range contentEnMap {
  389. needChangeIds += rk + ","
  390. multi += ` WHEN ` + rk + ` THEN ?`
  391. ups = append(ups, rv)
  392. }
  393. contentMap = make(map[string]string, 0)
  394. count = 0
  395. }
  396. contentMap[strconv.Itoa(int(v.Id))] = v.Content
  397. count += 1
  398. }
  399. }
  400. //剩余不满50条的content
  401. if count > 0 {
  402. contentEnMap, err, errMsg = batchTranslateHandlerByGoogle(contentMap)
  403. if err != nil {
  404. return
  405. }
  406. // 拼接更新sql
  407. for rk, rv := range contentEnMap {
  408. needChangeIds += rk + ","
  409. multi += ` WHEN ` + rk + ` THEN ?`
  410. ups = append(ups, rv)
  411. }
  412. }
  413. if needChangeIds != "" {
  414. needChangeIds = strings.Trim(needChangeIds, ",")
  415. err = day_new.MultiUpdateContentEn(multi, needChangeIds, ups)
  416. if err != nil {
  417. err = errors.New(fmt.Sprintf("更新翻译后的内容失败 err: %v", err))
  418. return
  419. }
  420. }
  421. return
  422. }
  423. func batchTranslateHandlerByGoogle(contentMap map[string]string) (contentEnMap map[string]string, err error, errMsg string) {
  424. contentStr, _ := json.Marshal(contentMap)
  425. contentEnMap, err, errMsg = GoogleTranslateApi(string(contentStr))
  426. if err != nil {
  427. err = fmt.Errorf("GoogleTranslateApi err: %v", err)
  428. return
  429. }
  430. for k, v := range contentEnMap {
  431. v = html.UnescapeString(v)
  432. contentEnMap[k] = v
  433. }
  434. return
  435. }
  436. func singleTranslateHandlerByGoogle(id uint64, content string) (err error, errMsg string) {
  437. var contentEn string
  438. contentEn, err, errMsg = GoogleSingleTranslateApi(content)
  439. if err != nil {
  440. err = fmt.Errorf("GoogleSingleTranslateApi err: %v", err)
  441. return
  442. }
  443. if contentEn != "" {
  444. contentEn = html.UnescapeString(contentEn)
  445. err = day_new.UpdateContentEnWeworkMsgById(id, contentEn)
  446. if err != nil {
  447. err = errors.New(fmt.Sprintf("更新翻译后的内容失败 err: %v", err))
  448. return
  449. }
  450. }
  451. return
  452. }