wechat.client.js 47 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021
  1. /**
  2. * 用户微信客户端。
  3. */
  4. "use strict";
  5. let RedisClient = require('../../repository/redis/redis.client');
  6. let RedisModel = require('../redis.model');
  7. let ObjectUtil = require("../../util/object.util.js");
  8. let ModelUtil = require('../../util/model.util');
  9. let WechatSDK = require('../../util/wechat.sdk');
  10. let PatientRepo = require('../../repository/oracle/patient.repo');
  11. let TopicRepo = require("../../repository/oracle/topics.repo.js");
  12. let ParticipantRepo = require("../../repository/oracle/participant.repo");
  13. let redisConn = RedisClient.redisClient().connection;
  14. let clientCache = require('../socket.io/client.cache').clientCache();
  15. let configFile = require('../../include/commons').CONFIG_FILE;
  16. let config = require('../../resources/config/' + configFile);
  17. let log = require("../../util/log.js");
  18. let https = require('https');
  19. let http = require('http');
  20. let async = require('async');
  21. let querystring = require('querystring');
  22. let HlwyyWechatAssistantSDK = require("../../util/hlwyyWechatAssistant.sdk");
  23. var reqq = require('request');
  24. const CONTENT_TYPES = require('../../include/commons').CONTENT_TYPES;
  25. const SESSION_TYPES = require('../../include/commons').SESSION_TYPES;
  26. const SOCKET_TYPES = require('../../include/commons').SOCKET_TYPES;
  27. const REDIS_KEYS = require('../../include/commons').REDIS_KEYS;
  28. class WechatClient extends RedisModel {
  29. constructor() {
  30. super();
  31. }
  32. /**
  33. * 取得用户微信端状态。若Redis中找不到,则从MySQL中查找。
  34. *
  35. * @param userId
  36. * @param handler
  37. */
  38. static getWechatStatus(userId, handler) {
  39. redisConn.hgetallAsync(RedisModel.makeRedisKey(REDIS_KEYS.UserWechatStatus, userId))
  40. .then(function (status) {
  41. if (status == null) {
  42. PatientRepo.findWechatOpenId(userId, handler);
  43. } else {
  44. handler(null, {openid: status.openid});
  45. }
  46. })
  47. .catch(function (err) {
  48. handler(err, null);
  49. });
  50. }
  51. /**
  52. * 向微信端用户发送消息。若用户微信端在线,通过Web Socket推送给患者,如果不在线则通过微信的模板消息。
  53. *
  54. * 只推送文本、图片及语音消息
  55. *
  56. * @param targetUserId
  57. * @param message 消息体
  58. */
  59. static sendMessage(targetUserId, targetUserName, message) {
  60. if (message&&(message.content_type == CONTENT_TYPES.PlainText ||
  61. message.content_type == CONTENT_TYPES.Image ||
  62. message.content_type == CONTENT_TYPES.Audio||
  63. message.content_type == CONTENT_TYPES.PrescriptionBloodStatus ||
  64. message.content_type == CONTENT_TYPES.PrescriptionFollowupContent ||
  65. message.content_type == CONTENT_TYPES.ReservationDoorCardInfo ||
  66. message.content_type == CONTENT_TYPES.ChangeDoorCardInfo ||
  67. message.content_type == CONTENT_TYPES.ChangeDoorDoctor ||
  68. message.content_type == CONTENT_TYPES.ChangeDoorPackageItems ||
  69. message.content_type == CONTENT_TYPES.VideoAnswerStatus ||
  70. message.content_type == CONTENT_TYPES.Screening ||
  71. message.content_type == CONTENT_TYPES.PrescriptionReject ||
  72. message.content_type == CONTENT_TYPES.PrescriptionSuggest ||
  73. message.content_type == CONTENT_TYPES.ConsultSuggest ||
  74. message.content_type == CONTENT_TYPES.PayMessage
  75. )) {
  76. let patientClient = clientCache.findById(targetUserId);
  77. let pc_patientClient = clientCache.findById("pcpatient_"+targetUserId);
  78. let doctorClient = clientCache.findByIdAndType(message.sender_id,SOCKET_TYPES.DOCTOR);
  79. let pc_doctorClient = clientCache.findByIdAndType("pc_"+message.sender_id,SOCKET_TYPES.PC_DOCTOR);
  80. let pc_patient_system_Client = clientCache.findByIdAndType("pcpatient_system_"+targetUserId,SOCKET_TYPES.PC_PATIENT_SYSTEM);
  81. var count = 0;
  82. if (patientClient || pc_patientClient || pc_patient_system_Client) {
  83. if(patientClient){
  84. log.warn("User's wechat endpoint is online, sending via web socket. User id: ", targetUserId);
  85. WechatClient.sendViaWebSocket(patientClient.socket, message);
  86. }
  87. if(pc_patientClient){
  88. log.warn("User's pc endpoint is online, sending via web socket. User id: ", targetUserId);
  89. WechatClient.sendViaWebSocket(pc_patientClient.socket, message);
  90. }
  91. if(pc_patient_system_Client){
  92. log.warn("User's pc systme endpoint is online, sending via web socket. User id: ", targetUserId);
  93. WechatClient.sendViaWebSocket(pc_patient_system_Client.socket, message);
  94. }
  95. if(doctorClient && (patientClient || pc_patientClient) ){
  96. log.error("doctor sessionid "+doctorClient.sessionId);
  97. if(patientClient && patientClient.sessionId==doctorClient.sessionId){
  98. log.error("patient sessionid "+patientClient.sessionId);
  99. //用户socket在线,推送给用户后,告知医生此消息已读
  100. WechatClient.updateParticipantLastFetchTime(doctorClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  101. WechatClient.sendReadDoctor(doctorClient.socket, message);
  102. }
  103. if(pc_patientClient && pc_patientClient.sessionId==doctorClient.sessionId){
  104. log.error("pc_patient sessionid "+pc_patientClient.sessionId);
  105. //用户socket在线,推送给用户后,告知医生此消息已读
  106. WechatClient.updateParticipantLastFetchTime(doctorClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  107. WechatClient.sendReadDoctor(doctorClient.socket, message);
  108. }
  109. }else{
  110. count++;
  111. }
  112. if(pc_doctorClient){
  113. log.error("pc_doctor sessionid "+pc_doctorClient.sessionId);
  114. if(patientClient){
  115. log.error("patient sessionid "+patientClient.sessionId);
  116. if(patientClient.sessionId==pc_doctorClient.sessionId){
  117. //用户socket在线,推送给用户后,告知医生此消息已读
  118. WechatClient.updateParticipantLastFetchTime(pc_doctorClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  119. WechatClient.sendReadDoctor(pc_doctorClient.socket, message);
  120. }
  121. }
  122. if(pc_patientClient){
  123. log.error("pc_patient sessionid "+pc_patientClient.sessionId);
  124. if(pc_patientClient.sessionId==pc_doctorClient.sessionId){
  125. //用户socket在线,推送给用户后,告知医生此消息已读
  126. WechatClient.updateParticipantLastFetchTime(pc_doctorClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  127. WechatClient.sendReadDoctor(pc_doctorClient.socket, message);
  128. }
  129. }
  130. }else{
  131. count++;
  132. }
  133. if(count==0){
  134. log.error("doctor client not found");
  135. }
  136. } else {
  137. log.info("User's wechat and pc endpoint is not online, sending via wechat template message. User id: ", targetUserId);
  138. var isSendWXTem = true;//是否发送微信模板
  139. if(message.content_type == CONTENT_TYPES.PrescriptionBloodStatus||message.content_type == CONTENT_TYPES.PrescriptionFollowupContent){
  140. var content = JSON.parse(message.content);
  141. if(content.isSendWxTemplate){
  142. message.content = content.text;
  143. }else {
  144. isSendWXTem = false;
  145. }
  146. }
  147. if(isSendWXTem){
  148. //发送第三方接口的微信模版消息
  149. WechatClient.sendThirdMessageTemplate(targetUserId, targetUserName, message);
  150. //发送厦门i健康的微信模版消息
  151. // WechatClient.sendViaMessageTemplate(targetUserId, targetUserName, message);
  152. }
  153. }
  154. } else if(message.content_type == CONTENT_TYPES.TopicEnd){
  155. let patientClient = clientCache.findById(targetUserId);
  156. if(patientClient){//结束咨询的告知患者
  157. WechatClient.sendViaWebSocket(patientClient.socket, message);
  158. }
  159. let pc_patientClient = clientCache.findById("pcpatient_"+targetUserId);
  160. if(pc_patientClient)//结束咨询的告知患者
  161. {
  162. WechatClient.sendViaWebSocket(pc_patientClient.socket, message);
  163. }
  164. }
  165. };
  166. static sendViaWebSocket(socket, message) {
  167. socket.emit('message', {
  168. id: message.id,
  169. session_id: message.session_id,
  170. sender_id: message.sender_id,
  171. sender_name: message.sender_name,
  172. content_type: message.content_type,
  173. content: message.content,
  174. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  175. type: message.content_type, // legacy support
  176. name: message.sender_name,
  177. sender_img : message.sender_img
  178. });
  179. }
  180. static sendAllRead(doctorId,sessionId){
  181. let doctorClient = clientCache.findByIdAndType(doctorId,SOCKET_TYPES.DOCTOR);
  182. let pc_doctorClient = clientCache.findByIdAndType("pc_"+doctorId,SOCKET_TYPES.PC_DOCTOR);
  183. if(doctorClient){
  184. if(doctorClient.sessionId==sessionId){
  185. doctorClient.socket.emit('message',{ read:"all"});
  186. }else{
  187. log.warn(" doctor not in the same session ");
  188. }
  189. }else{
  190. if(pc_doctorClient && pc_doctorClient.sessionId == sessionId){
  191. pc_doctorClient.socket.emit('message',{ read:"all"});
  192. }else{
  193. log.warn(doctorId+" target doctor is not online!");
  194. }
  195. }
  196. }
  197. static sendMucAllRead(doctorId,loginUserId,sessionId){
  198. let loginClinet = clientCache.findByIdAndType(loginUserId,SOCKET_TYPES.DOCTOR);
  199. if(loginClinet){
  200. //muc是医生来获取数据不能更新成已读
  201. log.warn("type is muc login is doctor not send all read to other doctor!")
  202. return;
  203. }
  204. let doctorClient = clientCache.findByIdAndType(doctorId,SOCKET_TYPES.DOCTOR);
  205. let pc_doctorClient = clientCache.findByIdAndType("pc_"+doctorId,SOCKET_TYPES.PC_DOCTOR);
  206. if(doctorClient){
  207. if(doctorClient.sessionId==sessionId){
  208. doctorClient.socket.emit('message',{ read:"all"});
  209. }else{
  210. log.warn(" doctor not in the same session ");
  211. }
  212. }else{
  213. if(pc_doctorClient && pc_doctorClient.sessionId == sessionId){
  214. pc_doctorClient.socket.emit('message',{ read:"all"});
  215. }else{
  216. log.warn(doctorId+" target doctor is not online!");
  217. }
  218. }
  219. }
  220. static sendReadDoctor(socket, message) {
  221. socket.emit('message', {
  222. id: message.id,
  223. session_id: message.session_id,
  224. sender_id: message.sender_id,
  225. sender_name: message.sender_name,
  226. content_type: message.content_type,
  227. content: message.content,
  228. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  229. type: message.content_type, // legacy support
  230. name: message.sender_name,
  231. read:"one"
  232. });
  233. }
  234. static sendReadDoctorByDoctorId(doctorId, message) {
  235. let doctorClient = clientCache.findByIdAndType(doctorId,SOCKET_TYPES.DOCTOR);
  236. let pc_doctorClient = clientCache.findByIdAndType("pc_"+doctorId,SOCKET_TYPES.PC_DOCTOR);
  237. if(!doctorClient&&!pc_doctorClient){
  238. log.warn("target doctor is not online!");
  239. return;
  240. }
  241. let sendDoctorClient = clientCache.findByIdAndType(message.sender_id,SOCKET_TYPES.DOCTOR);
  242. if(!sendDoctorClient){
  243. sendDoctorClient = clientCache.findByIdAndType("pc_"+message.sender_id,SOCKET_TYPES.PC_DOCTOR);
  244. }
  245. var count = 0;
  246. if(doctorClient&&sendDoctorClient&&sendDoctorClient.sessionId==doctorClient.sessionId){
  247. WechatClient.updateParticipantLastFetchTime(doctorClient.sessionId, doctorId, ObjectUtil.timestampToLong(message.timestamp));
  248. sendDoctorClient.socket.emit('message', {
  249. id: message.id,
  250. session_id: message.session_id,
  251. sender_id: message.sender_id,
  252. sender_name: message.sender_name,
  253. content_type: message.content_type,
  254. content: message.content,
  255. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  256. type: message.content_type, // legacy support
  257. name: message.sender_name,
  258. read:"one"
  259. });
  260. }else{
  261. count++;
  262. }
  263. //发送pc版医生端
  264. if(pc_doctorClient&&sendDoctorClient&&sendDoctorClient.sessionId==pc_doctorClient.sessionId){
  265. WechatClient.updateParticipantLastFetchTime(pc_doctorClient.sessionId, doctorId, ObjectUtil.timestampToLong(message.timestamp));
  266. pc_doctorClient.socket.emit('message', {
  267. id: message.id,
  268. session_id: message.session_id,
  269. sender_id: message.sender_id,
  270. sender_name: message.sender_name,
  271. content_type: message.content_type,
  272. content: message.content,
  273. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  274. type: message.content_type, // legacy support
  275. name: message.sender_name,
  276. read:"one"
  277. });
  278. }else{
  279. count++;
  280. }
  281. if(count==2){
  282. log.warn("doctor is not in the same session or is not online");
  283. }
  284. }
  285. static sendSocketMessageToDoctor(doctorId, message) {
  286. let doctorClient = clientCache.findByIdAndType(doctorId,SOCKET_TYPES.DOCTOR);
  287. let pc_doctorClient = clientCache.findByIdAndType("pc_"+doctorId,SOCKET_TYPES.PC_DOCTOR);
  288. if(!doctorClient&&!pc_doctorClient){
  289. log.warn("target doctor is not online!");
  290. return;
  291. }
  292. // let sendClient = clientCache.findByIdAndType(message.sender_id,SOCKET_TYPES.DOCTOR);//app医生发送的消息
  293. // if(!sendClient){//pc医生发送的消息
  294. // sendClient = clientCache.findByIdAndType("pc_"+message.sender_id,SOCKET_TYPES.PC_DOCTOR);
  295. // }
  296. // if(!sendClient){//居民发送的消息
  297. // sendClient = clientCache.findByIdAndType(message.sender_id,SOCKET_TYPES.PATIENT);
  298. // }
  299. var count = 0;
  300. if(doctorClient&&message.session_id==doctorClient.sessionId){
  301. WechatClient.updateParticipantLastFetchTime(doctorClient.sessionId, doctorId, ObjectUtil.timestampToLong(message.timestamp));
  302. doctorClient.socket.emit('message', {
  303. id: message.id,
  304. session_id: message.session_id,
  305. sender_id: message.sender_id,
  306. sender_name: message.sender_name,
  307. content_type: message.content_type,
  308. content: message.content,
  309. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  310. type: message.content_type, // legacy support
  311. name: message.sender_name,
  312. });
  313. }else{
  314. count++;
  315. }
  316. //发送pc端 - PC端消息不做sessionid的判断,前端自己判断消息归属于哪个会话,自行渲染--20191012-huangwenjie
  317. // if(pc_doctorClient&&message.session_id==pc_doctorClient.sessionId){
  318. if(pc_doctorClient){
  319. WechatClient.updateParticipantLastFetchTime(pc_doctorClient.sessionId, doctorId, ObjectUtil.timestampToLong(message.timestamp));
  320. pc_doctorClient.socket.emit('message', {
  321. id: message.id,
  322. session_id: message.session_id,
  323. sender_id: message.sender_id,
  324. sender_name: message.sender_name,
  325. content_type: message.content_type,
  326. content: message.content,
  327. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  328. type: message.content_type, // legacy support
  329. name: message.sender_name,
  330. });
  331. }else{
  332. count++;
  333. }
  334. if(count==2){
  335. log.warn("doctor is not in the same session or is not online");
  336. }
  337. }
  338. /**
  339. * 推送MDT,医生外层新消息
  340. * @param doctorId
  341. * @param message
  342. */
  343. static sendMDTSocketMessageToDoctor(doctorId, message) {
  344. // let doctorMDTClient = clientCache.findByIdAndType("pcim_"+doctorId,SOCKET_TYPES.PCIM_DOCTOR);
  345. let doctorSYSTEMClient = clientCache.findByIdAndType("pc_system_"+doctorId,SOCKET_TYPES.PC_DOCTOR_SYSTEM);
  346. let doctorAPPSYSTEMClient = clientCache.findByIdAndType("doctor_system_"+doctorId,SOCKET_TYPES.DOCTOR_SYSTEM);
  347. //外层
  348. if(!doctorSYSTEMClient){
  349. log.warn("target system doctor is not online!");
  350. }else{
  351. doctorSYSTEMClient.socket.emit('message', {
  352. id: message.id,
  353. session_id: message.session_id,
  354. sender_id: message.sender_id,
  355. sender_name: message.sender_name,
  356. content_type: 1,
  357. content: {"socket_sms_type":4},
  358. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  359. type: message.content_type, // legacy support
  360. name: message.sender_name,
  361. patient_name:message.patient_name,
  362. patient_age:message.patient_age,
  363. patient_sex:message.patient_sex
  364. });
  365. }
  366. if(!doctorAPPSYSTEMClient){
  367. log.warn("target system app doctor is not online!");
  368. }else{
  369. doctorAPPSYSTEMClient.socket.emit('message', {
  370. id: message.id,
  371. session_id: message.session_id,
  372. sender_id: message.sender_id,
  373. sender_name: message.sender_name,
  374. content_type: 1,
  375. content: {"socket_sms_type":4},
  376. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  377. type: message.content_type, // legacy support
  378. name: message.sender_name,
  379. patient_name:message.patient_name,
  380. patient_age:message.patient_age,
  381. patient_sex:message.patient_sex
  382. });
  383. }
  384. }
  385. static sendPcImSocket(targetId, message, sessionType) {
  386. if (message.content_type == CONTENT_TYPES.PlainText ||
  387. message.content_type == CONTENT_TYPES.Image ||
  388. message.content_type == CONTENT_TYPES.Audio||
  389. message.content_type == CONTENT_TYPES.Video||
  390. message.content_type == CONTENT_TYPES.GoTo||
  391. sessionType==SESSION_TYPES.SYSTEM) {
  392. let pcim_doctorClient = clientCache.findByIdAndType("pcim_"+targetId,SOCKET_TYPES.PCIM_DOCTOR);
  393. if(pcim_doctorClient) {
  394. let customData = {
  395. session_id: message.session_id||'',
  396. session_type: sessionType,
  397. from: message.sender_id|| '',
  398. data: message.content,
  399. business_type: message.business_type || 1
  400. };
  401. pcim_doctorClient.socket.emit('message', {
  402. session_id: message.session_id||'',
  403. session_type: sessionType,
  404. from: message.sender_id|| '',
  405. data: message.content,
  406. business_type: message.business_type || 1,
  407. sender_name: message.sender_name,
  408. content_type: message.content_type,
  409. content: message.content,
  410. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  411. type: message.content_type, // legacy support
  412. name: message.sender_name,
  413. patient_name:message.patient_name,
  414. patient_age:message.patient_age,
  415. patient_sex:message.patient_sex
  416. });
  417. }
  418. }
  419. }
  420. static sendSocketMessageToPatient(patientId, message) {
  421. let patientClient = clientCache.findByIdAndType(patientId,SOCKET_TYPES.PATIENT);
  422. let pc_patientClient = clientCache.findByIdAndType("pcpatient_"+patientId,SOCKET_TYPES.PC_PATIENT);
  423. if(!patientClient&&!pc_patientClient){
  424. log.warn("target patient is not online!");
  425. return;
  426. }
  427. // let sendClient = clientCache.findByIdAndType(message.sender_id,SOCKET_TYPES.DOCTOR);//app医生发送的消息
  428. // if(!sendClient){//pc医生发送的消息
  429. // sendClient = clientCache.findByIdAndType("pc_"+message.sender_id,SOCKET_TYPES.PC_DOCTOR);
  430. // }
  431. // if(!sendClient){//居民发送的消息
  432. // sendClient = clientCache.findByIdAndType(message.sender_id,SOCKET_TYPES.PATIENT);
  433. // }
  434. var count = 0;
  435. if(patientClient&&message.session_id==patientClient.sessionId){
  436. WechatClient.updateParticipantLastFetchTime(patientClient.sessionId, patientId, ObjectUtil.timestampToLong(message.timestamp));
  437. patientClient.socket.emit('message', {
  438. id: message.id,
  439. session_id: message.session_id,
  440. sender_id: message.sender_id,
  441. sender_name: message.sender_name,
  442. content_type: message.content_type,
  443. content: message.content,
  444. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  445. type: message.content_type, // legacy support
  446. name: message.sender_name,
  447. });
  448. }else{
  449. count++;
  450. }
  451. //发送pc端
  452. if(pc_patientClient&&message.session_id==pc_patientClient.sessionId){
  453. WechatClient.updateParticipantLastFetchTime(pc_patientClient.sessionId, patientId, ObjectUtil.timestampToLong(message.timestamp));
  454. pc_patientClient.socket.emit('message', {
  455. id: message.id,
  456. session_id: message.session_id,
  457. sender_id: message.sender_id,
  458. sender_name: message.sender_name,
  459. content_type: message.content_type,
  460. content: message.content,
  461. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  462. type: message.content_type, // legacy support
  463. name: message.sender_name,
  464. });
  465. }else{
  466. count++;
  467. }
  468. if(count==2){
  469. log.warn("patient is not in the same session or is not online");
  470. }
  471. }
  472. //推送居民、居民PC、医生、医生PC外层推送
  473. static sendSystemSocketMessage(targetUserId, message) {
  474. //居民外层消息推送
  475. let patientClient = clientCache.findByIdAndType("patient_system_"+targetUserId,SOCKET_TYPES.PATIENT_SYSTEM);
  476. let pc_patientClient = clientCache.findByIdAndType("pcpatient_system_"+targetUserId,SOCKET_TYPES.PC_PATIENT_SYSTEM);
  477. if(!patientClient&&!pc_patientClient){
  478. log.warn("target patient systemt is not online!");
  479. // return;
  480. }
  481. var patientcount = 0;
  482. if(patientClient&&message.session_id==patientClient.sessionId){
  483. WechatClient.updateParticipantLastFetchTime(patientClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  484. patientClient.socket.emit('message', {
  485. id: message.id,
  486. session_id: message.session_id,
  487. sender_id: message.sender_id,
  488. sender_name: message.sender_name,
  489. content_type: message.content_type,
  490. content: message.content,
  491. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  492. type: message.content_type, // legacy support
  493. name: message.sender_name,
  494. });
  495. }else{
  496. patientcount++;
  497. }
  498. //发送pc端
  499. if(pc_patientClient&&message.session_id==pc_patientClient.sessionId){
  500. WechatClient.updateParticipantLastFetchTime(pc_patientClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  501. pc_patientClient.socket.emit('message', {
  502. id: message.id,
  503. session_id: message.session_id,
  504. sender_id: message.sender_id,
  505. sender_name: message.sender_name,
  506. content_type: message.content_type,
  507. content: message.content,
  508. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  509. type: message.content_type, // legacy support
  510. name: message.sender_name,
  511. });
  512. }else{
  513. patientcount++;
  514. }
  515. if(patientcount==2){
  516. log.warn("patient system is not in the same session or is not online");
  517. }
  518. //医生外层消息推送
  519. let doctorClient = clientCache.findByIdAndType("doctor_system_"+targetUserId,SOCKET_TYPES.DOCTOR_SYSTEM);
  520. let pc_doctorClient = clientCache.findByIdAndType("pc_system_"+targetUserId,SOCKET_TYPES.PC_DOCTOR_SYSTEM);
  521. if(!doctorClient&&!pc_doctorClient){
  522. log.warn("target doctor system is not online!");
  523. // return;
  524. }
  525. var doctorcount = 0;
  526. if(doctorClient&&message.session_id==doctorClient.sessionId){
  527. WechatClient.updateParticipantLastFetchTime(doctorClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  528. doctorClient.socket.emit('message', {
  529. id: message.id,
  530. session_id: message.session_id,
  531. sender_id: message.sender_id,
  532. sender_name: message.sender_name,
  533. content_type: message.content_type,
  534. content: message.content,
  535. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  536. type: message.content_type, // legacy support
  537. name: message.sender_name,
  538. });
  539. }else{
  540. doctorcount++;
  541. }
  542. //发送pc端 - PC端消息不做sessionid的判断,前端自己判断消息归属于哪个会话,自行渲染--20191012-huangwenjie
  543. // if(pc_doctorClient&&message.session_id==pc_doctorClient.sessionId){
  544. if(pc_doctorClient){
  545. WechatClient.updateParticipantLastFetchTime(pc_doctorClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  546. pc_doctorClient.socket.emit('message', {
  547. id: message.id,
  548. session_id: message.session_id,
  549. sender_id: message.sender_id,
  550. sender_name: message.sender_name,
  551. content_type: message.content_type,
  552. content: message.content,
  553. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  554. type: message.content_type, // legacy support
  555. name: message.sender_name,
  556. });
  557. }else{
  558. doctorcount++;
  559. }
  560. if(doctorcount==2){
  561. log.warn("doctor system is not in the same session or is not online");
  562. }
  563. }
  564. //推送托盘消息
  565. static sendMDTSystemSocketMessage(targetUserId, message) {
  566. //居民外层消息推送
  567. let mdtDcotorClient = clientCache.findByIdAndType("pcim_"+targetUserId,SOCKET_TYPES.PCIM_DOCTOR);
  568. if(!mdtDcotorClient){
  569. log.warn("target mdt doctor is not online!");
  570. }
  571. var mdtDoctorCount = 0;
  572. if(mdtDcotorClient&&message.session_id==mdtDcotorClient.sessionId){
  573. WechatClient.updateParticipantLastFetchTime(mdtDcotorClient.sessionId, targetUserId, ObjectUtil.timestampToLong(message.timestamp));
  574. mdtDcotorClient.socket.emit('message', {
  575. id: message.id,
  576. session_id: message.session_id,
  577. sender_id: message.sender_id,
  578. sender_name: message.sender_name,
  579. content_type: message.content_type,
  580. content: message.content,
  581. timestamp: ObjectUtil.timestampToLong(message.timestamp),
  582. type: message.content_type, // legacy support
  583. name: message.sender_name,
  584. });
  585. }else{
  586. mdtDoctorCount++;
  587. }
  588. if(mdtDoctorCount==2){
  589. log.warn("doctor system is not in the same session or is not online");
  590. }
  591. }
  592. /**
  593. *
  594. * 发送微信模板消息给居民
  595. *
  596. * @param targetUserId
  597. * @param message
  598. */
  599. static sendViaMessageTemplate(targetUserId, targetUserName, message) {
  600. async.waterfall([
  601. // 获取微信openid
  602. function (callback) {
  603. PatientRepo.findWechatOpenIds(targetUserId, function (err, res) {
  604. if (err) {
  605. ModelUtil.logError("Get wechat openid failed", err);
  606. return;
  607. }
  608. var map = new Map();
  609. res.forEach(function (participant) {
  610. let openid = participant.openid;
  611. if (targetUserId==participant.code) {
  612. if (!openid) {
  613. ModelUtil.logError("User haven't bound with wechat, user id: " + targetUserId);
  614. }
  615. map.set("openid",participant);
  616. }else {
  617. if(!map.has(openid)){
  618. map.set(openid,participant);
  619. }
  620. }
  621. })
  622. //
  623. // let openid = result && result.length > 0 ? result[0].openid : null;
  624. // if (!openid) {
  625. // ModelUtil.logError("User haven't bound with wechat, user id: " + targetUserId);
  626. // return;
  627. // }
  628. //
  629. // log.warn("Send via wechat message template, user id: " + targetUserId + ", openid: " + openid);
  630. callback(null, map);
  631. });
  632. },
  633. // 获取议题信息
  634. function (map, callback) {
  635. TopicRepo.findLastTopicStatusAndType(message.session_id, function (err, res) {
  636. if (err) {
  637. ModelUtil.logError("Get topic failed", err);
  638. return;
  639. }
  640. if (!res || res.length == 0) {
  641. ModelUtil.logError("Unable to find session last topic");
  642. return;
  643. }
  644. callback(null, map, message.sender_name, res[0]);
  645. });
  646. },
  647. // 发送消息
  648. function (map, senderName, topic,callback) {
  649. let replyContent = message.content;
  650. switch (Number.parseInt(message.content_type)) {
  651. case CONTENT_TYPES.Image:
  652. replyContent = "[图片]";
  653. break;
  654. case CONTENT_TYPES.Audio:
  655. replyContent = "[语音]";
  656. break;
  657. default:
  658. break;
  659. }
  660. var patient = map.get("openid");
  661. map.delete("openid");
  662. let agent = topic.agent;
  663. let consultTitle = null;
  664. let description = null;
  665. let url = config.wechatConfig.baseUrl;
  666. switch (topic.type) {
  667. case 8:
  668. consultTitle = "续方";
  669. description = "续方咨询";
  670. url = url + "/wx/html/yszx/html/prescription-consulting.html";
  671. case 11:
  672. consultTitle = "上门服务";
  673. description = "上门服务咨询";
  674. url = url + "wx/html/appoint_service/html/appoint-serviceDetail.html";
  675. default:
  676. consultTitle = "健康";
  677. description = topic.description;
  678. url = url + "/wx/html/yszx/html/consulting-doctor.html";
  679. }
  680. if(agent){//代理人发起的议题
  681. var agentOpenid = "";
  682. if(map.size>0){
  683. for(var key of map.keys()){
  684. var member = map.get(key);
  685. if(agent == member.code){
  686. agentOpenid = key;
  687. var openid = key;
  688. var first = "您的家人("+patient.name+")的"+consultTitle+"咨询有新的回复";
  689. // 发送模板消息
  690. WechatSDK.sendTemplateMessage({
  691. touser: openid,
  692. name: member.name,
  693. patient: member.code,
  694. template_id: config.wechatConfig.template.consultTemplate,
  695. url: url + "?openid=" + openid + "&type="+topic.type+"&doctor="+message.sender_id+
  696. "&consult=" + topic.id + "&toUser=" + member.code + "&toName=" + member.name+"&represented="+patient.code,
  697. data: {
  698. first: {value: first, color: "#000000"}
  699. , remark: {value: "", color: "#000000"}
  700. , keyword1: {value: description, color: "#000000"}
  701. , keyword2: {value: replyContent, color: "#000000"}
  702. , keyword3: {value: senderName, color: "#000000"}
  703. }
  704. }, function (err, res) {
  705. err ? log.error(err) : log.info(res);
  706. });
  707. }
  708. }
  709. }
  710. if(patient.openid&&patient.openid!=agentOpenid){
  711. var first = "您的"+consultTitle+"咨询有新的回复";
  712. // 发送模板消息
  713. WechatSDK.sendTemplateMessage({
  714. touser: patient.openid,
  715. name: targetUserName,
  716. patient: targetUserId,
  717. template_id: config.wechatConfig.template.consultTemplate,
  718. url: url + "?openid=" + patient.openid +"&type="+topic.type+"&doctor="+message.sender_id+
  719. "&consult=" + topic.id + "&toUser=" + targetUserId + "&toName=" + targetUserName+"&represented="+patient.code,
  720. data: {
  721. first: {value: first, color: "#000000"}
  722. , remark: {value: "", color: "#000000"}
  723. , keyword1: {value: description, color: "#000000"}
  724. , keyword2: {value: replyContent, color: "#000000"}
  725. , keyword3: {value: senderName, color: "#000000"}
  726. }
  727. }, function (err, res) {
  728. err ? log.error(err) : log.info(res);
  729. });
  730. }
  731. }else {//自己发起的议题
  732. // 发送模板消息
  733. if(patient.openid){
  734. WechatSDK.sendTemplateMessage({
  735. touser: patient.openid,
  736. name: targetUserName,
  737. patient: targetUserId,
  738. template_id: config.wechatConfig.template.consultTemplate,
  739. url: url + "?openid=" + patient.openid +"&type="+topic.type+"&doctor="+message.sender_id+
  740. "&consult=" + topic.id + "&toUser=" + targetUserId + "&toName=" + targetUserName+"&represented="+patient.code,
  741. data: {
  742. first: {value: "您的"+consultTitle+"咨询有新的回复", color: "#000000"}
  743. , remark: {value: "", color: "#000000"}
  744. , keyword1: {value: description, color: "#000000"}
  745. , keyword2: {value: replyContent, color: "#000000"}
  746. , keyword3: {value: senderName, color: "#000000"}
  747. }
  748. }, function (err, res) {
  749. err ? log.error(err) : log.info(res);
  750. });
  751. }
  752. if(map.size>0){
  753. for(var key of map.keys()){
  754. if(!patient.openid||key!=patient.openid){
  755. var member = map.get(key);
  756. var openid = key;
  757. var first = "您的家人("+patient.name+")的"+consultTitle+"咨询有新的回复";
  758. // 发送模板消息
  759. WechatSDK.sendTemplateMessage({
  760. touser: openid,
  761. name: member.name,
  762. patient: member.code,
  763. template_id: config.wechatConfig.template.consultTemplate,
  764. url: url + "?openid=" + openid +"&type="+topic.type+"&doctor="+message.sender_id+
  765. "&consult=" + topic.id + "&toUser=" + member.code + "&toName=" + member.name+"&represented="+patient.code,
  766. data: {
  767. first: {value: first, color: "#000000"}
  768. , remark: {value: "", color: "#000000"}
  769. , keyword1: {value: description, color: "#000000"}
  770. , keyword2: {value: replyContent, color: "#000000"}
  771. , keyword3: {value: senderName, color: "#000000"}
  772. }
  773. }, function (err, res) {
  774. err ? log.error(err) : log.info(res);
  775. });
  776. }
  777. }
  778. }
  779. }
  780. callback(null, null);
  781. }
  782. ],
  783. function (err, res) {
  784. if (!err) {
  785. log.info("Send via wechat template message, DONE!");
  786. }
  787. });
  788. };
  789. static updateParticipantLastFetchTime(sessionId, userId, score) {
  790. score = score + 1000;
  791. let participantsKey = RedisModel.makeRedisKey(REDIS_KEYS.SessionParticipants, sessionId);
  792. redisConn.zaddAsync(participantsKey, score, userId)
  793. .then(function (res) {
  794. ParticipantRepo.updateLastFetchTime(new Date(score), sessionId, userId, function (err, res) {
  795. if (err) {
  796. log.error("Update participant last fetch time failed: ", err);
  797. }
  798. });
  799. })
  800. .catch(function (err) {
  801. log.error("Update participant last fetch time failed: ", err);
  802. });
  803. };
  804. /**
  805. * 发送第三方接口的微信模版消息
  806. * @param targetUserId
  807. * @param message
  808. */
  809. static sendThirdMessageTemplate(targetUserId, targetUserName, message) {
  810. async.waterfall([
  811. // 获取微信openid
  812. function (callback) {
  813. PatientRepo.findOne(targetUserId, function (err, res) {
  814. if (err) {
  815. ModelUtil.logError("Get wechat openid failed", err);
  816. return;
  817. }
  818. var map = new Map();
  819. res.forEach(function (participant) {
  820. let openid = participant.openid;
  821. let idcard = participant.idcard;
  822. let mobile = participant.mobile;
  823. let name = participant.name;
  824. let id = participant.id;
  825. map.set("openid",openid);
  826. map.set("idcard",idcard);
  827. map.set("mobile",mobile);
  828. map.set("name",name);
  829. map.set("id",id);
  830. })
  831. //
  832. // let openid = result && result.length > 0 ? result[0].openid : null;
  833. // if (!openid) {
  834. // ModelUtil.logError("User haven't bound with wechat, user id: " + targetUserId);
  835. // return;
  836. // }
  837. //
  838. // log.warn("Send via wechat message template, user id: " + targetUserId + ", openid: " + openid);
  839. callback(null, map);
  840. });
  841. },
  842. // 获取议题信息
  843. function (map, callback) {
  844. TopicRepo.findLastTopicStatusAndType(message.session_id, function (err, res) {
  845. if (err) {
  846. ModelUtil.logError("Get topic failed", err);
  847. return;
  848. }
  849. if (!res || res.length == 0) {
  850. ModelUtil.logError("Unable to find session last topic");
  851. return;
  852. }
  853. callback(null, map, message.sender_name, res[0]);
  854. });
  855. },
  856. // 发送消息
  857. function (map, senderName, topic,callback) {
  858. let replyContent = message.content;
  859. switch (Number.parseInt(message.content_type)) {
  860. case CONTENT_TYPES.Image:
  861. replyContent = "[图片]";
  862. break;
  863. case CONTENT_TYPES.Audio:
  864. replyContent = "[语音]";
  865. break;
  866. default:
  867. break;
  868. }
  869. let consultTitle = null;
  870. let description = null;
  871. let url = config.thirdApiMessageConfig.baseUrl;
  872. switch (topic.type) {
  873. case 8:
  874. consultTitle = "续方";
  875. description = "续方咨询";
  876. url = url + "/wx/html/yszx/html/prescription-consulting.html";
  877. case 11:
  878. consultTitle = "上门服务";
  879. description = "上门服务咨询";
  880. url = url + "wx/html/appoint_service/html/appoint-serviceDetail.html";
  881. default:
  882. consultTitle = "咨询回复提醒";
  883. description = topic.description;
  884. if("xmijk" == config.imClientType.id){
  885. url = "https://zb.xmtyw.cn/ims-wx/index.html#/chatRoom?type="+topic.type+"&consultCode="+topic.id;
  886. }else if("zsyy" == config.imClientType.id){
  887. url = "https://hlwyy.xmzsh.com/ims-wx/index.html#/chatRoom?type="+topic.type+"&consultCode="+topic.id;
  888. }else if("xm_ykyy_wx" == config.imClientType.id){
  889. url = "https://intel.yanketong.com/ims-wx/index.html#/chatRoom?type="+topic.type+"&consultCode="+topic.id;
  890. }else{}
  891. }
  892. // 发送模板消息
  893. if(map != null){
  894. let userName = map.get("name");
  895. let idCard = map.get("idcard");
  896. let phone = map.get("mobile");
  897. let title = consultTitle;
  898. let content = "您的咨询有新的回复";
  899. let contentString = replyContent;
  900. // log.info("推送居民公众号:params:"+params)
  901. let params = 'senderName='+encodeURIComponent(senderName)+'&userName='+encodeURIComponent(userName)+'&idCard='+idCard+"&phone="+phone+'&title='+encodeURIComponent(consultTitle)+'&content='+encodeURIComponent(description)+'&contentString='+encodeURIComponent(contentString)+'&url='+encodeURIComponent(url);
  902. HlwyyWechatAssistantSDK.request(userName,idCard,phone,title,content,contentString,url,params, function (err, res) {
  903. // WlyyAssistantSDK.request('admin', '0a5c5258-8863-4b07-a3f9-88c768528ab4', '', 'admin_imei', '/doctor/feldsher/sendDoctorTemplate', param, function (err, res) {
  904. // WlyySDK.request('admin', '0a5c5258-8863-4b07-a3f9-88c768528ab4', '', 'admin_imei', '/doctor/feldsher/sendDoctorTemplate?' + params, 'GET', function (err, res) {
  905. if(err){
  906. log.error(err);
  907. }else {
  908. log.info(res);
  909. }
  910. });
  911. }
  912. callback(null, null);
  913. }
  914. ],
  915. function (err, res) {
  916. if (!err) {
  917. log.info("Send via wechat template message, DONE!");
  918. }
  919. });
  920. };
  921. }
  922. module.exports = WechatClient;