|
|
using System;
|
|
|
using System.Collections.Generic;
|
|
|
using System.ComponentModel;
|
|
|
using System.Linq;
|
|
|
using System.Xml.Serialization;
|
|
|
using Unity.Injection;
|
|
|
|
|
|
namespace Implab.ServiceHost.Unity {
|
|
|
|
|
|
public class InjectionValueBuilder {
|
|
|
|
|
|
readonly TypeResolver m_resolver;
|
|
|
|
|
|
public Type DefaultType { get; private set; }
|
|
|
|
|
|
public Type ValueType { get; private set; }
|
|
|
|
|
|
public object Value { get; set; }
|
|
|
|
|
|
internal InjectionParameterValue Injection {
|
|
|
get {
|
|
|
if (Value != null)
|
|
|
return InjectionParameterValue.ToParameter(Value);
|
|
|
|
|
|
return new InjectionParameter(ValueType, null);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
internal InjectionValueBuilder(TypeResolver resolver, Type defaultType) {
|
|
|
m_resolver = resolver;
|
|
|
DefaultType = defaultType;
|
|
|
}
|
|
|
|
|
|
public Type ResolveInjectedValueType(string typeSpec) {
|
|
|
if (string.IsNullOrEmpty(typeSpec)) {
|
|
|
if (DefaultType == null)
|
|
|
throw new Exception("The type must be specified");
|
|
|
return DefaultType;
|
|
|
}
|
|
|
return m_resolver.Resolve(typeSpec);
|
|
|
}
|
|
|
|
|
|
public Type ResolveType(string typeSpec) {
|
|
|
return m_resolver.Resolve(typeSpec);
|
|
|
}
|
|
|
|
|
|
public void SetValue(Type type, object value) {
|
|
|
ValueType = type;
|
|
|
Value = value;
|
|
|
}
|
|
|
|
|
|
public void SetValue<T>(T value) {
|
|
|
SetValue(typeof(T), value);
|
|
|
}
|
|
|
|
|
|
public void SetDependencyReference(Type type, string name, bool optional) {
|
|
|
ValueType = type;
|
|
|
Value = optional ? (object)new OptionalParameter(type, name) : new ResolvedParameter(type, name);
|
|
|
}
|
|
|
|
|
|
internal void Visit(ArrayParameterElement arrayParameter) {
|
|
|
Type itemsType = null;
|
|
|
var arrayType = string.IsNullOrEmpty(arrayParameter.TypeName) ? null : ResolveType(arrayParameter.TypeName);
|
|
|
|
|
|
if (!string.IsNullOrEmpty(arrayParameter.ItemsType)) {
|
|
|
itemsType = ResolveType(arrayParameter.ItemsType);
|
|
|
if (arrayType == null)
|
|
|
arrayType = itemsType.MakeArrayType();
|
|
|
} else {
|
|
|
itemsType = arrayType?.GetInterface(typeof(IEnumerable<>).FullName)?.GetGenericArguments()[0];
|
|
|
}
|
|
|
|
|
|
if (itemsType == null)
|
|
|
throw new Exception("Failed to determine array elements type");
|
|
|
|
|
|
InjectionParameterValue[] injections = (arrayParameter.Items ?? new InjectionParameterElement[0])
|
|
|
.Select(x => {
|
|
|
var builder = new InjectionValueBuilder(m_resolver, itemsType);
|
|
|
x.Visit(builder);
|
|
|
return builder.Injection;
|
|
|
})
|
|
|
.ToArray();
|
|
|
|
|
|
var array = itemsType.IsGenericParameter ? (object)new GenericResolvedArrayParameter(itemsType.Name, injections) : new ResolvedArrayParameter(itemsType, injections);
|
|
|
ValueType = arrayType;
|
|
|
Value = array;
|
|
|
}
|
|
|
}
|
|
|
}
|