using System; using System.Collections.Generic; using System.Linq; using Unity.Injection; using Unity.Registration; namespace Implab.ServiceHost.Unity { public class TypeRegistrationContext : RegistrationContext { readonly TypeResolver m_resolver; readonly List m_injections = new List(); public InjectionMember[] Injections { get { return m_injections.ToArray(); } } public Type ImplementationType { get; private set; } internal TypeRegistrationContext(TypeResolver resolver, Type registrationType, Type implementationType) : base(registrationType) { ImplementationType = implementationType; // when registering a generic mapping, register all generic parameter names as local types if (ImplementationType.IsGenericTypeDefinition) { m_resolver = new TypeResolver(resolver); foreach (var p in ImplementationType.GetGenericArguments()) m_resolver.AddMapping(p.Name, p); } else { m_resolver = resolver; } } internal void Visit(ConstructorInjectionElement constructorInjection) { var valueContext = new InjectionValueContext(m_resolver, null); var parameters = constructorInjection.Parameters?.Select(x => x.Resolve(valueContext)).ToArray(); var injection = parameters != null ? new InjectionConstructor(parameters) : new InjectionConstructor(); m_injections.Add(injection); } internal void Visit(MethodInjectionElement methodInjection) { var valueContext = new InjectionValueContext(m_resolver, null); var parameters = methodInjection.Parameters?.Select(x => x.Resolve(valueContext)).ToArray(); var injection = parameters != null ? new InjectionMethod(methodInjection.Name, parameters) : new InjectionMethod(methodInjection.Name); m_injections.Add(injection); } internal void Visit(PropertyInjectionElement propertyInjection) { if (propertyInjection.Value == null) throw new Exception($"A value value must be specified for the property '{propertyInjection.Name}'"); var propertyType = RegistrationType.GetProperty(propertyInjection.Name)?.PropertyType; var valueContext = new InjectionValueContext(m_resolver, propertyType); var parameter = propertyInjection.Value.Resolve(valueContext); var injection = new InjectionProperty(propertyInjection.Name, parameter); m_injections.Add(injection); } } }