Project: .Net 9 Maui Package: ReactiveUI.Maui, ReactiveUI.Fody, Shiny.Jobs, Shiny.Hosting.Maui
I have a Foreground Job, that runs periodically as a singleton, it injects a singleton of ICloudToDeviceStateManager that maintains some shared properties for other services to observe. In this case if the job is running or not.. I expect that the viewmodel IsRunning property would be updated on each change so i can display a ActivityIndicator on the page that shows that the job is running. But only ever receive the job completion value..
public class CloudToDeviceStateManager : ReactiveObject
{
private readonly BehaviorSubject<bool> _isRunningSubject = new BehaviorSubject<bool>(false);
public IObservable<bool> IsRunningTicks => _isRunningSubject.AsObservable();
public bool IsRunning
{
get => _isRunningSubject.Value;
private set
{
_isRunningSubject.OnNext(value);
this.RaisePropertyChanged();
}
}
public void SetIsRunning(bool isRunning)
{
IsRunning = isRunning;
}
}
public partial class CloudToDeviceSyncJob : IJob
{
private readonly ICloudToDeviceStateManager _stateManager;
[ObservableAsProperty] public bool IsRunning { get; }
public CloudToDeviceSyncJob(ICloudToDeviceStateManager stateManager)
{
_stateManager = stateManager;
}
protected override async Task Run(CancellationToken cancelToken)
{
try
{
_stateManager.SetIsRunning(true);
cancelToken.ThrowIfCancellationRequested();
//... some logic here
}catch(Exception ex) {}
finally
{
_stateManager.SetIsRunning(false);
_logger.LogInformation("CloudToDeviceSyncJob finished");
}
}
}
I've injected this statemanager into a viewmodel
public class MainPageViewModel : ViewModelBase
{
private readonly ICloudToDeviceStateManager _stateManager;
[Reactive] public bool IsRunning { get; set; }
public MainPageViewModel(ICloudToDeviceStateManager stateManager)
{
_stateManager = stateManager;
// tried this..
this.WhenAnyValue(x => x._stateManager.IsRunning)
.ObserveOn(RxApp.MainThreadScheduler)
.BindTo(this, x => x.IsRunning);
// tried this
_stateManager.IsRunningTicks.Subscribe(x => IsRunning = x);
}
}
However when the job is ran, the _stateManager.SetIsRunning(true); does update the statemanager but the view model doesn't receive this value. it only ever receives the false setter.
it seems as if the job has to complete before the change notifier is submitted to the subscriber. I'm not sure what is preventing the view model from receiving the true statement..