<commit_before>﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using Expr = System.Linq.Expressions.Expression;

namespace Turner.Infrastructure.Mediator
{
    public class StaticDispatcher : IStaticDispatcher
    {
        private Dictionary<Type, Func<object, object>> _dispatchers;

        public StaticDispatcher(Func<Type, object> handlerFactory, params Assembly[] assemblies)
        {
            Register(handlerFactory, assemblies);
        }

        public object Dispatch(object request) =>
            _dispatchers[request.GetType()](request);

        private void Register(Func<Type, object> handlerFactory, Assembly[] assemblies)
        {
            _dispatchers = new Dictionary<Type, Func<object, object>>();

            foreach (var assembly in assemblies)
            {
                var classTypes = assembly.GetTypes()
                    .Where(type => type.IsClass && !type.IsAbstract && !type.IsInterface)
                    .ToArray();

                foreach (var type in classTypes
                    .SelectMany(type => type.GetInterfaces()
                        .Where(t => t.IsGenericType && typeof(IRequestHandler<>) == t.GetGenericTypeDefinition()))
                    .Select(type => type.GetGenericArguments().First()))
                {
                    RegisterType(type, handlerFactory);
                }

                foreach (var types in classTypes
                    .SelectMany(type => type.GetInterfaces()
                        .Where(t => t.IsGenericType && typeof(IRequestHandler<,>) == t.GetGenericTypeDefinition()))
                    .Select(type => type.GetGenericArguments()))
                {
                    RegisterType(types[0], types[1], handlerFactory);
                }
            }
        }

        private void RegisterType(Type requestType, Func<Type, object> handlerFactory)
        {
            var handlerType = typeof(IRequestHandler<>).MakeGenericType(requestType);
            _dispatchers[requestType] = CreateDispatcher(handlerType, requestType, handlerFactory);
        }

        private void RegisterType(Type requestType, Type resultType, Func<Type, object> handlerFactory)
        {
            var handlerType = typeof(IRequestHandler<,>).MakeGenericType(requestType, resultType);
            _dispatchers[requestType] = CreateDispatcher(handlerType, requestType, handlerFactory);
        }
        <commit_msg>refactor(dispatcher registration): refactor dispatcher registration for clarity<commit_after>﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using Expr = System.Linq.Expressions.Expression;

namespace Turner.Infrastructure.Mediator
{
    public class StaticDispatcher : IStaticDispatcher
    {
        private Dictionary<Type, Func<object, object>> _dispatchers;

        public StaticDispatcher(Func<Type, object> handlerFactory, params Assembly[] assemblies)
        {
            Register(handlerFactory, assemblies);
        }

        public object Dispatch(object request) =>
            _dispatchers[request.GetType()](request);

        private void Register(Func<Type, object> handlerFactory, IEnumerable<Assembly> assemblies)
        {
            _dispatchers = new Dictionary<Type, Func<object, object>>();

            var classTypes = assemblies
                .SelectMany(x => x.GetTypes())
                .Where(type => type.IsClass && !type.IsAbstract && !type.IsInterface)
                .ToArray();

            var requestTypesWithoutResult = classTypes
                .SelectMany(type => type.GetInterfaces()
                    .Where(t => t.IsGenericType && typeof(IRequestHandler<>) == t.GetGenericTypeDefinition()))
                .Select(type => type.GenericTypeArguments);

            foreach (var types in requestTypesWithoutResult)
            {
                var requestType = types[0];
                var handlerType = typeof(IRequestHandler<>).MakeGenericType(requestType);

                _dispatchers[requestType] = CreateDispatcher(handlerType, requestType, handlerFactory);
            }

            var requestTypesWithResult = classTypes
                .SelectMany(type => type.GetInterfaces()
                    .Where(t => t.IsGenericType && typeof(IRequestHandler<,>) == t.GetGenericTypeDefinition()))
                .Select(type => type.GenericTypeArguments);

            foreach (var types in requestTypesWithResult)
            {
                var requestType = types[0];
                var resultType = types[1];
                var handlerType = typeof(IRequestHandler<,>).MakeGenericType(requestType, resultType);

                _dispatchers[requestType] = CreateDispatcher(handlerType, requestType, handlerFactory);
            }
        }

{'fraction_non_alphanumeric': 0.09819389661615113, 'fraction_numerical': 0.0010379904504878555, 'mean_word_length': 2.313617606602476, 'pattern_counts': {'":': 0, '<': 26, '<?xml version=': 0, '>': 43, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3520456', 'n_tokens_mistral': 1197, 'n_tokens_neox': 1125, 'n_words': 243}