I'm working on some code that can automatically detect the serial port that a device (in this case, a spectrometer) is connected to.
I have the auto detection piece working, and I'm trying to write tests for the ViewModel that shows the progress of detection, errors, etc.
Here's the interface to the code that does the actual detection.
public interface IAutoDetector
{
Task DetectSpectrometerAsync(IProgress<int> progress);
bool IsConnected { get; set; }
string SelectedSerialPort { get; set; }
}
Here is the ViewModel that uses the IAutoDetector to detect the spectrometer
public class AutoDetectViewModel : Screen
{
private IAutoDetector autoDetect;
private int autoDetectionProgress;
public int AutoDetectionProgress
{
get { return autoDetectionProgress; }
private set
{
autoDetectionProgress = value;
NotifyOfPropertyChange();
}
}
[ImportingConstructor]
public AutoDetectViewModel(IAutoDetector autoDetect)
{
this.autoDetect = autoDetect;
}
public async Task AutoDetectSpectrometer()
{
Progress<int> progressReporter = new Progress<int>(ProgressReported);
await autoDetect.DetectSpectrometerAsync(progressReporter);
}
private void ProgressReported(int progress)
{
AutoDetectionProgress = progress;
}
}
I'm trying to write a test that verifies progress reported from the IAutoDetector updates the AutoDetectionProgress property in the AutoDetectionViewModel.
Here's my current (non-working) test:
[TestMethod]
public async Task DetectingSpectrometerUpdatesTheProgress()
{
Mock<IAutoDetector> autoDetectMock = new Mock<IAutoDetector>();
AutoDetectViewModel viewModel = new AutoDetectViewModel(autoDetectMock.Object);
IProgress<int> progressReporter = null;
autoDetectMock.Setup(s => s.DetectSpectrometerAsync(It.IsAny<IProgress<int>>()))
.Callback((prog) => { progressReporter = prog; });
await viewModel.AutoDetectSpectrometer();
progressReporter.Report(10);
Assert.AreEqual(10, viewModel.AutoDetectionProgress);
}
What I want to do is grab the IProgress<T> that is passed to autoDetect.DetectSpectrometerAsync(progressReporter), tell the IProgress<T> to report a progress of 10, then make sure the AutoDetectionProgress in the viewModel is 10 as well.
However, there's 2 problems with this code:
- It does not compile. The
autoDetectMock.Setupline has an error:Error 1 Delegate 'System.Action' does not take 1 arguments. I've used the same technique in other (non-synchronous) tests to gain access to passed values. - Will this approach even work? If my understanding of async is correct, the call
await viewModel.AutoDetectSpectrometer();will wait for the call to finish before callingprogressReporter.Report(10);, which won't have any effect because theAutoDetectSpectrometer()call has returned already.
Aucun commentaire:
Enregistrer un commentaire