public IRequestSubscriber Subscribe <TRequest>() where TRequest : IRequest
        {
            var key = _moduleOwnerKeyService.GetKeyForMessage <TRequest>();

            var handlerType = typeof(IRequestHandler <>);
            var args        = new [] { typeof(TRequest) };
            var typeToFind  = handlerType.MakeGenericType(args);

            var handler = (IRequestHandler <TRequest>)_serviceProvider.GetRequiredService(typeToFind);

            _requestRegistry.RegisterRequestHandler <TRequest>(key, (o) => handler.HandleAsync((TRequest)o));

            return(this);
        }
        public async Task <TResponse> GetAsync <TResponse, TRequest>(TRequest request)
        {
            var key = _moduleOwnerKeyService.GetKeyForMessage <TRequest>();

            var json = JsonConvert.SerializeObject(request);

            var subscription = _requestRegistry.GetSubscription(key);

            var result =
                await subscription.AsyncAction(JsonConvert.DeserializeObject(json, subscription.SubscriptionType));

            var responseJson = JsonConvert.SerializeObject(result);

            return(JsonConvert.DeserializeObject <TResponse>(responseJson));
        }
        public IEventSubscriber Subscribe <T>() where T : IDomainEvent
        {
            var key = _moduleOwnerKeyService.GetKeyForMessage <T>();

            var handlerType = typeof(IDomainEventHandler <>);
            var args        = new [] { typeof(T) };
            var typeToFind  = handlerType.MakeGenericType(args);

            var handler = (IDomainEventHandler <T>)_serviceProvider.GetService(typeToFind);

            if (handler is null)
            {
                throw new InvalidCastException();
            }

            _moduleEventRegistry.AddSubscriber <T>(key, obj => handler.HandleAsync((T)obj));
            return(this);
        }
        public async Task PublishDomainEventAsync <T>(T @event) where T : IDomainEvent
        {
            var key = _moduleOwnerKeyService.GetKeyForMessage <T>();

            var subscriptions = _moduleEventRegistry.GetSubscribers <T>(key);

            if (subscriptions is null)
            {
                _logger.LogWarning($"No subscribers for message with key {key}");
                return;
            }

            var json = JsonConvert.SerializeObject(@event);

            foreach (var subscription in subscriptions)
            {
                await subscription.AsyncAction(JsonConvert.DeserializeObject(json, subscription.SubscriptionType));
            }
        }