C# 数据交换格式 面向对象开发

数据交换格式

最近做梅州医院接口,数据交换格式不是常见的xml或json,“输入输出参数是以“^、$、|”分割的字符串”。

 

----------------- ↓↓↓ 接口数据格式说明 ↓↓↓ -------------------

入参格式: inputData

      业务编号^医疗机构编号^操作员编号^业务周期号^医院交易流水号^中心编码^入参^联机标志^

其中入参: 

以“|”分隔,详见每个交易的参数表, 分项之间使用管道分割符‘|’分割,最后必须要以管道分割符号‘|’结尾,不以‘|’开始。如果入参为多条记录,记录之间以‘$’分割,不同数据项之间以‘|’分割

说明:中心修改参数的原则:只增不减,增加的参数加在参数列表的最后,不在中间插入参数。

 ----------------- ↑↑↑ 接口数据格式说明 ↑↑↑ -------------------

 

程序架构设计
通过以上数据交换格式,程序架构设计如下:

基于面向对象开发,每一个业务的request body(BusinessBody)与参数(InputDateBase)、response body(ResponseBody)与参数(OutputDateBase)建立实体,以属性来对应参数字段。

 

1、业务Body类:

 

 

    /// <summary>

    /// 接口交易主体:

    /// 业务编号^医疗机构编号^操作员编号^业务周期号^医院交易流水号^中心编码^入参^联机标志^

    /// </summary>

    public class BusinessBody

    {

        /// <summary>

        /// 交易实体构造函数:实例化后需要手动指定中心编码

        /// </summary>

        /// <param name="businessType">业务类型</param>

        public BusinessBody(string businessType)

        {

            this.InputDateList = new List<InputDateBase>();

        }

        /// <summary>

        /// 交易实体构造函数

        /// </summary>

        /// <param name="businessType">业务类型</param>

        /// <param name="pactCode">合同单位编码</param>

        public BusinessBody(string businessType,Neusoft.HISFC.Models.Base.Pact pact)

        {

            this.InputDateList = new List<InputDateBase>();

        }

        #region 属性

        /// <summary>

        /// 业务编号(4位)宏定义, 分别对应后台的一项业务操作

        /// </summary>

        public string BusinessType { get; set; }

        /// <summary>

        /// 定点医疗机构编号

        /// </summary>

        public string HospitalNO { get; set; }

        /// <summary>

        /// 操作员编号(8位)医院分配给操作员的唯一标识

        /// </summary>

        public string OperCode { get; set; }

        /// <summary>

        /// 业务周期号(最大36位)操作员签到时,中心返回给his的业务周期号。

        /// </summary>

        public string OperOnlineNo { get; set; }

        /// <summary>

        /// 医院交易流水号(发送方交易流水号)(最大30位)

        /// </summary>

        public string BusinessNO { get; set; }

        /// <summary>

        /// 中心编码:梅州传 441400异地就医传异地的统筹区号

        /// </summary>

        public string CenterCode { get; set; }

        /// <summary>

        /// 入参:以“|”分隔,详见每个交易的参数表, 分项之间使用管道分割符‘|’分割,

        /// 最后必须要以管道分割符号‘|’结尾,不以‘|’开始。如果入参为多条记录,

        /// 记录之间以‘$’分割,不同数据项之间以‘|’分割

        /// 说明:

        /// 中心修改参数的原则:只增不减,增加的参数加在参数列表的最后,不在中间插入参数。

        /// </summary>

        public List<InputDateBase> InputDateList { get; set; }

        

        /// <summary>

        /// 联机标志:梅州:固定传1:联机。

        /// </summary>

        public string ConnetFlag { get; set; }

        #endregion 属性

        #region 方法

        /// <summary>

        /// 返回交易

        /// </summary>

        /// <returns></returns>

        public string GetText()

        {

            string text = string.Empty;

            Class.Function.AddStringCaret(this.BusinessType, ref text);

            Class.Function.AddStringCaret(this.HospitalNO, ref text);

            Class.Function.AddStringCaret(this.OperCode, ref text);

            Class.Function.AddStringCaret(this.OperOnlineNo, ref text);

            Class.Function.AddStringCaret(this.BusinessNO, ref text);

            Class.Function.AddStringCaret(this.CenterCode, ref text);

            string inputDate = string.Empty;

            if (this.InputDateList!=null)

            {                

                foreach (var item in this.InputDateList)

                {

                    Class.Function.AddStringSegment(item.GetText(), ref inputDate);

                }

                inputDate = inputDate.TrimEnd('$');

            }

            Class.Function.AddStringCaret(inputDate, ref text);

            Class.Function.AddStringCaret(this.ConnetFlag, ref text);

            return text;

        }

        #endregion 方法

    }

 

2、响应Body类:

 

    /// <summary>

    /// 交易返回实体 by chen.fch@2017-12-05

    /// 中心交易流水号^联脱机标志^输出参数^

    /// </summary>

    public class ResponseBody

    {

        public ResponseBody()

        {

            OutputDateList = new List<OutputDateBase>();

        }

        /// <summary>

        /// 中心交易流水号:中心交易流水号(最大30位)中心返回

        /// </summary>

        public string ContenBusinessNo { get; set; }

        /// <summary>

        /// 联脱机标志:对联脱机的方案,就诊登记时返回该笔业务的联脱机标志,针对联机项目,该字段不用。

        /// </summary>

        public string CennetFlag { get; set; }

        /// <summary>

        /// 输出参数实体

        /// </summary>

        public List<OutputDateBase> OutputDateList { get; set; }

        /// <summary>

        /// 输出参数文本

        /// </summary>

        public string OutputDateText { get; set; }

        /// <summary>

        /// 将交易返回文本赋值到实体

        /// </summary>

        /// <param name="outputText"></param>

        public int InitModel(string outputText,ref string errMsg)

        {

            try

            {

                string[] ssTemp = Class.Function.SplitStringCaret(outputText);

                this.ContenBusinessNo = ssTemp[0];

                this.CennetFlag = ssTemp[1];

                this.OutputDateText = ssTemp[2];

            }

            catch (Exception ex)

            {

                errMsg = ex.Message;

                return -1;

            }

            return 1;

        }

    }

 

3、请求入参抽象类:

 

    /// <summary>

    /// 入参基础类:处理实现转换为Text格式 by chen.fch@2017-12-05

    /// </summary>

    public abstract class InputDateBase

    {

        /// <summary>

        /// 获取入参文本

        /// </summary>

        /// <returns>返回实体转换文本</returns>

        public abstract string GetText();

    }

4、响应出参抽象类:

 

    /// <summary>

    /// 交易返回抽象类 by chen.fch@2017-12-05

    /// </summary>

    public abstract class OutputDateBase

    {

        /// <summary>

        /// 将交易返回文本转换成实体

        /// </summary>

        /// <param name="text">响应文本</param>

        public abstract void InitModel(string text);

    }

 

5、共通函数类(Function)添加拼接入参和解析出参字符串:

 

        #region 拼接入参

        /// <summary>

        /// 添加以^分隔的属性

        /// </summary>

        /// <param name="addValue"></param>

        /// <param name="strText"></param>

        public static void AddStringCaret(string addValue, ref string strText)

        {

            strText = strText + addValue+ "^";

        }

        /// <summary>

        /// 添加以|分隔的属性

        /// </summary>

        /// <param name="addValue"></param>

        /// <param name="strText"></param>

        public static void AddStringFilter(string addValue, ref string strText)

        {

            strText = strText + addValue + "|";

        }

        /// <summary>

        /// 添加以$分隔的属性

        /// </summary>

        /// <param name="addValue"></param>

        /// <param name="strText"></param>

        public static void AddStringSegment(string addValue, ref string strText)

        {

            strText = strText + addValue + "$";

        }

        

        /// <summary>

        /// 获取入参

        /// </summary>

        /// <param name="t">入参实体</param>

        /// <returns>返回入参文本</returns>

        public static string GetText<T>(T t)

        {

            string text = string.Empty;

            // 设置属性默认值

            PropertyInfo[] propertys = typeof(T).GetProperties();

            foreach (var property in propertys)

            {

                object obj = property.GetValue(t, null);

                AddStringFilter(obj == null ? string.Empty : obj.ToString(), ref text);

            }

            return text;

        }

        #endregion 拼接入参

        #region 解析出参

        /// <summary>

        /// 拆分以^分隔的文本

        /// </summary>

        /// <param name="addValue"></param>

        /// <param name="strText"></param>

        public static string[] SplitStringCaret(string strText)

        {

            return strText.Split('^');

        }

        /// <summary>

        /// 拆分以|分隔的文本

        /// </summary>

        /// <param name="addValue"></param>

        /// <param name="strText"></param>

        public static string[] SplitStringFilter(string strText)

        {

            return strText.Split('|');

        }

        /// <summary>

        /// 拆分以$分隔的文本

        /// </summary>

        /// <param name="addValue"></param>

        /// <param name="strText"></param>

        public static string[] SplitStringSegment(string strText)

        {

            return strText.Split('$');

        }

        /// <summary>

        /// 解析出参

        /// </summary>

        /// <typeparam name="T">返回实体</typeparam>

        /// <param name="t">解析实体</param>

        /// <param name="text">出参文本</param>

        public static void InitModel<T>(T t,string text)

        {

            if (string.IsNullOrEmpty(text.Trim()))

            {

                return;

            }

            string[] ssTemp = SplitStringFilter(text);

            // 设置属性默认值

            PropertyInfo[] propertys = typeof(T).GetProperties();

            int n = 0;

            

            foreach (var property in propertys)

            {

                if (ssTemp.Length > n)

                {

                    property.SetValue(t, ssTemp[n++], null);

                }                

            }

        }

        #endregion 解析出参

 

6、入参与出参实体类:

 

    /// <summary>

    /// 4.3.2.11费用结算撤销(2430)

    /// </summary>

    public class CancelBalance:Base.InputDateBase

    {

        //编号说明类型约束备注

        //1就诊流水号VARCHAR2(20)NOT NULL同登记时的就诊流水号

        public string 就诊流水号 { get; set; }

        //2单据号VARCHAR2(20)NOT NULL调用需要撤销的单据号 

        public string 单据号 { get; set; }

        //3结算日期VARCHAR2(14)

        public string 结算日期 { get; set; }

        //4经办人VARCHAR2(20)NOT NULL医疗机构操作员姓名

        public string 经办人 { get; set; }

        //5是否保存处方标志VARCHAR2(3)二级代码,1:保存;0:不保存

        public string 是否保存处方标志 { get; set; }

        //6开发商标识VARCHAR2(20)

        public string 开发商标识 { get; set; }

        //7交易流水号VARCHAR2(22)异地就医

        public string 交易流水号 { get; set; }

        public override string GetText()

        {

            return Class.Function.GetText<CancelBalance>(this);

        }

    }

 

    /// <summary>

    /// 4.3.2.11费用结算撤销(2430)

    /// </summary>

    public class CancelBalanceResponse:Base.OutputDateBase

    {

        //编号说明类型约束备注

        //1对账日期VARCHAR2(8)YYYYMMDD,跨省异地就医时使用

        public string 对账日期 { get; set; }

        public override void InitModel(string text)

        {

            Class.Function.InitModel<CancelBalanceResponse>(this, text);

        }

    }

 

结束语,以上架构使数据交换格式的字符串处理变成面向对象操作,这样能大大提高程序的可维护性。

 

posted @ 2018-01-21 15:45  大成成  阅读(227)  评论(0编辑  收藏  举报