一、跨域

nuget引用microsoft.aspnet.webapi.core

webapiconfig.cs中配置:

// web api 配置和服务
config.enablecors(new enablecorsattribute("*", "*", "*"));2

二、清除默认返回xml格式

global.asax中配置:

globalconfiguration.configuration.formatters.xmlformatter.supportedmediatypes.clear();

三、oracle配置

nuget引用oracle.manageddataaccess

1、根据插件生成app.config中的配置添加到web.config中

2、引用oracle.manageddataaccess.client

四、log4net

1、nuget引用log4net

2、assemblyinfo.cs中配置:

[assembly: log4net.config.xmlconfigurator(configfile = "log4net.config", watch = true)]

3、新建log4net.config配置文件

属性-复制到输出目录改为如果较新则复制

log4net.config中配置:

<!-- level的级别,由高到低 -->
<!-- none > fatal > error > warn > debug > info > all-->
<log4net>
  <!--信息日志类-->
  <logger name="loginfo">
    <level value="info" />
    <appender-ref ref="infoappender" />
  </logger>
  <!--错误日志类-->
  <logger name="logerror">
    <level value="error" />
    <appender-ref ref="errorappender" />
  </logger>
  <!--信息日志附加介质-->
  <!-- name属性指定其名称,type则是log4net.appender命名空间的一个类的名称-->
  <appender name="infoappender" type="log4net.appender.rollingfileappender">
    <!--日志输出到exe程序这个相对目录下-->
    <param name="file" value="log4net\\loginfo\\" />
    <!--输出的日志不会覆盖以前的信息-->
    <param name="appendtofile" value="true" />
    <!--日志文件的最大大小-->
    <param name="maximumfilesize" value="2mb" />
    <!--备份文件的个数-->
    <param name="maxsizerollbackups" value="10" />
    <!--是否使用静态文件名-->
    <param name="staticlogfilename" value="false" />
    <!--日志文件名-->
    <param name="datepattern" value="yyyymmdd&quot;.txt&quot;" />
    <!--文件创建的方式-->
    <param name="rollingstyle" value="composite" />
    <!--过滤器-->
    <lockingmode type="asia.mobile.apiservice.filter.minimallockdeleteempty"></lockingmode>
    <!--信息日志布局-->
    <layout type="log4net.layout.patternlayout">
      <param name="conversionpattern" value="日志时间:%d [%t] &lt;br&gt;%n日志级别:%-5p &lt;br&gt;%n日 志 类:%c [%x] &lt;br&gt;%n%m &lt;br&gt;%n 
" />
    </layout>
  </appender>
  <appender name="errorappender" type="log4net.appender.rollingfileappender">
    <param name="file" value="log4net\\logerror\\" />
    <param name="appendtofile" value="true" />
    <param name="maxsizerollbackups" value="100" />
    <param name="maxfilesize" value="10240" />
    <param name="staticlogfilename" value="false" />
    <param name="datepattern" value="yyyymmdd&quot;.txt&quot;" />
    <param name="rollingstyle" value="date" />
    <lockingmode type="asia.mobile.apiservice.filter.minimallockdeleteempty"></lockingmode>
    <!--错误日志布局-->
    <layout type="log4net.layout.patternlayout">
      <param name="conversionpattern" value="&lt;hr color=red&gt;%n异常时间:%d [%t] &lt;br&gt;%n异常级别:%-5p 
   &lt;br&gt;%n异 常 类:%c [%x] &lt;br&gt;%n%m &lt;br&gt;%n &lt;hr size=1&gt;" />
    </layout>
  </appender>
</log4net>

4、新增log4nethelper.cs帮助类

public class log4nethelper
    {
        public static readonly log4net.ilog loginfo = log4net.logmanager.getlogger("loginfo");
        public static readonly log4net.ilog logerror = log4net.logmanager.getlogger("logerror");

        public static void writelog(string info)
        {
            if (loginfo.isinfoenabled)
            {
                loginfo.info(info);
            }
        }

        public static void writelog(string info, exception ex)
        {
            if (logerror.iserrorenabled)
            {
                logerror.error(info, ex);
            }
        }
    }

5、新建logfilter.cs过滤器

在控制器上添加:[apilogfilterattribute]

五、swagger

1、nuget引用swashbuckle

 2、新增实现了iswaggerprovider的接口类:

在app_start文件夹中添加swaggercontrollerdescprovider.cs

/// <summary>
    /// 显示swagger控制器的描述
    /// </summary>
    public class swaggercontrollerdescprovider : iswaggerprovider
    {
        private readonly iswaggerprovider _swaggerprovider;
        private static concurrentdictionary<string, swaggerdocument> _cache = new concurrentdictionary<string, swaggerdocument>();
        private readonly string _xml;
        /// <summary>
        /// 
        /// </summary>
        /// <param name="swaggerprovider"></param>
        /// <param name="xml">xml文档路径</param>
        public swaggercontrollerdescprovider(iswaggerprovider swaggerprovider, string xml)
        {
            _swaggerprovider = swaggerprovider;
            _xml = xml;
        }

        public swaggerdocument getswagger(string rooturl, string apiversion)
        {
            var cachekey = string.format("{0}_{1}", rooturl, apiversion);
            swaggerdocument srcdoc = null;
            //只读取一次
            if (!_cache.trygetvalue(cachekey, out srcdoc))
            {
                srcdoc = _swaggerprovider.getswagger(rooturl, apiversion);

                srcdoc.vendorextensions = new dictionary<string, object> { { "controllerdesc", getcontrollerdesc() } };
                _cache.tryadd(cachekey, srcdoc);
            }
            return srcdoc;
        }

        /// <summary>
        /// 从api文档中读取控制器描述
        /// </summary>
        /// <returns>所有控制器描述</returns>
        public concurrentdictionary<string, string> getcontrollerdesc()
        {
            string xmlpath = _xml;
            concurrentdictionary<string, string> controllerdescdict = new concurrentdictionary<string, string>();
            if (file.exists(xmlpath))
            {
                xmldocument xmldoc = new xmldocument();
                xmldoc.load(xmlpath);
                string type = string.empty, path = string.empty, controllername = string.empty;

                string[] arrpath;
                int length = -1, ccount = "controller".length;
                xmlnode summarynode = null;
                foreach (xmlnode node in xmldoc.selectnodes("//member"))
                {
                    type = node.attributes["name"].value;
                    if (type.startswith("t:"))
                    {
                        //控制器
                        arrpath = type.split('.');
                        length = arrpath.length;
                        controllername = arrpath[length - 1];
                        if (controllername.endswith("controller"))
                        {
                            //获取控制器注释
                            summarynode = node.selectsinglenode("summary");
                            string key = controllername.remove(controllername.length - ccount, ccount);
                            if (summarynode != null && !string.isnullorempty(summarynode.innertext) && !controllerdescdict.containskey(key))
                            {
                                controllerdescdict.tryadd(key, summarynode.innertext.trim());
                            }
                        }
                    }
                }
            }
            return controllerdescdict;
        }
    }

3、新增swaggerconfig.js,设置成嵌入式资源

功能:1、汉化 2、界面控制器的面熟

'use strict';
window.swaggertranslator = {
    _words: [],

    translate: function () {
        var $this = this;
        $('[data-sw-translate]').each(function () {
            $(this).html($this._trytranslate($(this).html()));
            $(this).val($this._trytranslate($(this).val()));
            $(this).attr('title', $this._trytranslate($(this).attr('title')));
        });
    },

    setcontrollersummary: function () {
        $.ajax({
            type: "get",
            async: true,
            url: $("#input_baseurl").val(),
            datatype: "json",
            success: function (data) {
                var summarydict = data.controllerdesc;
                var id, controllername, strsummary;
                $("#resources_container .resource").each(function (i, item) {
                    id = $(item).attr("id");
                    if (id) {
                        controllername = id.substring(9);
                        strsummary = summarydict[controllername];
                        if (strsummary) {
                            $(item).children(".heading").children(".options").first().prepend('<li class="controller-summary" title="' + strsummary + '">' + strsummary + '</li>');
                        }
                    }
                });
            }
        });
    },
    _trytranslate: function (word) {
        return this._words[$.trim(word)] !== undefined ? this._words[$.trim(word)] : word;
    },

    learn: function (wordsmap) {
        this._words = wordsmap;
    }
};


/* jshint quotmark: double */
window.swaggertranslator.learn({
    "warning: deprecated": "警告:已过时",
    "implementation notes": "实现备注",
    "response class": "响应类",
    "status": "状态",
    "parameters": "参数",
    "parameter": "参数",
    "value": "值",
    "description": "描述",
    "parameter type": "参数类型",
    "data type": "数据类型",
    "response messages": "响应消息",
    "http status code": "http状态码",
    "reason": "原因",
    "response model": "响应模型",
    "request url": "请求url",
    "response body": "响应体",
    "response code": "响应码",
    "response headers": "响应头",
    "hide response": "隐藏响应",
    "headers": "头",
    "try it out!": "试一下!",
    "show/hide": "显示/隐藏",
    "list operations": "显示操作",
    "expand operations": "展开操作",
    "raw": "原始",
    "can't parse json.  raw result": "无法解析json. 原始结果",
    "model schema": "模型架构",
    "model": "模型",
    "apply": "应用",
    "username": "用户名",
    "password": "密码",
    "terms of service": "服务条款",
    "created by": "创建者",
    "see more at": "查看更多:",
    "contact the developer": "联系开发者",
    "api version": "api版本",
    "response content type": "响应content type",
    "fetching resource": "正在获取资源",
    "fetching resource list": "正在获取资源列表",
    "explore": "浏览",
    "show swagger petstore example apis": "显示 swagger petstore 示例 apis",
    "can't read from server.  it may not have the appropriate access-control-origin settings.": "无法从服务器读取。可能没有正确设置access-control-origin。",
    "please specify the protocol for": "请指定协议:",
    "can't read swagger json from": "无法读取swagger json于",
    "finished loading resource information. rendering swagger ui": "已加载资源信息。正在渲染swagger ui",
    "unable to read api": "无法读取api",
    "from path": "从路径",
    "server returned": "服务器返回"
});
$(function () {
    window.swaggertranslator.translate();
    window.swaggertranslator.setcontrollersummary();
});

4、配置swaggerconfig.cs

public class swaggerconfig
    {
        public static void register()
        {
            var thisassembly = typeof(swaggerconfig).assembly;

            globalconfiguration.configuration
                .enableswagger(c =>
                    {
                        c.singleapiversion("v1", "asia.mobile.apiservice");
                        //添加下述代码                        
                        var xmlfile = string.format("{0}/bin/asia.mobile.apiservice.xml", system.appdomain.currentdomain.basedirectory);
                        if (system.io.file.exists(xmlfile))
                        {
                            c.includexmlcomments(xmlfile);
                        }
                        c.resolveconflictingactions(apidescriptions => apidescriptions.first());
                        c.customprovider((defaultprovider) => new swaggercontrollerdescprovider(defaultprovider, xmlfile));
                    })
                .enableswaggerui(c =>
                    {
                        c.injectjavascript(assembly.getexecutingassembly(), "asia.mobile.apiservice.scripts.swaggerconfig.js");
                    });
        }
    }

5、配置项目的xml文档文件

 6、取消警告提示

6、分组

新增描述信息过滤器:

[attributeusage(attributetargets.class, allowmultiple = false)]
    public class controllergroupattribute : attribute
    {
        /// <summary>
        /// 当前controller所属模块 请用中文
        /// </summary>
        public string groupname { get; private set; }

        /// <summary>
        /// 当前controller用途    请用中文
        /// </summary>
        public string useage { get; private set; }

        /// <summary>
        ///  controller描述信息 构造
        /// </summary>
        /// <param name="groupname">模块名称</param>
        /// <param name="useage">当前controller用途</param>
        public controllergroupattribute(string groupname, string useage)
        {
            if (string.isnullorempty(groupname) || string.isnullorempty(useage))
            {
                throw new argumentnullexception("groupname||useage");
            }
            groupname = groupname;
            useage = useage;
        }
    }

给controller加上这个attribute,再给swaggerconfig.cs进行分组操作:

c.groupactionsby(apidesc => apidesc.getcontrollerandactionattributes<controllergroupattribute>().any() ? 
apidesc.getcontrollerandactionattributes<controllergroupattribute>().first().groupname + "_" + 
apidesc.getcontrollerandactionattributes<controllergroupattribute>().first().useage : "无模块归类");