3

I need to use WCF tracing in my application but it needs to be controlled from code as much as possible.

IT was suggested that I install the following sections in my app.config file:

<configuration>
  <system.serviceModel>
    <diagnostics>
      <messageLogging
        maxMessagesToLog="100"
        logEntireMessage="true"
        logMessagesAtServiceLevel="true"
        logMalformedMessages="true"
        logMessagesAtTransportLevel="true">
      </messageLogging>
    </diagnostics>
  </system.serviceModel>  
  <system.diagnostics>
    <sources>
      <source name="System.ServiceModel" >
        <listeners>
          <add type="System.Diagnostics.DefaultTraceListener" name="dummy"/>
        </listeners>
      </source>
    </sources>
  </system.diagnostics>
</configuration>

Then the following code could be used to get the trace running as needed:

BindingFlags privateMember = BindingFlags.NonPublic | BindingFlags.Instance;
BindingFlags privateStaticMember = privateMember | BindingFlags.Static;

Type type = Type.GetType("System.ServiceModel.DiagnosticUtility, System.ServiceModel, Version=3.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089");
MethodInfo[] mi = type.GetMethods(privateStaticMember);

// invoke InitializeTracing   
object diagnosticTrace = mi.FirstOrDefault(e => e.Name == "InitializeTracing").Invoke(null, null);
if (diagnosticTrace != null)
{
    // get TraceSource   
    Type type2 = Type.GetType("System.ServiceModel.Diagnostics.DiagnosticTrace, SMDiagnostics, Version=3.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089");
    PropertyInfo pi = type2.GetProperty("TraceSource", privateMember);
    TraceSource traceSource = pi.GetValue(diagnosticTrace, null) as TraceSource;

    // clear all listeners in the trace source   
    traceSource.Listeners.Clear();

    // add listener to trace source   
    XmlWriterTraceListener listener = new XmlWriterTraceListener("mylogfile".svclog");
    listener.TraceOutputOptions = TraceOptions.Timestamp | TraceOptions.Callstack;
    traceSource.Attributes["propagateActivity"] = "true";
    traceSource.Switch.ShouldTrace(TraceEventType.Verbose | TraceEventType.Start);
    traceSource.Listeners.Add(listener);

    // enable tracing   
    type.GetProperty("Level", privateStaticMember).SetValue(null, SourceLevels.All, null);

    Trace.AutoFlush = true;

This works fine up to a point, the main problem being that the messagelogging settings in the system.servicemodel section of the app.config file are being ignored.

Is there anything that can be done to solve this problem?

John Saunders
  • 160,644
  • 26
  • 247
  • 397
BillK
  • 31
  • 1
  • 2

2 Answers2

0

I can't comment on all of your code because I have not used System.Diagnostics in this way before (programmatically configuring the WCF communication tracing), but if your intent on this line:

traceSource.Switch.ShouldTrace(TraceEventType.Verbose | TraceEventType.Start);

Is to set the level of tracing that you want, I think that you should be using the Switch.Level property instead. ShouldTrace is for asking if a given TraceSource would trace, given the input flags.

traceSource.Switch.Level = SourceLevels.Verbose | SourceLevels.ActivityTracing; 

Note that according to this link, it is possible to configure apparently reasonable settings and yet the activity id might not be propogated correctly. Read it carefully. It may or not apply to your situation.

wageoghe
  • 27,390
  • 13
  • 88
  • 116
  • This doesn't seem to help very much. Perhaps I didn't make it clear earlier, but the basic tracing itself is working. But I am only seeing the headers and the other messagelogging settings in the app.config file are definitely being ignored. – BillK Nov 17 '10 at 00:40
-1
  1. You need to enable MessageLogging by defining a trace source as indicated in this MSDN Library page. So, you need this extra bit in your app.config in the sources section:

    <source name="System.ServiceModel.MessageLogging">
       <listeners>
         <add type="System.Diagnostics.DefaultTraceListener" name="dummy"/>
      <remove name="Default" />
    </listeners>      </source>
    

The message logging settings don't apply to the System.ServiceModel trace source.

Erikest
  • 4,997
  • 2
  • 25
  • 37