CloudImageService.cs 28 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711
  1. /******************************************************************************
  2. * 文件名称: CloudImageService.cs
  3. * 文件说明: 个人医保云(影像云)数据采集全量接口封装
  4. * 包含两套子系统共29个交易接口:
  5. * 1. 数据采集系统(11xxx系列): 患者信息/费用/病案/病历等 18个接口
  6. * 2. 医疗机构前置(12xxx系列): 检查检验/结算/预约挂号 9个+2个预留
  7. * 当前版本: V2.0
  8. * 创建日期: 2026-05-06
  9. * 更新日期: 2026-05-07 (补全数据采集系统全量接口)
  10. ******************************************************************************/
  11. using Newtonsoft.Json;
  12. using Newtonsoft.Json.Linq;
  13. using PTMedicalInsurance.Common;
  14. using PTMedicalInsurance.Helper;
  15. using PTMedicalInsurance.Variables;
  16. using System;
  17. using System.Collections.Generic;
  18. using System.IO;
  19. using System.Net;
  20. using System.Text;
  21. namespace PTMedicalInsurance.Business
  22. {
  23. /// <summary>
  24. /// 云影像(个人医保云影像云)数据采集服务封装类
  25. /// 对接两套子系统:数据采集系统 + 医疗机构前置
  26. /// </summary>
  27. public class CloudImageService
  28. {
  29. #region 配置参数
  30. /// <summary>
  31. /// 个人医保云(影像云)数据采集系统服务地址(IP:Port)
  32. /// 负责患者信息、费用、病案、病历等数据的采集
  33. /// 可配置,每家医院可能不同
  34. /// </summary>
  35. public string CollectServerUrl { get; set; } //= "http://10.188.1.44:8091";
  36. /// <summary>
  37. /// 医疗机构前置服务地址(IP:Port)
  38. /// 负责检查检验报告、影像文件、结算信息等的采集
  39. /// 可配置,每家医院可能不同
  40. /// </summary>
  41. public string MedPreServerUrl { get; set; } //= "http://172.25.6.33:5002";
  42. /// <summary>
  43. /// 医疗机构编码
  44. /// </summary>
  45. public string FixmedinsCode { get; set; } //= "H65010200152";
  46. /// <summary>
  47. /// 接口调用密钥
  48. /// </summary>
  49. public string ApiKey { get; set; }// = "XC0Em467BOw9NjpH3OrS";
  50. /// <summary>
  51. /// 接口版本号
  52. /// </summary>
  53. private const string INF_VER = "V1.0";
  54. /// <summary>
  55. /// 请求超时时间(毫秒)
  56. /// </summary>
  57. private const int TIMEOUT_MS = 60000;
  58. #endregion
  59. #region 接口URL映射字典(双系统)
  60. /// <summary>
  61. /// 交易编号与API目标系统的映射关系
  62. /// key: 交易编号(infno), value: (系统类型, API路径)
  63. /// 系统类型: "collect"=数据采集系统, "medpre"=医疗机构前置
  64. /// </summary>
  65. private static readonly Dictionary<string, Tuple<string, string>> ApiUrlMapping = new Dictionary<string, Tuple<string, string>>
  66. {
  67. // ========== 一、数据采集系统 (11xxx系列) ==========
  68. // 所有数据采集系统接口统一走 /collect/elecmedrcd
  69. // 来源:改造说明文档"个人医保云(影像云)数据采集系统"章节
  70. // --- 患者与就诊基础信息 ---
  71. { "11101", Tuple.Create("collect", "/collect/elecmedrcd") }, // 患者基本信息上传
  72. { "11102", Tuple.Create("collect", "/collect/elecmedrcd") }, // 患者费用明细信息上传
  73. { "11103", Tuple.Create("collect", "/collect/elecmedrcd") }, // 患者费用结算信息上传
  74. { "11201", Tuple.Create("collect", "/collect/elecmedrcd") }, // 住院病案首页上传
  75. { "11202", Tuple.Create("collect", "/collect/elecmedrcd") }, // 住院病历记录上传
  76. { "11301", Tuple.Create("collect", "/collect/elecmedrcd") }, // 门急诊诊疗记录上传
  77. { "11302", Tuple.Create("collect", "/collect/elecmedrcd") }, // 急诊留观手术及抢救信息上传
  78. { "11401", Tuple.Create("collect", "/collect/elecmedrcd") }, // 医嘱明细记录上传
  79. { "11402", Tuple.Create("collect", "/collect/elecmedrcd") }, // 输血信息上传
  80. { "11403", Tuple.Create("collect", "/collect/elecmedrcd") }, // 护理操作生命体征测量记录上传
  81. // --- 删除类 ---
  82. { "11104", Tuple.Create("collect", "/collect/elecmedrcd") }, // 患者基本信息删除
  83. { "11901", Tuple.Create("collect", "/collect/elecmedrcd") }, // 就诊业务数据删除
  84. //// --- 特殊信息类 --- 暂无对应编号
  85. //{ "11301", Tuple.Create("collect", "/collect/elecmedrcd") }, // 新生儿信息上传
  86. //{ "11302", Tuple.Create("collect", "/collect/elecmedrcd") }, // 死亡医学证明上传
  87. //{ "11401", Tuple.Create("collect", "/collect/elecmedrcd") }, // 透析治疗记录上传
  88. //{ "11402", Tuple.Create("collect", "/collect/elecmedrcd") }, // 预防接种记录上传
  89. //{ "11501", Tuple.Create("collect", "/collect/elecmedrcd") }, // 高危人群筛查记录上传
  90. //{ "11502", Tuple.Create("collect", "/collect/elecmedrcd") }, // 体检登记信息上传
  91. // ========== 二、医疗机构前置 (12xxx系列) ==========
  92. // 来源:改造说明文档"医疗机构前置"章节
  93. // --- 检查检验报告类 ---
  94. { "12101", Tuple.Create("medpre", "/api/uploadInspection") }, // 临床检验报告上传
  95. { "12102", Tuple.Create("medpre", "/api/uploadStudy") }, // 临床检查报告上传
  96. { "12103", Tuple.Create("medpre", "/api/uploadPath") }, // 病理检查报告上传
  97. { "12104", Tuple.Create("medpre", "/api/uploadBacterial") }, // 细菌培养报告上传
  98. { "12109", Tuple.Create("medpre", "/api/deleteReport") }, // 检验检查报告删除
  99. // --- 结算信息类 ---
  100. { "12201", Tuple.Create("medpre", "/api/uploadSettle") }, // 检查报告结算信息上传
  101. { "12209", Tuple.Create("medpre", "/api/deleteSettle") }, // 检查报告结算信息删除
  102. // --- 预约挂号类 ---
  103. { "12301", Tuple.Create("medpre", "/api/uploadAppoin") }, // 预约挂号信息上传
  104. { "12309", Tuple.Create("medpre", "/api/deleteAppoin") }, // 预约挂号信息删除
  105. //// --- 影像调阅(预留) --- AI自己加的?
  106. //{ "12401", Tuple.Create("medpre", "/api/queryImageIndex") }, // 影像索引查询(预留)
  107. //{ "12402", Tuple.Create("medpre", "/api/viewImage") }, // 影像调阅查看(预留)
  108. };
  109. #endregion
  110. #region 交易编号名称映射
  111. /// <summary>
  112. /// 交易编号与中文名称的映射(用于日志记录和错误提示)
  113. /// </summary>
  114. private static readonly Dictionary<string, string> InfNoNameMapping = new Dictionary<string, string>
  115. {
  116. // 数据采集系统 - 患者与就诊基础信息
  117. { "11101", "患者基本信息上传" },
  118. { "11102", "患者费用明细信息上传" },
  119. { "11103", "患者费用结算信息上传" },
  120. { "11201", "住院病案首页上传" },
  121. { "11202", "住院病历记录上传" },
  122. { "11301", "门急诊诊疗记录上传" },
  123. { "11302", "急诊留观手术及抢救信息上传" },
  124. { "11401", "医嘱明细记录上传" },
  125. { "11402", "输血信息上传" },
  126. { "11403", "护理操作生命体征测量记录上传" },
  127. // 数据采集系统 - 删除类
  128. { "11104", "患者基本信息删除" },
  129. { "11901", "就诊业务数据删除" },
  130. //// 数据采集系统 - 特殊信息类
  131. //{ "11301", "新生儿信息上传" },
  132. //{ "11302", "死亡医学证明上传" },
  133. //{ "11401", "透析治疗记录上传" },
  134. //{ "11402", "预防接种记录上传" },
  135. //{ "11501", "高危人群筛查记录上传" },
  136. //{ "11502", "体检登记信息上传" },
  137. // 医疗机构前置
  138. { "12101", "临床检验报告上传" },
  139. { "12102", "临床检查报告上传" },
  140. { "12103", "病理检查报告上传" },
  141. { "12104", "细菌培养报告上传" },
  142. { "12109", "检验检查报告删除" },
  143. { "12201", "检查报告结算信息上传" },
  144. { "12209", "检查报告结算信息删除" },
  145. { "12301", "预约挂号信息上传" },
  146. { "12309", "预约挂号信息删除" },
  147. //{ "12401", "影像索引查询(预留)" },
  148. //{ "12402", "影像调阅查看(预留)" },
  149. };
  150. #endregion
  151. #region 公开方法 - 统一入口
  152. /// <summary>
  153. /// 执行云影像交易(统一入口)
  154. /// HIS端只需传入交易编号和input入参,外层报文头由本类自动组装
  155. /// 根据交易编号自动路由到对应的数据采集系统或医疗机构前置
  156. /// </summary>
  157. /// <param name="infno">交易编号(如11101患者基本信息, 12101临床检验等)</param>
  158. /// <param name="input">HIS传入的交易入参(input部分),JSON字符串或JObject</param>
  159. /// <returns>统一格式的返回JSON</returns>
  160. public JObject Execute(string infno, object input)
  161. {
  162. string errMsg;
  163. JObject joRtn = new JObject();
  164. string outPut = "";
  165. try
  166. {
  167. Global.writeLog($"[CloudImage] 开始执行交易: {infno} ({GetInfNoName(infno)})");
  168. // 1. 校验交易编号是否有效
  169. if (!ApiUrlMapping.ContainsKey(infno))
  170. {
  171. errMsg = $"不支持的交易编号: {infno},当前支持的交易编号范围: 11101~11502(数据采集), 12101~12402(医疗机构前置)";
  172. Global.writeLog($"[CloudImage] {errMsg}");
  173. return JsonHelper.setExceptionJson(-1, errMsg, errMsg);
  174. }
  175. // 2. 构造完整请求报文
  176. JObject joRequest = BuildRequest(infno, input);
  177. Global.writeLog($"[CloudImage] 请求报文: {JsonHelper.Compress(joRequest.ToString())}");
  178. // 3. 发送HTTP POST请求(自动路由到对应系统)
  179. string responseStr = SendRequest(infno, joRequest.ToString());
  180. Global.writeLog($"[CloudImage] 响应报文: {JsonHelper.Compress(responseStr)}");
  181. // 4. 解析返回结果
  182. joRtn = ParseResponse(responseStr);
  183. Global.writeLog($"[CloudImage] 交易 {infno} 执行完成");
  184. outPut = joRtn.ToString();
  185. return joRtn;
  186. }
  187. catch (Exception ex)
  188. {
  189. errMsg = $"[CloudImage] 交易 {infno} 异常: {ex.Message}";
  190. Global.writeLog(errMsg);
  191. outPut = JsonHelper.setExceptionJson(-1, GetInfNoName(infno), ex.Message).ToString();
  192. return JsonHelper.setExceptionJson(-1, GetInfNoName(infno), ex.Message);
  193. }
  194. finally
  195. {
  196. }
  197. }
  198. #endregion
  199. #region 私有方法 - 报文构造
  200. /// <summary>
  201. /// 构造完整的请求报文
  202. /// 自动组装外层报文头(infno, msgid, infver, inf_time, fixmedins_code, key, rcd_num)
  203. /// HIS传入的数据作为input节点
  204. /// </summary>
  205. private JObject BuildRequest(string infno, object input)
  206. {
  207. JObject joInput = (JObject)input;
  208. int rcdNum = int.Parse(joInput["rcd_num"].ToString());
  209. joInput.Remove("rcd_num");
  210. return BuildRequest( infno, rcdNum, joInput);
  211. }
  212. private JObject BuildRequest(string infno,int rcdNum, object input)
  213. {
  214. JObject joRequest = new JObject();
  215. // 报文头信息
  216. joRequest.Add("infno", infno);
  217. joRequest.Add("msgid", GenerateMsgId());
  218. joRequest.Add("infver", INF_VER);
  219. joRequest.Add("inf_time", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"));
  220. joRequest.Add("fixmedins_code", FixmedinsCode);
  221. joRequest.Add("key", ApiKey);
  222. joRequest.Add("rcd_num", rcdNum);
  223. // 处理input部分
  224. if (input is string)
  225. {
  226. string inputStr = input as string;
  227. if (!string.IsNullOrEmpty(inputStr) && (inputStr.StartsWith("{") || inputStr.StartsWith("[")))
  228. {
  229. joRequest.Add("input", JObject.Parse(inputStr));
  230. }
  231. else
  232. {
  233. joRequest.Add("input", inputStr ?? "");
  234. }
  235. }
  236. else if (input is JObject)
  237. {
  238. joRequest.Add("input", input as JObject);
  239. }
  240. else if (input is JToken)
  241. {
  242. joRequest.Add("input", input as JToken);
  243. }
  244. else
  245. {
  246. joRequest.Add("input", input != null ? input.ToString() : "");
  247. }
  248. return joRequest;
  249. }
  250. /// <summary>
  251. /// 生成报文ID
  252. /// 格式:医疗机构编码 + 年月日时分秒 + 5位随机数
  253. /// 示例:H65010200152202605070003012345
  254. /// </summary>
  255. private string GenerateMsgId()
  256. {
  257. Random rnd = new Random();
  258. int randNum = rnd.Next(10000, 99999);
  259. return $"{FixmedinsCode}{DateTime.Now:yyyyMMddHHmmss}{randNum}";
  260. }
  261. #endregion
  262. #region 私有方法 - HTTP通信(双系统路由)
  263. /// <summary>
  264. /// 发送HTTP POST请求到对应的目标系统
  265. /// 根据交易编号自动选择:数据采集系统 或 医疗机构前置
  266. /// </summary>
  267. /// <param name="infno">交易编号</param>
  268. /// <param name="requestData">请求数据(JSON字符串)</param>
  269. /// <returns>响应内容</returns>
  270. //private string SendRequest(string infno, string requestData)
  271. //{
  272. // var targetInfo = ApiUrlMapping[infno];
  273. // string systemType = targetInfo.Item1; // "collect" 或 "medpre"
  274. // string apiPath = targetInfo.Item2;
  275. // // 根据系统类型选择服务器地址
  276. // string serverUrl;
  277. // if (systemType == "collect")
  278. // {
  279. // serverUrl = CollectServerUrl.TrimEnd('/');
  280. // }
  281. // else // medpre
  282. // {
  283. // serverUrl = MedPreServerUrl.TrimEnd('/');
  284. // }
  285. // string apiUrl = serverUrl + apiPath;
  286. // string systemName = systemType == "collect" ? "数据采集系统" : "医疗机构前置";
  287. // Global.writeLog($"[CloudImage] [{systemName}] 请求URL: {apiUrl}");
  288. // ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls;
  289. // ServicePointManager.ServerCertificateValidationCallback = delegate { return true; };
  290. // HttpWebRequest request = (HttpWebRequest)WebRequest.Create(apiUrl);
  291. // request.Method = "POST";
  292. // request.ContentType = "application/json; charset=utf-8";
  293. // request.Timeout = TIMEOUT_MS;
  294. // byte[] data = Encoding.UTF8.GetBytes(requestData);
  295. // request.ContentLength = data.Length;
  296. // using (Stream reqStream = request.GetRequestStream())
  297. // {
  298. // reqStream.Write(data, 0, data.Length);
  299. // }
  300. // using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
  301. // {
  302. // using (StreamReader reader = new StreamReader(response.GetResponseStream(), Encoding.UTF8))
  303. // {
  304. // return reader.ReadToEnd();
  305. // }
  306. // }
  307. //}
  308. private string SendRequest(string infno, string requestData)
  309. {
  310. var targetInfo = ApiUrlMapping[infno];
  311. string systemType = targetInfo.Item1; // "collect" 或 "medpre"
  312. string apiPath = targetInfo.Item2;
  313. // 根据系统类型选择服务器地址
  314. string serverUrl = systemType == "collect"
  315. ? CollectServerUrl.TrimEnd('/')
  316. : MedPreServerUrl.TrimEnd('/');
  317. string apiUrl = serverUrl + apiPath;
  318. string systemName = systemType == "collect" ? "数据采集系统" : "医疗机构前置";
  319. Global.writeLog($"[CloudImage] [{systemName}] 请求URL: {apiUrl}");
  320. string input = requestData;
  321. string output = "";
  322. string url = apiUrl; // 用于 finally 中的日志
  323. try
  324. {
  325. ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls;
  326. ServicePointManager.ServerCertificateValidationCallback = delegate { return true; };
  327. HttpWebRequest request = (HttpWebRequest)WebRequest.Create(apiUrl);
  328. request.Method = "POST";
  329. request.ContentType = "application/json; charset=utf-8";
  330. request.Timeout = TIMEOUT_MS;
  331. byte[] data = Encoding.UTF8.GetBytes(requestData);
  332. request.ContentLength = data.Length;
  333. using (Stream reqStream = request.GetRequestStream())
  334. {
  335. reqStream.Write(data, 0, data.Length);
  336. }
  337. using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
  338. using (StreamReader reader = new StreamReader(response.GetResponseStream(), Encoding.UTF8))
  339. {
  340. output = reader.ReadToEnd();
  341. return output;
  342. }
  343. }
  344. catch (Exception ex)
  345. {
  346. // 捕获异常,记录到 output 供日志使用
  347. output = $"[ERROR] {ex.Message} (StackTrace: {ex.StackTrace?.Substring(0, Math.Min(500, ex.StackTrace.Length))})";
  348. throw; // 重新抛出,保持原有异常行为
  349. }
  350. finally
  351. {
  352. // 统一日志:无论成功或失败都记录
  353. Global.writeLog($"{infno}:{url}", input, output);
  354. }
  355. }
  356. #endregion
  357. #region 私有方法 - 响应解析
  358. /// <summary>
  359. /// 解析响应报文并转换为统一返回格式
  360. /// 响应格式:{ infcode, msgid, refmsg_time, respond_time, err_msg, Output }
  361. /// </summary>
  362. private JObject ParseResponse(string responseStr)
  363. {
  364. try
  365. {
  366. JObject joResponse = JObject.Parse(responseStr);
  367. string infcode = JsonHelper.getDestValue(joResponse, "infcode");
  368. string err_msg = JsonHelper.getDestValue(joResponse, "err_msg");
  369. // infcode == "0" 表示成功
  370. if (infcode == "0")
  371. {
  372. JObject joRtn = new JObject();
  373. joRtn.Add("errorCode", 0);
  374. joRtn.Add("errorMessage", "");
  375. // 将Output节点作为result返回给HIS
  376. if (joResponse.ContainsKey("Output"))
  377. {
  378. joRtn.Add("result", joResponse["Output"]);
  379. }
  380. else
  381. {
  382. joRtn.Add("result", new JObject());
  383. }
  384. return joRtn;
  385. }
  386. else
  387. {
  388. // 返回错误信息
  389. return JsonHelper.setExceptionJson(-1, "云影像接口错误",
  390. !string.IsNullOrEmpty(err_msg) ? err_msg : "未知错误");
  391. }
  392. }
  393. catch (Exception ex)
  394. {
  395. return JsonHelper.setExceptionJson(-1, "解析响应异常", ex.Message);
  396. }
  397. }
  398. /// <summary>
  399. /// 获取交易名称(用于日志)
  400. /// </summary>
  401. private string GetInfNoName(string infno)
  402. {
  403. return InfNoNameMapping.ContainsKey(infno) ? InfNoNameMapping[infno] : "未知交易";
  404. }
  405. #endregion
  406. #region 公开方法 - 便捷方法(数据采集系统)
  407. /// <summary>
  408. /// 11101 患者基本信息上传
  409. /// </summary>
  410. public JObject UploadPatnBasInfo(object input) { return Execute("11101", input); }
  411. /// <summary>
  412. /// 11102 患者费用明细信息上传
  413. /// </summary>
  414. public JObject UploadPatnFeeDetail(object input) { return Execute("11102", input); }
  415. /// <summary>
  416. /// 11103 患者费用结算信息上传
  417. /// </summary>
  418. public JObject UploadPatnFeeSettle(object input) { return Execute("11103", input); }
  419. /// <summary>
  420. /// 11104 住院病案首页上传
  421. /// </summary>
  422. public JObject UploadInpMedRec(object input) { return Execute("11104", input); }
  423. /// <summary>
  424. /// 11105 住院病历记录上传
  425. /// </summary>
  426. public JObject UploadInpCaseRecord(object input) { return Execute("11105", input); }
  427. /// <summary>
  428. /// 11106 门急诊诊疗记录上传
  429. /// </summary>
  430. public JObject UploadOPEmrRecord(object input) { return Execute("11106", input); }
  431. /// <summary>
  432. /// 11107 急诊留观手术及抢救信息上传
  433. /// </summary>
  434. public JObject UploadEmrgObsSurgery(object input) { return Execute("11107", input); }
  435. /// <summary>
  436. /// 11108 医嘱明细记录上传
  437. /// </summary>
  438. public JObject UploadMedOrderDetail(object input) { return Execute("11108", input); }
  439. /// <summary>
  440. /// 11109 输血信息上传
  441. /// </summary>
  442. public JObject UploadBloodTransfusion(object input) { return Execute("11109", input); }
  443. /// <summary>
  444. /// 11110 护理操作生命体征测量记录上传
  445. /// </summary>
  446. public JObject UploadNursingVitalsign(object input) { return Execute("11110", input); }
  447. /// <summary>
  448. /// 11201 患者基本信息删除
  449. /// </summary>
  450. public JObject DeletePatnBasInfo(object input) { return Execute("11201", input); }
  451. /// <summary>
  452. /// 11202 就诊业务数据删除
  453. /// </summary>
  454. public JObject DeleteVisitBizData(object input) { return Execute("11202", input); }
  455. /// <summary>
  456. /// 11301 新生儿信息上传
  457. /// </summary>
  458. public JObject UploadNewbornInfo(object input) { return Execute("11301", input); }
  459. /// <summary>
  460. /// 11302 死亡医学证明上传
  461. /// </summary>
  462. public JObject UploadDeathCert(object input) { return Execute("11302", input); }
  463. /// <summary>
  464. /// 11401 透析治疗记录上传
  465. /// </summary>
  466. public JObject UploadDialysisRecord(object input) { return Execute("11401", input); }
  467. /// <summary>
  468. /// 11402 预防接种记录上传
  469. /// </summary>
  470. public JObject UploadVaccinationRecord(object input) { return Execute("11402", input); }
  471. /// <summary>
  472. /// 11501 高危人群筛查记录上传
  473. /// </summary>
  474. public JObject UploadHighRiskScreening(object input) { return Execute("11501", input); }
  475. /// <summary>
  476. /// 11502 体检登记信息上传
  477. /// </summary>
  478. public JObject UploadHealthExamReg(object input) { return Execute("11502", input); }
  479. #endregion
  480. #region 公开方法 - 便捷方法(医疗机构前置)
  481. /// <summary>
  482. /// 12101 临床检验报告上传
  483. /// </summary>
  484. public JObject UploadInspection(object input) { return Execute("12101", input); }
  485. /// <summary>
  486. /// 12102 临床检查报告上传(云影像核心接口)
  487. /// </summary>
  488. public JObject UploadStudy(object input) { return Execute("12102", input); }
  489. /// <summary>
  490. /// 12103 病理检查报告上传
  491. /// </summary>
  492. public JObject UploadPathology(object input) { return Execute("12103", input); }
  493. /// <summary>
  494. /// 12104 细菌培养报告上传
  495. /// </summary>
  496. public JObject UploadBacterial(object input) { return Execute("12104", input); }
  497. /// <summary>
  498. /// 12105 检验检查报告删除
  499. /// </summary>
  500. public JObject DeleteReport(object input) { return Execute("12105", input); }
  501. /// <summary>
  502. /// 12201 检查报告结算信息上传
  503. /// </summary>
  504. public JObject UploadSettle(object input) { return Execute("12201", input); }
  505. /// <summary>
  506. /// 12202 检查报告结算信息删除
  507. /// </summary>
  508. public JObject DeleteSettle(object input) { return Execute("12202", input); }
  509. /// <summary>
  510. /// 12301 预约挂号信息上传
  511. /// </summary>
  512. public JObject UploadAppointment(object input) { return Execute("12301", input); }
  513. /// <summary>
  514. /// 12302 预约挂号信息删除
  515. /// </summary>
  516. public JObject DeleteAppointment(object input) { return Execute("12302", input); }
  517. /// <summary>
  518. /// 12401 影像索引查询(预留)
  519. /// </summary>
  520. public JObject QueryImageIndex(object input) { return Execute("12401", input); }
  521. /// <summary>
  522. /// 12402 影像调阅查看(预留)
  523. /// </summary>
  524. public JObject ViewImage(object input) { return Execute("12402", input); }
  525. #endregion
  526. #region 配置方法
  527. /// <summary>
  528. /// 从外部设置数据采集系统服务器地址(支持运行时动态配置)
  529. /// </summary>
  530. /// <param name="serverUrl">完整的服务器地址,如 http://192.168.1.100:8091</param>
  531. public void SetCollectServerUrl(string serverUrl)
  532. {
  533. if (!string.IsNullOrWhiteSpace(serverUrl))
  534. {
  535. CollectServerUrl = serverUrl.TrimEnd('/');
  536. }
  537. }
  538. /// <summary>
  539. /// 从外部设置医疗机构前置服务器地址(支持运行时动态配置)
  540. /// </summary>
  541. /// <param name="serverUrl">完整的服务器地址,如 http://192.168.1.100:5002</param>
  542. public void SetMedPreServerUrl(string serverUrl)
  543. {
  544. if (!string.IsNullOrWhiteSpace(serverUrl))
  545. {
  546. MedPreServerUrl = serverUrl.TrimEnd('/');
  547. }
  548. }
  549. /// <summary>
  550. /// 从外部设置APIKEY
  551. /// </summary>
  552. /// <param name="apikey"></param>
  553. public void SetAPIKey(string apikey)
  554. {
  555. if (!string.IsNullOrWhiteSpace(apikey))
  556. {
  557. ApiKey = apikey;
  558. }
  559. }
  560. /// <summary>
  561. /// 从外部设置APIKEY
  562. /// </summary>
  563. /// <param name="apikey"></param>
  564. public void SetFixmedinsCode(string fixmedinsCode)
  565. {
  566. if (!string.IsNullOrWhiteSpace(fixmedinsCode))
  567. {
  568. FixmedinsCode = fixmedinsCode;
  569. }
  570. }
  571. /// <summary>
  572. /// 获取所有支持的交易编号列表
  573. /// </summary>
  574. public List<string> GetSupportedInfNos()
  575. {
  576. return new List<string>(ApiUrlMapping.Keys);
  577. }
  578. /// <summary>
  579. /// 获取指定系统类型的交易编号列表
  580. /// </summary>
  581. /// <param name="systemType">"collect"=数据采集系统, "medpre"=医疗机构前置</param>
  582. public List<string> GetInfNosBySystem(string systemType)
  583. {
  584. List<string> result = new List<string>();
  585. foreach (var kv in ApiUrlMapping)
  586. {
  587. if (kv.Value.Item1 == systemType)
  588. {
  589. result.Add(kv.Key);
  590. }
  591. }
  592. return result;
  593. }
  594. #endregion
  595. }
  596. }