【问题标题】:System.Diagnostics - Eventsource with empty messageSystem.Diagnostics - 带有空消息的事件源
【发布时间】:2016-01-16 07:58:33
【问题描述】:

我正在使用 System.Diagnostics 使用 EventSource 获取一些消息,并将它们作为日志进行跟踪。似乎缺少一些信息,例如 EventMessage 和 Message(它们是空的),而 EventId 和 Level 设置正确。 WriteEvent 方法是正确的(传递给每个事件方法的参数的数量和类型与传递给 WriteEvent() 的参数完全匹配)。 特别是,我在 ServiceFabric 群集上使用 WAD 来收集 Azure 表存储上的跟踪。 有什么想法吗?

谢谢!

【问题讨论】:

  • 有什么更新吗?您是否尝试通过 Perfview 将事件记录到 ETL 中?

标签: events logging trace system.diagnostics etw-eventsource


【解决方案1】:

Event 的参数必须与您调用的方法的参数匹配。 Eventsource 根据方法的参数构建清单。

事件方法必须与它调用的 WriteEvent 重载的类型完全匹配,特别是您应该避免隐式标量转换;它们很危险因为清单是根据 ETW 事件方法的签名生成的,但传递给 ETW 的值是基于 WriteEvent 重载的签名。

【讨论】:

  • 我做到了,我传递了相同类型的确切数量的参数。
  • 试试 NuGet 版本的 Eventsource
  • 我正在尝试,但似乎并未处理所有消息。 WAD 或 EventSource 会不会只发送按特定关键字或特定级别分类的事件?
  • 我只通过WPR.exe将数据收集到ETL文件中,所以不知道其他收集工具是否有问题。
  • 这似乎取决于进程正在运行哪些机器:如果我通过分区到不同机器的同一应用程序在 5 台机器上收集数据,只有在重新启动后它似乎才能工作。
【解决方案2】:

自从我们升级到任何高于 4.5.2 的 .NET Framework 版本后,我就遇到了这个问题。我终于弄清楚了我的问题,希望这对你也有帮助。我知道这是一篇旧帖子,但也许它也会对其他人有所帮助。

Windows 事件跟踪 (ETW) 似乎可以处理错误,而您获得的唯一指示就是您看到的记录消息为空的位置。我正在使用从 IEventTextFormatter 派生的自定义格式化程序。 (EventData.FormattedMessage 为空)。在此方法中设置断点显示 EventData.FormattedMessage 为空。我还在 Visual Studio 的输出/调试窗口中注意到以下消息:

The parameters to the Event method do not match the parameters to the WriteEvent method. This may cause the event to be displayed incorrectly.
EventSourceException while processing event "WriteLogDefault": System.IndexOutOfRangeException:Index was outside the bounds of the array.
A first chance exception of type 'System.NullReferenceException' occurred in NEAM.App.ProfileDataMart.BL.dll

我将我的问题追溯到以下方法:

[Event(1, Message = "{2}", Level = EventLevel.Informational, Keywords = Keywords.Informational)]
private void WriteLogDefault(int p_EventId, string p_AssemblyName, int p_Key, string p_Message)
{
    WriteEvent(p_EventId, p_AssemblyName, p_Key, p_Message);
}

根据MSDN 上的文档中的注释,对WriteEvent 的调用应包括EventId,后跟传递给您的方法的所有参数。显然,上述代码在 .NET Framework 4.5.2 或更早版本中没有引发任何异常。

当您在 EventSource 派生类中实现被标识为 ETW 事件的方法时。您必须调用基类 WriteEvent 方法,传递 EventId 和与实现方法相同的参数。

我的代码现在看起来像这样并且可以按预期工作。祝你好运!

    [Event(1, Message = "{2}", Level = EventLevel.Informational, Keywords = Keywords.Informational)]
    public void WriteLogDefault(string p_AssemblyName, int p_Key, string p_Message)
    {
        WriteEvent(1, p_AssemblyName, p_Key, p_Message);
    }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-11-06
    • 1970-01-01
    • 1970-01-01
    • 2010-09-20
    • 2011-10-11
    • 2017-03-29
    • 2015-10-02
    相关资源
    最近更新 更多