Tuesday, August 21, 2007

Hosting WCF in WPF app

In an application that I am developing, I have encountered a problem when the WPF GUI freezes when a client access the services in the server. Both client and server are WPF applications and the service operations typically takes several seconds to complete. So, the server GUI became unresponsive when the client performs service operation calls to the server. After some investigation, I found that the default behavior for WCF is to use the default synchronization context for the current AppDomain for synchronizing client access. Thus, when it is hosted in a GUI application, it locks the UI thread too.

To disable this behavior, I have disable the UseSynchonizationContext switch in the ServiceBehavior attribute of the service implementation class.

[ServiceContract]
public interface IMyService
{
[OperationContract]
void DoSomething();
}

[ServiceBehavior(
UseSynchonizationContext = false)]
public class MyServiceImpl : IMyService
{
public void DoSomething()
{
...
}
}


Unfortunately, setting this flag to false also means I have to be extra careful with the golden rule of GUI and multithreading programming:

"Thou shalt only update UI using code that runs on the same thread as the UI."

Disabling UseSynchonizationContext causes WCF to process incoming client request using background thread. Thus, if we need to update the UI during the service operation execution, I'll need to use Dispatcher.BeginInvoke to marshal the call to the UI dispatcher thread to perform the UI update operations. For more information on multithreading and GUI, see this article from WPF SDK blog:
Thou Shalt Not Break the Golden Rule of Windows Multithreading. Or, Why the Dispatcher Rocks.

No comments: