I have an MVVM-lite application that I would like to test for unit. The model uses System.Timers.Timer, and therefore the update event ends in the background thread. This unit test is excellent, but at runtime threw a System.NotSupportedException "This type of CollectionView does not support changes to the SourceCollection from a stream other than the Dispatcher stream." I was hoping the MVVM-lite Threading.DispatcherHelper class would fix everything, but calling DispatcherHelper.CheckBeginInvokeOnUI would result in a unit test error. Here is the code I got in the view model
private void locationChangedHandler(object src, LocationChangedEventArgs e) { if (e.LocationName != this.CurrentPlaceName) { this.CurrentPlaceName = e.LocationName; List<FileInfo> filesTaggedForHere = Tagger.FilesWithTag(this.CurrentPlaceName); //This nextline fixes the threading error, but breaks it for unit tests //GalaSoft.MvvmLight.Threading.DispatcherHelper.CheckBeginInvokeOnUI(delegate { updateFilesIntendedForHere(filesTaggedForHere); }); if (Application.Current != null) { this.dispatcher.Invoke(new Action(delegate { updateFilesIntendedForHere(filesTaggedForHere); })); } else { updateFilesIntendedForHere(filesTaggedForHere); } } } private void updateFilesIntendedForHere(List<FileInfo> filesTaggedForHereIn) { this.FilesIntendedForHere.Clear(); foreach (FileInfo file in filesTaggedForHereIn) { if (!this.FilesIntendedForHere.Contains(file)) { this.FilesIntendedForHere.Add(file); } } }
I tried the trick at http://kentb.blogspot.com/2009/04/mvvm-infrastructure-viewmodel.html , but the Invoke call on Dispatcher.CurrentDispatcher did not start during the unit test and so it failed. This is why I call the helper method directly if the run is in a test and not in the application.
This may not be right - the ViewModel does not have to care about where it is being called from. Can anyone understand why neither the Kent Boogaart dispatcher method nor the MVVM-lite DispatcherHelper.CheckBeginInvokeOnUI work in my unit test?
source share