#c# #rabbitmq #masstransit
#c# #кролик #масстрансит
Вопрос:
Для проекта с архитектурой микросервиса я создал методы расширения для регистрации MassTransit. Вот пример одного из двух:
public static IServiceCollection AddMassTransitConfigWorker(this IServiceCollection services, IConfiguration config, string nameQueue) { return services.AddMassTransit(x =gt; { x.UsingRabbitMq((context, cfg) =gt; { cfg.Host(config.GetValuelt;stringgt;("MqHost"), hostCfg =gt; { hostCfg.Username(config.GetValuelt;stringgt;("MqUser")); hostCfg.Password(config.GetValuelt;stringgt;("MqPassword")); }); cfg.ReceiveEndpoint(nameQueue, epCfg =gt; { var provider = services.BuildServiceProvider(); var massTransitManager = provider.GetServicelt;IMassTransitManagergt;(); epCfg.Consumer(() =gt; new RequestModelConsumer(massTransitManager)); }); }); x.AddRequestClientlt;RequestModelWorkergt;(); }) .AddMassTransitHostedService(); }
Также была создана простая служба для отправки сообщения в очередь и получения ответа:
public class TestService : ITestService { private readonly IRequestClientlt;RequestModelgt; _client; public TestService(IRequestClientlt;RequestModelgt; client) { _client = client; } public async Tasklt;stringgt; SendRequestMessageAsync(string request) { var response = await _client.GetResponselt;RequestModelResponsegt;(new RequestModelResponse { RequestString = request }); return response.Message.ResponseString; } }
Затем служба TestService зарегистрирована в DI, но IRequestClient был равен нулю. Текст ошибки:
MassTransit.ConfigurationException: An exception occurred during bus creation ---gt; System.NullReferenceException: Object reference not set to an instance of an object. at MassTransit.RabbitMqTransport.Configuration.RabbitMqHostConfiguration.Build() at MassTransit.Registration.TransportRegistrationBusFactory`1.CreateBus[T,TConfigurator](T configurator, IBusRegistrationContext context, Action`2 configure, IEnumerable`1 specifications) --- End of inner exception stack trace --- at MassTransit.Registration.TransportRegistrationBusFactory`1.CreateBus[T,TConfigurator](T configurator, IBusRegistrationContext context, Action`2 configure, IEnumerable`1 specifications) at MassTransit.RabbitMqTransport.Configuration.RabbitMqRegistrationBusFactory.CreateBus(IBusRegistrationContext context, IEnumerable`1 specifications) at MassTransit.ExtensionsDependencyInjectionIntegration.Registration.ServiceCollectionBusConfigurator.CreateBus[T](T busFactory, IServiceProvider provider) at MassTransit.ExtensionsDependencyInjectionIntegration.Registration.ServiceCollectionBusConfigurator.lt;gt;c__DisplayClass7_0`1.lt;SetBusFactorygt;b__0(IServiceProvider provider) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitFactory(FactoryCallSite factoryCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitRootCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.Resolve(ServiceCallSite callSite, ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceLookup.DynamicServiceProviderEngine.lt;gt;c__DisplayClass1_0.lt;RealizeServicegt;b__0(ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService(IServiceProvider provider, Type serviceType) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService[T](IServiceProvider provider) at MassTransit.ExtensionsDependencyInjectionIntegration.Registration.ServiceCollectionBusConfigurator.lt;gt;c__7`1.lt;SetBusFactorygt;b__7_4(IServiceProvider provider) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitFactory(FactoryCallSite factoryCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitRootCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.Resolve(ServiceCallSite callSite, ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceLookup.DynamicServiceProviderEngine.lt;gt;c__DisplayClass1_0.lt;RealizeServicegt;b__0(ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService(IServiceProvider provider, Type serviceType) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService[T](IServiceProvider provider) at MassTransit.ExtensionsDependencyInjectionIntegration.Registration.ServiceCollectionBusConfigurator.lt;.ctorgt;b__1_1(IServiceProvider provider) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitFactory(FactoryCallSite factoryCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitRootCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.Resolve(ServiceCallSite callSite, ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceLookup.DynamicServiceProviderEngine.lt;gt;c__DisplayClass1_0.lt;RealizeServicegt;b__0(ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService(IServiceProvider provider, Type serviceType) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService[T](IServiceProvider provider) at MassTransit.ExtensionsDependencyInjectionIntegration.Registration.DependencyInjectionContainerRegistrar.GetClientFactory(IServiceProvider provider) at MassTransit.ExtensionsDependencyInjectionIntegration.Registration.DependencyInjectionContainerRegistrar.lt;gt;c__DisplayClass16_0`1.lt;MassTransit.Registration.IContainerRegistrar.RegisterRequestClientgt;b__0(IServiceProvider provider) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitFactory(FactoryCallSite factoryCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitScopeCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitConstructor(ConstructorCallSite constructorCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitScopeCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitConstructor(ConstructorCallSite constructorCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitScopeCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitConstructor(ConstructorCallSite constructorCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitDisposeCache(ServiceCallSite transientCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitIEnumerable(IEnumerableCallSite enumerableCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.Resolve(ServiceCallSite callSite, ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceLookup.DynamicServiceProviderEngine.lt;gt;c__DisplayClass1_0.lt;RealizeServicegt;b__0(ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService(IServiceProvider provider, Type serviceType) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService[T](IServiceProvider provider) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetServices[T](IServiceProvider provider) at Worker.WorkerEngine..ctor(IServiceProvider provider, ILogger`1 logger, IAccessSecurityService accessSecurityService, IUserContext userContext, IUserInfoStorage userInfoStorage, IDiagnosticsService diagnosticsService, JsonRpcService jsonRpcService) in WorkerWorkerEngine.cs:line 63 at System.RuntimeMethodHandle.InvokeMethod(Object target, Object[] arguments, Signature sig, Boolean constructor, Boolean wrapExceptions) at System.Reflection.RuntimeConstructorInfo.Invoke(BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitConstructor(ConstructorCallSite constructorCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitDisposeCache(ServiceCallSite transientCallSite, RuntimeResolverContext context) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument) at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.Resolve(ServiceCallSite callSite, ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceLookup.DynamicServiceProviderEngine.lt;gt;c__DisplayClass1_0.lt;RealizeServicegt;b__0(ServiceProviderEngineScope scope) at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetService[T](IServiceProvider provider) at Startup.lt;gt;c__DisplayClass5_0.lt;lt;ConfigureServicesgt;b__5gt;d.MoveNext() in Startup.cs:line 131 --- End of stack trace from previous location --- at MassTransitManager.ProcessMessageAsync(String requestString) in MasstransitManager.cs:line 54 at MassTransitManager.StartAsync(String requestString) in MasstransitManager.cs:line 34
Почему я получаю эту ошибку? Интересно, что вторая служба идентична, и во второй службе нет ошибок.
Ответ №1:
Ну, вам нужно указать тип сообщения в клиенте запроса, а не тип работника??
x.AddRequestClientlt;RequestModelgt;();
Он должен соответствовать тому, что используется в конструкторе службы тестирования.
Комментарии:
1. Я нашел проблему. Когда я регистрирую службу MassTransitManager, у нее есть делегат, которому я передаю новую область, и, поскольку в ней нет службы IRequestClient, затем создается новая точка приема и, следовательно, новая очередь. Я предполагаю, что это связано с тем, что имя очереди дублируется.
2. можно ли зарегистрировать RequestClient как синглтон?
3. Нет, вы должны создать область для ее решения. Если вам нужно отправлять запросы из контекста, не относящегося к области действия, вы можете вызвать
bus.CreateRequestClientlt;Tgt;()
usingIBus
в качестве зависимости вместоIRequestClient
.4. Попытался добавить
IBus
, но получил ошибку — во время создания шины произошло исключение. Что я сделал не так?5. Вы чрезмерно абстрагируетесь от «менеджера общественного транспорта» вместо того, чтобы регистрировать своих потребителей в контейнере и позволять MassTransit разрешать их. Это есть в документации, но вам нужно использовать
AddConsumer
иConfigureConsumer
вместо создания поставщика услуг в вашем методе настройки. Базовый контейнер 101-го уровня.