I need to initialize few objects, it can take a while so I want to do it in some background thread. I also want to display progressBar showing what is the progress of initialization.
What is the most elegant way to do it?
I was thinking about an interface:
interface ILoadable
{
int Progress { get; }
event EventHandler Loaded;
}
Why not just use a BackgroundWorker directly? It provides events for DoWork, ProgressChanged, and RunWorkerCompleted.
The advantage of this (or a thin wrapper over this) is that you automatically get the threading handled for you, properly, and it's very well tested.
If you want to make a wrapper around this, I'd actually recommend making yourself an abstract class that encapsulates the BackgroundWorker, and lets you provide Action delegates for the run operation.
Related
From the Progress<T> Class reference page:
Any handler provided to the constructor or event handlers registered with the ProgressChanged event are invoked through a SynchronizationContext instance captured when the instance is constructed. If there is no current SynchronizationContext at the time of construction, the callbacks will be invoked on the ThreadPool.
I'm creating a Progress<int> on a background thread. I want the callbacks, and any associated cancellations (throwing an OperationCancelledException), to occur on the same thread.
At the time of constructing the Progress<int> object, SynchronizationContext.Current is null.
And so, as the above documentation tells me, the callbacks are being executed on the Thread Pool...
Questions
Is it possible to do anything about the fact that the current SynchronizationContext is null? For example, create one for the current thread?
If that is possible, would the Progress<T> capture that SynchronizationContext?
If that is possible, would that reliably mean that the callbacks are executed on the same thread? As, I've read in other places, such as this SO answer, that:
...a SynchronizationContext does not necessarily represent a specific thread; it can also forward invocation of the delegates passed to it to any of several threads (e.g. to a ThreadPool worker thread)...
Solution/workaround
To make sure that callbacks are happening on the same thread, I'm using my own implementation of the IProgress<T> interface:
public class SynchronousProgress<T> : IProgress<T>
{
private readonly Action<T> action;
public SynchronousProgress(Action<T> action)
{
this.action = action;
}
public void Report(T value)
{
action(value);
}
}
It works. However, I'm still wondering if there is a way to achieve this with the .NET Progress<T> class?
Update: background information
The attempted usage of the Progress<T> class sits inside a custom, cancellable progress dialog, which encapsulates doing some work and reporting progress. In this case, the work (that can be cancelled) is occuring on the other side of a plugin boundary. It's desirable to use a .NET type (e.g. IProgress<T>) in the plugin interface for communicating progress, rather than a custom type (e.g. our own, (older) IProgress type).
The callback being given to the .NET IProgress<T> implementation, is simply an instruction to increment the progress of the custom IProgress implementation. Along the lines of:
public void Export(CulturedStreamWriter writer, IProgress progress) // that's a custom IProgress
{
progress.Steps = toExport.Count;
exporter.Export(toExport, writer, new SynchronousProgress<int>(progress.StepTo)); // increment the progress of the custom IProgress
}
Using the .NET Progress<T> in place of the SynchronousProgress<T> does not work, as cancellation exceptions are being thrown on a different thread to this code, which is where they need to be caught.
Seems as the custom implementation of the .NET IProgress<T> is working (SynchronousProgress<T>), perhaps it is in fact the most appropriate approach (given the surrounding code/constraints).
You can set SynchronizationContext.Current before constructing the instance to a value of your choice. Reset it afterwards (with a finally block to make sure you don't permanently mess up the thread).
This is a bit ugly. WebClient requires the same thing (unrelated to this question - just an example). I find it an API omission in Progress<T> that you can't provide the sync context. You could consider opening an issue on GitHub as a public service.
If you want to can just fork the source code of Progress<T> and add a constructor argument for the sync context. It's a small, self-contained class.
If that is possible, would that reliably mean that the callbacks are executed on the same thread?
They would run wherever that sync context chooses to run them. Depends on the context.
Your own implementation really just runs the callback right now which seems pointless. This IProgress implementation behaves just like an event that does not know anything about threads. It will not target any thread in particular. I doubt this is what you need although I can't be sure.
I want to achieve something life below -
My application will start UI Module, from UI module I will initiate core module. Core module will keep on running on different thread. On specific action in core module, I want to raise and event which will be subscribed by UI module.
Basically, I want to send specific enum information to UI module.
Please suggest me a model for it. I am trying to achieve it.
Will both module run with any blocking in this model?
Thanks in advance
You can use the Progress class with the IProgress interface to do exactly this.
In your UI context create a Progress object with a generic argument of whatever data you need to pass.
Subscribe to it's event to do whatever you want to do when the background task updates you.
Have the background task accept an object of type IProgress (which Progress implements) and have it periodically Report with the relevant data.
The ProgressChanged event will be fired whenever Report is called, and the Progress object will capture the current synchronization context of where it was created, which is a fancy way of saying that the event will be fired in the UI thread.
I would recommend using the BackgroundWorker Class
Checkout this tutorial
http://www.dotnetperls.com/backgroundworker
Class reference
http://msdn.microsoft.com/en-us/library/system.componentmodel.backgroundworker.aspx
Here how it goes in simple ways:
Open your UI form (design view)
Add a backgroundworker control on your UI form
Open the properties pane and switch to events (lightning bolt icon)
Double click on dowork and runworkercompleted events (this will generate event handlers)
Go to the event handlers (in code)
Now write your processing code in dowork handler and add the result you want to send to your ui module like so e.Result = your_enum (or any other Object);
Next come to the runworkercompleted handler and typecast the RunWorkerCompletedEventArgs e (RunWorkerCompletedEventArgs object) to your enum (or object you returned from the dowork handler) and use it in UI as needed.
Finally do not forget to initiate the backgroundworker : backgroundWorker1.RunWorkerAsync() from your UI mdoule
Remark: If you need to report progress periodically use the ReportProgress method of BackgroundWorker class. There are two overloads for this method:
1) http://msdn.microsoft.com/en-us/library/ka89zff4.aspx
2) http://msdn.microsoft.com/en-us/library/a3zbdb1t.aspx
The first one allows to report only the progress percentage and the second one you can use to pass in any object also if you will
This should be pretty easy to do with either the System.Threading.Thread or BackgroundWorker or Task class. You can use either of those to run code on another thread.
When you need to notify the UI, just raise an event. To build events, take a look here:
How can I make my own event in C#?
Then you just need to make sure to call Invoke to make sure that you execute the final UI update code on the correct thread. For that, take a look at this:
Thread Control.Invoke
Sounds like a classic use of the Mediator pattern to me. The Mediator allows disconnected components to talk to each other.
I just happen to have a copy of this in my own MVVM framework, which you can grab from here :
http://cinch.codeplex.com/SourceControl/changeset/view/70832#796984
Also grab this
http://cinch.codeplex.com/SourceControl/changeset/view/70832#797008
My implementation allows you to do it using WeakReference so no strong references are held. Its also allows subscribers to hook up methods to listen to certain events using attributes, and publishers to broadcast a new messaage of T.
Publisher/Subscriber simply register with Mediator
//done by both subscriber and publisher
Mediator.Instance.Register(this);
//Subscriber
[MediatorMessageSinkAttribute("DoBackgroundCheck")]
void OnBackgroundCheck(string someValue) { ... }
//publisher might typically do this
mediator.NotifyColleagues("DoBackgroundCheck", "Nice message");
You may need to use your own SynchronizationContext when subscriber gets message (WPF / Winforms have pre built ones of these) to dispatch call to correct thread.
I also allow for synchronise/aysynchronise calls
I'm jusing Jurassic javascript compiler to run javascript in my C# application. Now, jurassic isn't thread-safe, and I call functions (in javascript) from threads all over the place, which I figured wasn't that smart. What I could do was ofcause just to create a simple lock on the javscript-engine, however, what I want is a programming model similar to the one you have when working with a GUI thread in WPF or WinForms. So, I spawned a thread, and created my javascript-engine inside that thread, and what I would like is that no other threads are allowed to edit the objects created in that thread (which will just be the javascript-engine and all the js-objectes). And then, to call js-code from other thread I'd like to use a dispatcher, or something similar, to make the js-thread run the code.
Is this possible in C#?
It doesn't quite answer your question but you may want to take a look at this MSDN article. It talks about the approach that WPF took with their objects and the Dispatcher model, as well as the Dispatcher, DispatcherObject and DispatcherSynchronizationContext classes.
What they recommend for individual objects is to inherit from DispatcherObject (which may not be feasible for your situation) and call the inherited VerifyAccess() method on public access.
public class ThreadOwnedObject : DispatcherObject
{
private string field;
public string ExposedProperty
{
get { return field; }
set
{
VerifyAccess();
field = value;
}
}
}
And the invocation would use the inbuilt Dispatcher.
ThreadOwnedObject ownedInstance = new ThreadOwnedObject();
ownedInstance.Dispatcher.Invoke(new Action(() => ownedInstance.ExposedProperty = "foo"));
Alternately, if that or the DispatcherSynchronizationContext in the article doesn't fit your needs, I imagine that you could probably create a mechanism that mimics the DispatcherObject by holding onto the Thread.CurrentThread.ManagedThreadId when an object is created and perform checks against that value for every exposed access. Beyond that or an equivalent, I don't think that there's a built-in mechanism that will associate a random object with a given thread.
I'm not quite sure what you are asking, but I'll try to help anyway.
Can you use a semaphore to lock the thread running the javascript engine? Even if you don't use the Semaphore class, you could use a boolean or "lock" keyword to protect the code block with the executing engine. The objects produced by that thread could be hidden by the class with the engine until you are ready. You could also expose a method in that class that would allow code injection or object fetching from behind the protected code.
In my WPF try to separate my classes logic from any interface related data and only supply ObservableCollection properties for binding.
Problem is, when I access those binded OCs from other threads, I am required to do so through the dispatcher. The result is that I am required to add many Dispatcher.Invoke() calls, hidden inside my classes, whenever one of the methods attempts to update the OCs.
How can I do that in a more clean and separated way, so the dispatcher calls be abstracted away from my methods?
I don't have a silver bullet. But if you are certain and ready to take the responsibility of implicit UI delegation, you can always inherit from ObservableCollection, override methods and dispatch all requests to UI.
But the following code makes me scary:
// somewhere in thread pool:
for(int i = 0; i < 1000; i++)
{
_dispatcherAwareCollection.Add(i);
}
It seems innocent, but under the hood it blocks calling thread 1000 times. Alternatives might be your specific BulkXXX() methods, that will delay notification until all elements are processed. This solution is not perfect either, since you wanted an abstraction that could let you seamlessly swap collections, but BulkXXX() methods are very specific to new collection.
Option 1
I think you should look into a better separation of your code using the MVVM pattern, if you aren't familiar with it, I highly suggest to see the following video as it explains exactly what you're looking for.
Specifically, however, in your case you should have the model class with regular collection (e.g List) on which you do all the work in the threads. Your ViewModel should contain the ObservableCollections and connect loosely with the collections that exist in the model, e.g, you can choose to subscribe via an event from your ViewModel to a certain update logic in your model. You will STILL need to use Dispatcher to update the OC, but you will only need to do it once.
Option 2
You can instead just use the solution described here. Basically, he created a new derived class from OC that allows you to dispatch changes from the code automatically without you ever needing to update the dispatcher yourself.
The common approach is to have a Dispatcher property on your view model (probably in a base class for all view models) that can be injected outside. It is OK to have it in a view model because view model SHOULD be aware of UI concepts, but it should not be aware of particular view (layout, controls, etc.) and certainly it should not have a reference to the view.
What you can do is you can make it easier to dispatch your code to the Dispatcher thread by creating a helper or a service that will abstract the dispatcher away. For example, you can create a helper like this:
public class AsyncHelper
{
public static void EnsureUIThread(Action action)
{
if (Application.Current != null && !Application.Current.Dispatcher.CheckAccess())
{
Application.Current.Dispatcher.BeginInvoke(action, DispatcherPriority.Background);
}
else
{
action();
}
}
}
And whenever you need to update you observable collection, you wrap you code in that helper method:
AsyncHelper.EnsureUIThread(() =>
{
// Update you observable collections here
});
OR, you can go further and use AOP (e.g. PostSharp) to specify declaratively (using attributes) that a method should be executed in the UI thread.
And finally, please note that you have to dispatch only collection updates to the UI thread. Usual properties can be safely updated from a background thread. The updates will be dispatched to the UI thread automatically by the binding mechanism. Probably in future versions of WPF updates to a collection from a background thread also will be supported.
Well you could write yourself an AsyncObservableCollection, if you know how to write it threadsafe. Then you can encapsulate the Dispatcher calls in it.
The problem is you would not use the standard ObservableCollection delivered within the .Net - Framework. It would increase the risk of errors in your application.
Another option would be to implement a WrapperClass, which contains and exposes an ObservableCollection for binding and has methods to modify the collection.
public class WrapperClass<T>
{
public ObservableCollection<T> Collection {get; set;}
public void Add(T item)
{
//do your dispatcher magic here
}
...
}
To modify the collection you implement the methods in it. The problem here is, that there is no guarantee, that others will use these methods, too.
I am afraid that you will have to wait for the next version of wpf
From this post:
A few nuggets we can expect to see in the next version of WPF include:
Hosting of Silverlight content with the new SilverlightHost element, without airspace issues (the inability to overlap WPF content over native Windows hWnd content)
Overall better management of airspace with hosted native hWnd-based content like the WebBrowser, HwndHost and WindowsFormsHost
Enabling binding and change notification for collections that are created on a background thread
Better integration with UI virtualization
Integration of the Ribbon control
And more
Use SynchronizationContext instead of Dispatcher. SynchronizationContext is common feature for threads synchronization in .NET, meanwhile Dispatcher is intentionally developed for WPF.
You probably want to use something like MTObservableCollection. I've used this in a project and it worked fantastically. Basically, it does all the dispatching work for you when the collection changed event is raised, by analysing the thread that the handler was assigned from, and dispatching accordingly.
The article is well worth a read, even if you don't plan to take this option.
I have an extension for this:
public static class DispatcherInvoker
{
public static void AddOnUI<T>(this ICollection<T> collection, T item)
{
Action<T> addMethod = collection.Add;
Application.Current.Dispatcher.BeginInvoke(addMethod, item);
}
}
EDIT:
I stole it from an stackoverflow post but forgot from which one
I think you have to much coupling if you need to think about threading in your model layer.
What you should do is to not connect your model directly to the GUI. As others have said, use a layer in between (MVVM).
This means that you let your MVVM layer respond to the change notifications from your observable collection. It is the MVVM layer that decides if and how these notifications should be passed on to the GUI. Look here for a way to lower the update frequency of the GUI to keep it usable.
In short:
Keep using an ObeservableCollection in your model layer if you like but don't use it directly in the GUI binding. Let another layer receive the notifications and control the GUI update.
I have a class that handles events created by multiple member objects. Events from these objects spawn worker threads for the event, so that the various event handlers in my class are running on different threads (one is a serial handler, one is a timer event, etc.) I'm looking for a simple way to make my code thread-safe, preferably by forcing the event handlers to run on my object's thread.
If this were a Forms UI object, I could take advantage of its implementation of the ISynchronizeInvoke interface, and make calls to InvokeRequired, Invoke, etc. In WPF I could use a Dispatcher object. But my class needs to run *independently of any UI code.
Here's a simplified example of what I have:
public class MyClass
{
private SomeObject object1;
private AnotherObject object2;
public MyClass()
{
object1 = new SomeObject();
object2 = new AnotherObject();
object1.AThreadedEvent += ThreadedEventHandler1;
object2.AnotherThreadedEvent += ThreadedEventHandler2;
}
// This runs in its own thread!
private void ThreadedEventHandler1()
{
// DO STUFF HERE
}
// This runs in its own thread!
private void ThreadedEventHandler2()
{
// DO STUFF HERE
}
}
Because both event handlers access the same objects in the parent class (including each-other!), it would be awesome if there were a simple way to force the event handlers to run in the creating object's thread.
I've toyed with the idea of having my class implement the ISynchronizeInvoke interface, but it appears that doing so can get pretty complicated. Before I jump down that rabbit hole, I thought I'd ping the experts to see if there is a more simple solution.
Thoughts?
EDIT:
Part of the reason I want to run the event handlers in the parent object's thread is because the parent object has it's *own events that are triggered based on the events sent by its member objects. I'd like any threading functionality to be hidden by this class, so that code that uses the class doesn't have to worry about thread-related issues (ie. locks and so on). Simply locking shared data won't do the job, because I *still need to trigger events from within the threaded event handlers.
The ideea of invoking on another thread is hand to hand with having a while loop that from time to time it checks whether there is an "outside" message to be processed. For UI, there is the windows loop that does that. For an external thread, you must write manually a loop. Imagine a situation without a loop and that you have a relative long running thread right ? and sudently you want to interrupt this thread to invoke your message and resume what it was doing ON THE SAME shared stack memory. This interruption would destroy your stack. This is simply NOT possible. The other possibility is to use a synchronization mechanism such as ManualResetEvent and just wait for a signal (a signal that comes outside your thread). So, to resume, in order to process a message from another thread, you basically have only two options:
1) You have a while loop, eventually using a little sleep (to give some time / ticks to other threads to do their job)
while (true) {
Thread.Sleep (5);
if (someMessageArrived) { ... }
}
2) You just wait for a message implementing somehow the producer / consummer architecture:
On listening thread:
aManualResetEvent.WaitOne ();
On the "producer" thread:
aManualResetEvent.Set ();
There are advanced classes in .NET framework that might help such as BlockingCollection.
Hope this helps
Assumming, that your class runs in its own thread that the only logic is to execute the incomming calls from other threads, this would be the solution:
(comments inside)
public class MyClass
{
private SomeObject object1;
private AnotherObject object2;
public MyClass()
{
object1 = new SomeObject();
object2 = new AnotherObject();
object1.AThreadedEvent += ThreadedEventHandler1;
object2.AnotherThreadedEvent += ThreadedEventHandler2;
}
// This runs in its own thread!
// Only add the real function call to the queue
public void ThreadedEventHandler1()
{
tasks.Add(ThreadedEventHandler1_really);
}
private void ThreadedEventHandler1_really()
{
// DO STUFF HERE
}
// This runs in its own thread!
// Only add the real function call to the queue
public void ThreadedEventHandler2()
{
tasks.Add(ThreadedEventHandler2_really);
}
// here is the actual logic of your function
private void ThreadedEventHandler2_really()
{
// DO STUFF HERE
}
// the queue of the tasks
BlockingCollection<Action> tasks = new BlockingCollection<Action>();
// this method never returns, it is blocked forever
// and the only purpose of i is to do the functions calls when they added to the queue
// it is done in the thread of this instance
public void StartConsume()
{
foreach (Action action in tasks.GetConsumingEnumerable())
{
// add logic before call
action();
// add logic after call
}
}
}
The solution based on that the caller threads tat calls the functions: ThreadedEventHandler1 and ThreadedEventHandler2, actually add the real call to the queue and emediately continue with their run.
From the other hand, StartConsume function iterates the queue and makes the calls of the added method calls. If you want to add another logic before and after call, you can add it in this function.
Hope it helped to achieve your goal.
Without completely understanding the rational behind your design. I can say that the problem you are trying to solve was solved many times before.
I will assume your main object is like a service which expects calls (in this case events) from itself and other services (the sub objects). If you would think about it in terms of services (which you arguably should) WCF solves that problem for you doing all the heavy lifting #Rami suggested.
You define the main service with the following behavior:
Instance Context Mode - Single
Concurrency Mode - Single
More about these here.
And every event handler would call that main service notifying it about the event.
I am pretty sure you would not go that far and implement every class as a service, but thought it is worth offering anyway as an option.
OK, based on all of your feedback (thanks!) I have a solution to my problem. The short answer: what I wanted to do isn't possible.
Here are more details for those who asked. I'm writing a DLL that manages a device attached to a serial port. This includes basic serial port COM (packet TX and RX, including parsing), and higher-level protocol behavior (TX, Ack, retry on timeout, etc.) The serial port event handlers provided by .NET are obviously asynchronous, as are the System.Timers.Timer objects that I use to handle timeouts, etc.
I am building the code around an MVVM architecture, so that my UI doesn't have any logic in it whatsoever. Hence my need to avoid exploiting Dispatcher or Invoke functionality provided by the UI.
What I was looking for was a way to handle asynchronous events within my DLL in the same simple manner provided by WinForms and WPF. But as has been pointed out, and as I learned when digging deeper, what you are *really doing when you call BeginInvoke or a Dispatcher is pushing something onto a queue, to be consumed later by a different thread polling the queue. Outside the context of a UI, no such polling architecture exists.
SO. My options are to lock the shared objects in my class to make it thread safe, or to implement my own polling architecture within another thread (to avoid blocking the program that uses the DLL) that emulates what the UI code already does.
In either case, the UI code will still need to use its Invoke or equivalent tools when handling events from the DLL class. I suppose that's OK.