2011-11-22 7 views
0

Я использую Rx и, более конкретно, ReactiveUI некоторое время в проекте и попал в ситуацию, когда мне кажется, мне нужен совет.ReactiveUI MessageBus и MessageBox с результатом

Проблема заключается в том, что при выполнении команды (нажата кнопка) я хочу показать окно сообщения, которое пользователь ответит «Да» или «Нет». В зависимости от ответа я хочу сделать еще несколько вещи. Поскольку я использую MVVM с модульными тестами, я бы хотел, чтобы MessageBox тестировался; т.е. заменить другим кодом. Это, по сути, то, что у меня есть.

На мой взгляд, модель:

this.ExternalObservable = this.SomeOperationCommand 
      .SelectMany(_ => this.UserWantsToContinueWithOperation()) 
      .Where(x => x) 
      .Select(_ => this.SomeData) 
      .Where(x => x != null); 

private IObservable<bool> UserWantsToContinueWithOperation() { 
     var subject = new Subject<bool>(); 

     var box = new GuiMsgBox("Continue?", 
      result => { 
       subject.OnNext(result == System.Windows.MessageBoxResult.Yes); 
      }); 

     MessageBus.Current.SendMessage(box); 

     return subject; 
    } 

И GuiMsgBox, по существу, оболочка вокруг System.Windows.MessageBox класса, который я слушаю с помощью MessageBus в пользовательском интерфейсе и в моих тестах.

Все это отлично работает при запуске приложения, но в модульных тестах, поскольку шина использует планировщик Immediate, очевидно, что он работает не так.

Я чувствую, что здесь есть некоторые ошибки в конструкции, поэтому любой ввод на актуальную проблему; чтобы показать окно сообщения, возвращающий результат, который может быть протестирован, был бы очень признателен!

ответ

1

Трудно сказать, не видя больше деталей реализации, но вместо этого я бы подумал об использовании TestScheduler. В RxUI.Testing, это так же просто, как:

(new TestScheduler()).With(sched => { 
    // Write your test here, all the schedulers will be 
    // implicitly set to your 'sched' scheduler. 
}); 

Вот пример кучу MVVM связанных тестов, тестирование таймер Pomodoro:

https://github.com/xpaulbettsx/ReactiveUI/blob/master/ReactiveUI.Sample/ReactiveUI.Sample.Tests/ViewModels/BlockTimerViewModelTest.cs

Вот еще один хороший пример MVVM основанное тестирование from my Rx book (извините о вилке), в частности, с использованием CreateColdObservable для того, чтобы дразнить вход (т.е. тестирование сценария «Нажмите кнопку, подождите 10 секунд, проверьте результат»)

https://github.com/ProgRx/Chapter-9

+0

Хорошо, я попробую 'TestScheduler' для этой конкретной проблемы. Что еще вы думаете об этом способе получения результата из диалогового окна? Как вы это делаете при использовании ReactiveUI? Я полагаю, что это сводится к тому, что «MessageBus» откладывается вместо немедленного, что имеет место, например, MVVMLight, не так ли? – lbergnehr