1.前言

        分享一个的我最近完成的开放平台设计

2.简介

开放平台(以下简API) 是为供应商和分销商(以下简称开发人员)开放的API 接口,开发人员可以通过调用搜物API接口,快速的实现和搜物网的数据交换。搜物API支持Json 格式和XML数据格式进行数据交换,搜物API 根据你传入的数据格式返回对应的数据,如你传入的是是XML搜物API将返回Xml 格式数据如是Json 则返回Json格式数据

 

3.总体架构

 

 

 

如上图所示,这里采用了分层来的思想开发本系统

l  HelperLogic  助手类

l  CahceLogic   缓存部分静态数据,

l   DataLogic   数据库业务层

l  OrderLogic  订单逻辑层

l  ProductLogic 产品逻辑层

l  purviewLogic  鉴权逻辑层

l  LogisticsLogic  物流模板逻辑层

 

4.业务逻辑处理

 

 

5.签名算法

   

  1. 把请求中的参数 除了Signature 外 按照参数名称进行正向排序
  2. 把所有参数名和参数值串在一起(不能有空格)
  3. 把后台设置的key值串接到“第二步”得到的字符串尾部(不能有空格)
  4. 采用MD5算法对“第三步”得到的字符串进行加密,生成Signature的值
         /// <summary>
         /// 获取签名字符串
        /// </summary>
        /// <param name="parameters">所有字符型的请求参数</param>
        /// <param name="secret">签名密钥(即搜物APIKey)</param>
        /// <returns>签名</returns>
        public static string GetSignatureStr(IDictionary<string, string> parameters, string secret)
          {
            parameters.Remove("Signature");
            // 第一步:把字典按Key的字母顺序排序
            IDictionary<string, string> sortedParams = new SortedDictionary<string, string>(parameters);
            IEnumerator<KeyValuePair<string, string>> dem = sortedParams.GetEnumerator();

            // 第二步:把所有参数名和参数值串在一起
            StringBuilder query = new StringBuilder();
            while (dem.MoveNext())
            {
                string key = dem.Current.Key;
                string value = dem.Current.Value;
                if (!string.IsNullOrEmpty(key) && !string.IsNullOrEmpty(value))
                {
                    query.Append(key + "=" + value + "&");
                }
            }
            query.Append("key=" + secret);

            // 第三步:使用MD5加密
            MD5 md5 = MD5.Create();
            byte[] bytes = md5.ComputeHash(Encoding.UTF8.GetBytes(query.ToString()));
            // 第四步:把二进制转化为大写的十六进制
            StringBuilder result = new StringBuilder();
            for (int i = 0; i < bytes.Length; i++)
            {
                string hex = bytes[i].ToString("X");
                if (hex.Length == 1)
                {
                    result.Append("0");
                }
                result.Append(hex);
            }
            return result.ToString();
        }

6.安全性考虑

      1.权限接口控制

         

   2.异常访问

      1.在30分钟内,10次签名出错,认为账号异常

      2.访问过于频繁

      3.手动添加黑名单

  3.用户可追溯性

      我们主要实现2点功能 1. 记录用户的访问操作,比如访问那些接口,上传了那些数据, 2.对于重要的数据的可追溯性,如商品价格,库存等 3. 记录每个请求耗时多久  为了实现以上3点功能,我们在这里引入log4net 做为日志系统,减少开发工作量

 

7.POST 数据和返回数据格式参考

   

  [XmlRoot(ElementName = "DataPost")]
    public class DataPostCommon
    { /// <summary>
        /// 方法名
        /// </summary>
        [XmlElement(ElementName = "MethodsName")]
        public string MethodsName { get; set; }
        /// <summary>
        /// ApiGuid
        /// </summary>
         [XmlElement(ElementName = "ApiGuid")]
        public string ApiGuid { get; set; }
        /// <summary>
        /// 数据签名
        /// </summary>
       [XmlElement(ElementName = "Signature")]
        public string Signature { get; set; }

    }

    [XmlRoot(ElementName = "DataPost")]
    /// <summary>
    /// 用户Post 数据格式
    /// </summary>
    public class DataPost<T> : DataPostCommon
    {
       [XmlElement(ElementName = "Parameters")]

        public T Parameters { get; set; }
    }
   /// <summary>
    /// 服务返回
    /// </summary>
    [XmlRoot(ElementName = "SeverReturn")]
    public class SeverReturn<T>
    {
        public SeverReturn()
        {
            ErrNo = ErrorNo.IsSuccess;
        }
        /// <summary>
        /// 错误代码
        /// </summary>
        [XmlElement(ElementName = "ErrNo")]
        public int ErrNo { get; set; }
        /// <summary>
        /// 错误描述
        /// </summary>
        [XmlElement(ElementName = "ErrorDesc")]
        public string ErrorDesc { get; set; }

        [XmlElement(ElementName = "RunResults")]
        public T RunResults { get; set; }
    }
}

 

 posted on 2014-12-04 17:10  Wang.Crystal  阅读(5217)  评论(12编辑  收藏  举报