我目前有一个使用Autofac和MassTransit的WPF应用程序。 WPF主窗口是由不同控件组成的复合UI(状态部分,命令部分和主要部分)。通过使用MassTransit和InMemory传输,我可以与这些控件进行通信。
当用户在特定的文本框中键入内容时,我会发布“ IRipWidthChanged”事件。该事件的使用者将其拾取并在WPF中完成它的工作。
查看模型
private string _ripWidthString;
public string RipWidthString {
get => _ripWidthString;
set => {
if (_ripWidthString == value) return;
FirePropertyChanged();
FirePropertyChanged(nameof(ClearValuesButtonEnabled));
_bus.PublishAsync(new RipWidthChanged.Builder() { NewRipWidth = value }.Build());
}
}
消费者
public task Consume(ConsumeContext<IRipWidthChanged> ctx) => Task.Run(() =>
_viewModelFactory.Construct<ICommandsViewModel>().UpdateRipWidth(ctx.Message.NewRipWidth)
);
当“ RipWidthString”属性的设置器被调用时,总线发布消息,但从未调用我的使用者。我添加了错误和其他机制来查看是否正在发生其他事情,但是什么也没得到调用。
我还使用相同的代码在这些前端之间设置我的Autofac容器,因此视图模型和ServiceBus已在Autofac中注册。
编辑1这是注册Autofac容器的代码
Android Xamarin项目中的MainActivity.cs
void RegisterDependencies() {
App.Register<IMessageBox, AndroidMessageBox>();
App.Register<IPopupMessage, AndroidPopupMessage>();
App.Register<SemiAutoPage>();
App.Register<CommandsControlViewModel>();
App.BuildContainer();
}
Xamarin核心项目中的App.xaml.cs文件
private static void SetupDiContainer() {
_builder.RegisterModule(new ViewModelModule());
_builder.RegisterModule(new ServiceBusModule());
_builder.RegisterModule(new FactoriesModule());
_builder.RegisterModule(new ValidationModule());
_builder.RegisterModule(new FileSystemModule());
_builder.RegisterModule(new DataConversionModule());
_builder.RegisterType<NullLoggingService>().As<ILoggingService>();
_builder.RegisterType<MassTransitCommandExecutor>()
.As<ICommandExecutionService>()
.SingleInstance();
_builder.Register(ctx => ServiceFactory.Construct<IPanelSawService>(IPAddress.Parse("192.168.1.12"), 5001))
.As<IPanelSawService>();
_builder.Register(ctx => ServiceFactory.Construct<IMachineStateService>(IPAddress.Parse("192.168.1.12"), 5001))
.As<IMachineStateService>();
}
//...
public static void BuildContainer() {
SetupDiContainer();
_diContainer = _builder.Build();
}
以及用于设置和注册MassTransit总线的代码
ServiceBusModule.cs Autofac模块
public class ServiceBusModule : Module {
protected override void Load(ContainerBuilder builder) {
builder.AddMassTransit(x => {
x.AddConsumers(
typeof(StateChangedConsumer),
typeof(CutCompletedConsumer),
typeof(SettingsConsumer),
typeof(ExceptionConsumer)
);
x.AddBus(context => Bus.Factory.CreateUsingInMemory(busConfig => {
busConfig.ReceiveEndpoint("panelsaw_queue", cfg => {
cfg.ConfigureConsumers(context);
});
}));
});
builder.Register(ctx => new PanelSawServiceBus(ctx.Resolve<IBus>(), ctx.Resolve<IBusControl>()))
.As<IServiceBus>()
.SingleInstance();
}
}
向遇到此问题的其他人。请记住,确保启动服务总线非常重要。我的WPF和Xamarin应用程序之间的区别在于,在引导过程中,WPF应用程序将解析IServiceBus接口,并在应用程序启动之前启动它。
一旦我在Xamarin应用程序中执行了相同的操作,一切都会按照我的预期进行。给我的消费者提供了正确的信息。