11

Every so often I find that I have accidentally broken data binding in my application. Either by renaming a property and not renaming it in the XAML or by a property throwing an exception for some reason.

By default data binding errors are logged to debug output and exceptions that are thrown are caught and suppressed.

Is there an easy way to have an exception thrown after the debug output is logged?

I want to know as soon as possible if data binding is broken (ideally picking it up in an automated test) and not risk the chance that it might go unnoticed until tested by a human.

Ashley Davis
  • 9,896
  • 7
  • 69
  • 87

4 Answers4

12

After some procrastination I finally set about coding a solution to my original issue.

My solution uses a custom TraceListener (originally suggested by John) that logs to an output window. The output window is automatically displayed and bought to the foreground when an error occurs.

Here is my TraceListener:

public class ErrorLogTraceListener : TraceListener
{
    public override void Write(string message)
    {
        ...
    }

    public override void WriteLine(string message)
    {
        ...
    }
}

TraceListener is defined in System.Diagnostics.

The custom TraceListener must be hooked into the system to be used. The official way to do this is to set something in the registry and then use the App.config file to configure the TraceListener.

However I found that there is a much easier way to do this programmatically:

ErrorLogTraceListener listener = new ErrorLogTraceListener();
PresentationTraceSources.Refresh();

PresentationTraceSources.DataBindingSource.Listeners.Add(listener);
PresentationTraceSources.DataBindingSource.Switch.Level = SourceLevels.Error;

PresentationTraceSources is also defined in System.Diagnostics.

For more information on trace sources see Mike Hillberg's blog.

Bea Stollnitz has some useful info on her blog.

STiLeTT
  • 1,023
  • 10
  • 23
Ashley Davis
  • 9,896
  • 7
  • 69
  • 87
  • 1
    I found that this only catches errors when the debugger is attached. When the debugger is not attached then WPF doesn't emit the errors in the first place.. (?) Has anyone else experienced this? – pauldoo Nov 18 '10 at 15:50
  • 1
    On further investigation it's just the flushing behaviour that is altered when the debugger is attached. Use `System.Diagnostics.Trace.AutoFlush = true;` fixed our problem. – pauldoo Nov 18 '10 at 16:37
  • 2
    For a full example: http://www.jasonbock.net/jb/Default.aspx?blog=entry.0f221e047de740ee90722b248933a28d – Thomas Dec 04 '10 at 05:20
  • Be aware that the call to Refresh() removes the default listeners, if not explicitly defined in app.config. I got confused myself with this when I didn't see any binding errors in the output window after returning to the project a few months later. – Anttu Jan 25 '13 at 11:08
2

Have a look at this blog article which may help get around this issue.

Ryan_S
  • 304
  • 3
  • 10
John
  • 29,788
  • 18
  • 89
  • 130
  • This is a good article about debugging problems with data bindings. But it depends on you having detected the problems in the first place right? This isn't really the answer I was after. What I want (if it is possible) is a concise description of how to make data-binding problems stand-out more in the first place. – Ashley Davis Apr 23 '09 at 08:22
  • You could create a custom trace listener that throws exceptions – John Apr 23 '09 at 10:27
0

Raising binding exceptions in WPF & Silverlight with .net 4.0 Dynamics.

Ryan_S
  • 304
  • 3
  • 10
CompareTheMooCat
  • 1,047
  • 2
  • 10
  • 14
0

I implemented a solution very similar to the accepted answer:

  1. Derived a TraceListener that throws instead of logging
  2. Added that listener to PresentationTraceSources.DataBindingSource

Please see the complete solution on GitHub, it includes a demo application and a unit test project.

Exception in Visual Studio

Benoit Blanchon
  • 13,364
  • 4
  • 73
  • 81