In my library, I use a SynchronizationContext to enable me easily to raise events on the GUI thread whether the library is being used in a Windows Forms or WPF app. If my class was created on a background thread, the SynchronizationContext is null, so I raise the event directly.
For example:
private void RaisePlaybackStoppedEvent()
{
EventHandler handler = PlaybackStopped;
if (handler != null)
{
if (this.syncContext == null)
{
handler(this, EventArgs.Empty);
}
else
{
this.syncContext.Post(state => handler(this, EventArgs.Empty), null);
}
}
}
This works fine, except that I have had user reports that it goes wrong in ASP.NET applications:
System.NullReferenceException was unhandled
Message=Object reference not set to an instance of an object.
Source=System.Web
StackTrace:
at System.Web.HttpApplication.ThreadContext.Enter(Boolean setImpersonationContext)
at System.Web.HttpApplication.OnThreadEnterPrivate(Boolean setImpersonationContext)
at System.Web.AspNetSynchronizationContext.CallCallbackPossiblyUnderLock(SendOrPostCallback callback, Object state)
at System.Web.AspNetSynchronizationContext.CallCallback(SendOrPostCallback callback, Object state)
at System.Web.AspNetSynchronizationContext.Post(SendOrPostCallback callback, Object state)
I had assumed that SynchronizationContext
would be null in an ASP.NET website. I need a way to not use the SynchronizationContext if it is an instance of AspNetSynchronizationContext, although to do this would be rather hacky as I have no reference to System.Web and it isn't a publicly visible type anyway.
My question is, what is the best way to determine whether I am in an application with a GUI (e.g. WinForms, WPF, WinRT), and only use SynchronizationContext in that setting?