Is WPF Dispatcher the solution of multi threading problems? - wpf

I have a very bad feeling about using lock in my code but now the Dispatcher of WindowBase exists and I want to use it everywhere.
For example I use a multi thread singleton WCF service who publish events on the EventAggregator of PRISM, the payload is immutable (it is just data) and every thread with a dispatcher can retrieve the event gracefully, whitout deadlock in their own dispatcher. (Not only UI thread, but also threads with database calls, threads with services call, threads which log or other threads with slow calls, because I don't want to freeze the UI).
But my problem is that this Dispatcher is coupled with WPF so I feel a bit guilty when I use it everywhere, I feel that the dispatcher was not created for my use case in mind.
Does it exist another Dispatcher implementation not coupled with WPF ? or that's OK to abuse it ?
Thanks,
Update
The solution that Paul Stovell give to me is to create an interface IDispatcher, and an adapter for the Wpf Dispatcher, so this will be easier to test !
This solution was good for me because, I refactored my tests and I can now use a SynchronousDispatcherAdapter in my tests (Thanks to it, I don't have to use the Dispatcher of WPF in my tests).
Using the Dispatcher instead of a BackgroundWorker make sense, because I'm using a multi publisher / subscriber pattern (with PRISM), and thanks to the Dispatcher every event handler are called on threads who subscribe them to the event. This means that the only point where multi threading issue can happen is at the payload of my event (I made him immutable).
My different threads don't communicate directly between them they can just publish and subscribe to event.
Thus, database calls, logs calls, services calls, UI calls run on different threads and don't know about each other (they only know about events they subscribe and publish).
The background worker will make sense, when I will make some calls from my UI to a repository.
But I hope to find a design without using BackgroundWorker because I prefere to use this subscriber/publisher pattern (I think it makes my code more readable)

The main issue with using the Dispatcher (or BackgroundWorker) is that it's difficult to test, unless your testing harness actually has a UI thread.
Solution 1
Use the SynchronizationContext. It provides the same ability to invoke on the UI thread and works in Windows or WPF. Testing it also possible.
Solution 2
Think of the dispatcher as being just another service. As you use PRISM, you are familiar with services and IOC. Here is how such a service may be used:
// Not a UI component
public class MyDomainService : IMyDomainService
{
private readonly IDispatcher _dispatcher;
public MyDomainService(IDispatcher dispatcher)
{
_dispatcher = dispatcher;
}
private void GotResultFromBackgroundThread()
{
_dispatcher.Dispatch(() => DoStuffOnForegroundThread());
}
}
This allows you to substitute in different implementations for your platform/testing.
Here is an example of IDispatcher, a WPF implementation and a test implementation. You would register them with your IOC container just like any other service, and they are available to both UI and other services.

yes and no.. its a rendering thing..not a threading thing per se..
The Dispatcher selects work items on a priority basis and runs each one to completion. Every UI thread must have at least one Dispatcher, and each Dispatcher can execute work items in exactly one thread. as per this this link from Microsoft.
You still have to handle on your own any threads you start yourself.
Check this one for info on: Multithreaded Programming with the Event-based Asynchronous Pattern
Personally I use the Background Worker for my threading needs.
Best Practices here.

I'm going to necro the heck out of this, but this sounds like a bad idea. What you are saying is that you need a queue for your publisher to dump items on for its subscribers. A Dispatcher, at its core, is just a glorified queue, with a LOT of overhead around it. The overhead is specifically for protecting access to UI resources, which you aren't using. That suggests it's the wrong thing to use.
The person who suggested a SynchronizationContext is on a good path. This accomplishes what you want (safely marshalling data to another thread), without tying you to a UI concept. You could write an extension method which marshals your event to the SynchronizationContext requested by each subscriber of the event (it is available by casting the Target of your subscribing Delegate to ISynchronizeInvoke. The result of that cast will allow you to know if it needs to be marhalled, and can do it automatically for you.
Even better would be to just use a queue with appropriate locking semantics. The overhead of the lock is unlikely to be an issue, and if it is, your use of the Dispatcher would be far more destructive than a simple lock. In this case, simpler is better. They key would be to only keep the lock to add/remove an item from the queue. Your subscribers should perform whatever work they do outside of the lock.

Related

Why does Silverlight Add Service Ref. use eventing instead of IAsyncResult?

Ye Olde Add Web Reference generates XXXAsync calls to services that use eventing to inform the caller that the call had completed.
Add Service Reference in something like a WPF or console app, when told to generate async operations, uses the IAsyncResult design pattern (BeginXXX and EndXXX operations). My understanding is that this was generally regarded as a step forward in usability and flexibility - you can use a callback, you can begin blocking at any point in time simply by calling EndXXX, you can group wait handles and block on a set of operations, you can poll, etc.
Why doesn't ASR in Silverlight use IAsyncResult? My guess is because the designers wanted to make it very clear that full asynchronicity is in fact required, and if they had used the IAsyncResult design pattern, it would have been too easy to try just call Begin immediately followed by End, which would have made for a stumbling block that would have been hit by roughly 100% of new devs or people who didn't have a good grasp of async.
The Silverlight team provided immediate access to the event based async pattern because it's an easier to use approach (but a lot less flexible). For example, the event is fired in the display thread, allowing developpers unwilling to think about their thread model to forget about it.
If you need better flexibility (as me), the Begin/End async pattern is available for Silverlight too. In fact the event based generated code is based upon the IAsyncResult one.
Your generated Channel interface defines the begin/end methods, and you can use the channel factory to obtain an usable implementation of the interface.
From MSDN:
Usually, the event-based asynchronous model described previously raises the completion event on the same thread on which the service was called. This is convenient in many applications, because you often invoke services from the UI (User Interface) thread, and can update UI components (such as text boxes in our example) directly in the completion event handler.
Occasionally, you may want the completion event to be processed on a background thread. Either for this or for other reasons, you may want to use an alternative asynchronous invocation model based on the IAsyncResult mechanism and on Begin/End methods.
To use this model, you must first cast the proxy to an appropriate interface type. The interface type is generated automatically alongside the proxy by the Add Service Reference tool. You can then invoke the appropriate Begin method.
CopyIAsyncResult iar = ((CustomerService)proxy).BeginGetUser(userId, GetUserCallback, proxy);
Thanks to Kimberly for the MSDN link.

Generic timer that works in both WinForms and other apps

I need to write a library class that performs timing operations, and raises a tick event periodically. I need this library to be usable from both WinForms and non-WinForms applications.
The problem is that the threading model is quite different for different types of applications. WinForms apps even have their own dedicated timers, but I don;t know in advance what type of app will be calling me.
Is there an established pattern for safely raising a timer event without prior knowledge of the type of app (WinForms, WPF, Silverlight, ASP.NET, etc.) that will use it?
Is there an established pattern for safely raising a timer event without prior knowledge of the type of app (WinForms, WPF, Silverlight, ASP.NET, etc.) that will use it?
There are timers that are platform neutral in the framework: System.Threading.Timer and System.Timers.Timer. However, these will both require you to handle the marshaling back to your synchronization context, as they raise their events on a threadpool thread.
You could provide this marshaling in a generic way - ie: make a "timer" class that wraps one of the above, taking a SynchronizationContext as an argument. When the timer's Tick event occurs, you could Post the data back to the context. This is, effectively, what the Windows Forms timer does.
You'd then just create it in your UI thread and pass SynchronizationContext.Current to the "new timer" class. This would work for Windows Forms, WCF, WPF, Silverlight, etc - as they all setup a SynchronizationContext on their "main" thread.

Approach to loading forms and busy indicator

I am "slowly" moving into Silverlight from asp.net and have a question about how to deal with situation where some code needs to be executed after web service calls have completed. For example, when user clicks on the row in the data grid a dialog box is shown that allows editing of the record. It contains numerous combo boxes, check boxes etc. So I need to first load data for each of the combo boxes, and than when all finished loading, I need to set the bound entity. Since I am new to this async thing, I was thinking to have some kind of counter that will keep track on how many calls have been dispatched, and as they finish reduce them by one, until it is zero, at which point I could raise an event that load has finished, and I could proceed with what ever is dependent on this. But this seems very clunky way of doing it. I am sure many have faced this issue, so how do you do this. If it helps, we use Prism with MVVM approach and Ria Services with Dtos.
What you've described is pretty much the way to go. There may be more elegant things you can do with locks and mutexes, but your counter will work. It has the bonus that you can see how many operations are still "in progress" at any one time.
You could dispatch your events sequentially but that would defeat the whole purpose of asynchronous operations.
If you analysed what each part of your UI needs you might be able to do some operations before all of your async events have finished. Making sure you start the longest running operations first might help - but there's no guarantee that the other shorter operations will finish first. It all depends on what resources are available on both the client and server at the time the call is made.

Silverlight Threading and its usage

Scenario : I am working on LOB application, as in silverlight every call to service is Async so automatically UI is not blocked when the request is processed at server side.
Silverlight also supports threading as per my understanding if you are developing LOB application threads are most useful when you need to do some IO operation but as i am not using OOB application it is not possible to access client resource and for all server request it is by default Async.
In above scenario is there any usage of Threading or can anyone provide some good example where by using threading we can improve performance.
I have tried to search a lot on this topic but everywhere i have identified some simple threading example from which it is very difficult to understand the real benefit.
Thanks for help
Tomasz Janczuk has also pointed out that if the UI thread is fairly busy, you can significantly improve the performance even of async WCF calls by marshaling them onto a separate thread. And I should note that the UI thread can get awfully busy doing things that you wouldn't anticipate would chew up cycles, like calculating drop-shadows and what-not, so this might be worth investigating (and measuring) for your application.
That said, I've been writing LOB apps for the better part of two decades, and synchronous IO aside, I haven't found a lot of scenarios where adding multiple threads in an LOB application was worth the additional complexity.
Edit 4/2/10: I had lunch with Tomasz Janczuk and some other folks from the WCF team the other day, and they clarified a few issues for me about how WCF works with Silverlight background threads. There are two things to be concerned with: sending data, and receiving it (say, from duplex callbacks or async call completions). When you send data, the call will always be made from the thread that actually makes the call. So if you have a lot of data that needs to be serialized, you might get a small performance boost by marshaling the outgoing call onto a background thread (say, by using ThreadPool.QueueUserWorkItem). But it's not likely to be a substantial performance boost.
However, when you receive data, either through a duplex callback, or through an async xxxCompleted method, the data is always received on the thread on which the connection was originally opened. This means that if you're opening the connection explicitly, it will receive data on that thread; but if you're opening the connection implicitly, it will receive data on the thread on which you made your first outbound connection. This won't make a lot of difference if you need to update the UI on every callback, since you'd just have to marshal the call back onto the UI thread. But if there are times when you just need to store the data for future reference or processing, you can get yourself a significant performance boost by opening your connection on a separate thread, so that you can receive and process callbacks without waiting on the UI thread.
Hope this helps. Thought I'd write it down while I still have it reasonably fresh in my head.
The same advantages apply to Silverlight as to other applications. If your are doing a long running calculation on the client and don't want to tie up the main/ui thread, then threading is an obvious choice.
Also, I haven't researched it, but I would imagine if you are running a multi-core machine, you could improve performance by splitting work into multiple separate threads.

Asynchronously populate datagridview in Windows Forms application

howzit!
I'm a web developer that has been recently requested to develop a Windows forms application, so please bear with me (or dont laugh!) if my question is a bit elementary.
After many sessions with my client, we eventually decided on an interface that contains a tabcontrol with 5 tabs. Each tab has a datagridview that may eventually hold up to 25,000 rows of data (with about 6 columns each). I have successfully managed to bind the grids when the tab page is loaded and it works fine for a few records, but the UI freezes when I bound the grid with 20,000 dummy records. The "freeze" occurs when I click on the tab itself, and the UI only frees up (and the tab page is rendered) once the bind is complete.
I communicated this to the client and mentioned the option of paging for each grid, but she is adament w.r.t. NOT wanting this. My only option then is to look for some asynchronous method of doing this in the background. I don't know much about threading in windows forms, but I know that I can use the BackgroundWorker control to achieve this. My only issue after reading up a bit on it is that it is ideally used for "long-running" tasks and I/O operations.
My questions:
How does one determine a long-running task?
How does one NOT MISUSE the BackgroundWorker control, ie. is there a general guideline to follow when using this? (I understand that opening/spawning multiple threads may be undesirable in certain instances)
Most importantly: How can I achieve (asychronously) binding of the datagridview after the tab page - and all its child controls - loads.
Thank you for reading this (ahem) lengthy query, and I highly appreciate any responses/thoughts/directions on this matter!
Cheers!
There's no hard and fast rule for determining a long-running task. It's something you have to know as a developer. You have to understand the nature of your data and your architecture. For example, if you expect to fetch some info from a desktop database with a single user from a table that contains a couple dozen rows you might not even bother showing a wait cursor. But if you're fetching hundreds of rows of data across a network to a shared database sever then you'd better expect that it will potentially be a long-running task to be handled not simply with a wait cursor but a thread that frees up your UI for the duration of the fetch. (You're definitely on the right track here.)
BackgroundWorker is a quick and dirty way of handling threading in forms. In your case, it will very much tie the fetching of data to the user interface. It is doable, works fine but certainly is not considered "best practice" for threading, OOP, separation of concerns etc. And if you're worried about abusing the alocation of threads you might want to read up on the ThreadPool.
Here's a nice example of using asynchronous threading with the thread pool. To do data binding, you fetch your data in the thread and when you get your callback, simply assign the result set to the the grid view's datasource property.

Resources