使用NLog记录HTTP请求

时间:2013-10-03 08:54:53

标签: .net asp.net-mvc logging asp.net-web-api nlog

如何使用 NLog 完全记录 HTTP请求

以下是 Fiddler 抓住它的方式,我需要这样的内容:

POST http://localhost/api/places/add HTTP/1.1
User-Agent: Fiddler
Host: localhost
Authorization: 375DF933413
Content-Length: 78
Content-Type: application/json

{ "location": { "lon": 35.005577, "lat": 48.435533}, "name": "n1" } 

我认为应该可以编写一些“神奇的”NLog布局表达式。

2 个答案:

答案 0 :(得分:1)

我正在使用ActionFilterAttribute来实现类似的目标:

public class LogHttpRequest : ActionFilterAttribute
{
    private readonly Logger _log = LogManager.GetCurrentClassLogger();

    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        var request = filterContext.HttpContext.Request;
        var sb = new StringBuilder();

        sb.Append(request.RequestType + " " + request.Url + "\n");

        var parsed = HttpUtility.ParseQueryString(request.Headers.ToString());

        foreach (string key in parsed)
        {
            sb.Append(key + ": " + parsed[key] + "\n");
        }

        var inputStream = request.InputStream;
        inputStream.Position = 0;

        using (var reader = new StreamReader(inputStream))
        {
            var body = reader.ReadToEnd();
            sb.Append("\n" + body);
        }

        _log.Log(LogLevel.Info, sb.ToString());

        base.OnActionExecuting(filterContext);
    }
}

如果您真的想使用NLog布局表达式,可以在ActionFilter中执行类似的操作:

var logEventInfo = new LogEventInfo(LogLevel.Info, null, null);
var parsed = HttpUtility.ParseQueryString(request.Headers.ToString());

foreach (string key in parsed)
{
    logEventInfo.Properties.Add(key, parsed[key]);
}

var inputStream = request.InputStream;
inputStream.Position = 0;

using (var reader = new StreamReader(inputStream))
{
    var body = reader.ReadToEnd();
    logEventInfo.Properties.Add("Body", body);
}

_log.Log(logEventInfo);

然后在您的NLog布局中,您可以访问这些属性 ${event-context:item=Key}其中Key是要包含在输出中的标题名称。

答案 1 :(得分:1)

一种简单的方法:

public class LogHttpRequestAttribute : ActionFilterAttribute
{
    private static Logger _logger = LogManager.GetCurrentClassLogger();

    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        _logger.Debug("action executing");

        base.OnActionExecuting(filterContext);
    }
}

用法:

protected void Application_Start()
{
    AreaRegistration.RegisterAllAreas();

    // Register global filter
    GlobalFilters.Filters.Add(new LogHttpRequestAttribute ());


}

要记录该网址,请在配置中使用${aspnet-request:serverVariable=HTTP_URL},请参阅wiki。为这些布局渲染器安装NLog.Web。

请参阅NLog Wiki