Mercurial > pub > ImplabNet
comparison Implab.ServiceHost/Unity/TypeResolver.cs @ 277:963b17c275be v3
Refactoring
Added <array> element to injection parameters
Working on registrations of factories
author | cin |
---|---|
date | Sat, 28 Apr 2018 18:48:09 +0300 |
parents | 9d1cca834b05 |
children | 6691aff01de1 |
comparison
equal
deleted
inserted
replaced
276:b4e0f81c7425 | 277:963b17c275be |
---|---|
3 using System.Linq; | 3 using System.Linq; |
4 using System.Text; | 4 using System.Text; |
5 using System.Text.RegularExpressions; | 5 using System.Text.RegularExpressions; |
6 using Implab.Diagnostics; | 6 using Implab.Diagnostics; |
7 | 7 |
8 namespace Implab.ServiceHost.Unity | 8 namespace Implab.ServiceHost.Unity { |
9 { | |
10 using static Trace<TypeResolver>; | 9 using static Trace<TypeResolver>; |
11 public class TypeResolver | 10 public class TypeResolver { |
12 { | |
13 readonly Dictionary<string, Type> m_cache = new Dictionary<string, Type>(); | 11 readonly Dictionary<string, Type> m_cache = new Dictionary<string, Type>(); |
14 | 12 |
15 Regex _nsRx = new Regex(@"^\w+(\.\w+)*$", RegexOptions.Compiled); | 13 Regex _nsRx = new Regex(@"^\w+(\.\w+)*$", RegexOptions.Compiled); |
16 readonly LinkedList<string> m_namespases = new LinkedList<string>(); | 14 readonly LinkedList<string> m_namespases = new LinkedList<string>(); |
17 | 15 |
47 public Type Resolve(TypeReference reference) { | 45 public Type Resolve(TypeReference reference) { |
48 var args = reference.IsGeneric && !reference.IsOpenGeneric ? reference.GenericParameters?.Select(Resolve).ToArray() : null; | 46 var args = reference.IsGeneric && !reference.IsOpenGeneric ? reference.GenericParameters?.Select(Resolve).ToArray() : null; |
49 var argc = reference.IsGeneric ? reference.GenericParameters.Length : 0; | 47 var argc = reference.IsGeneric ? reference.GenericParameters.Length : 0; |
50 | 48 |
51 Type resolved; | 49 Type resolved; |
52 if(!m_cache.TryGetValue(reference.ToString(), out resolved)) { | 50 if (!m_cache.TryGetValue(reference.ToString(), out resolved)) { |
53 resolved = ResolveInternal(reference, args, argc); | 51 resolved = ResolveInternal(reference, args, argc); |
54 if (resolved == null) | 52 if (resolved == null) |
55 throw new Exception($"Failed to resolve {reference}"); | 53 throw new Exception($"Failed to resolve {reference}"); |
56 m_cache[reference.ToString()] = resolved; | 54 m_cache[reference.ToString()] = resolved; |
57 } | 55 } |
63 return Resolve(TypeReference.Parse(typeSpec)); | 61 return Resolve(TypeReference.Parse(typeSpec)); |
64 } | 62 } |
65 | 63 |
66 Type ResolveInternal(TypeReference reference, Type[] args, int argc) { | 64 Type ResolveInternal(TypeReference reference, Type[] args, int argc) { |
67 var resolved = ProbeInNamespaces( | 65 var resolved = ProbeInNamespaces( |
68 String.Join(".", new [] { reference.Namespace, reference.TypeName }.Where(x => !string.IsNullOrEmpty(x)) ), | 66 String.Join(".", new[] { reference.Namespace, reference.TypeName }.Where(x => !string.IsNullOrEmpty(x))), |
69 args, | 67 args, |
70 argc, | 68 argc, |
71 reference.IsArray, | 69 reference.IsArray, |
72 reference.ToString() | 70 reference.ToString() |
73 ); | 71 ); |
74 | 72 |
75 if (resolved == null && m_parent != null) | 73 if (resolved == null && m_parent != null) |
76 resolved = m_parent.Resolve(reference); | 74 resolved = m_parent.ResolveInternal(reference, args, argc); |
77 | 75 |
78 return resolved; | 76 return resolved; |
79 } | 77 } |
80 | 78 |
81 public Type ProbeInNamespaces(string localName, Type[] args, int argc, bool isArray, string referenceName) { | 79 public Type ProbeInNamespaces(string localName, Type[] args, int argc, bool isArray, string referenceName) { |
82 foreach (var ns in m_namespases) { | 80 foreach (var ns in m_namespases) { |
83 var typeName = FormatName(new [] { ns, localName}, argc, args, isArray); | 81 var typeName = FormatName(new[] { ns, localName }, argc); |
84 | 82 |
85 var resolved = Probe(typeName); | 83 var resolved = Probe(typeName); |
86 if (resolved != null) { | 84 if (resolved != null) { |
85 if (args != null && args.Length > 0) { | |
86 resolved = resolved.MakeGenericType(args); | |
87 } | |
88 | |
89 if (isArray) | |
90 resolved = resolved.MakeArrayType(); | |
91 | |
87 Log("Probe succeed {0} in '{1}': {2} -> {3}", referenceName, ns, typeName, resolved.AssemblyQualifiedName); | 92 Log("Probe succeed {0} in '{1}': {2} -> {3}", referenceName, ns, typeName, resolved.AssemblyQualifiedName); |
88 return resolved; | 93 return resolved; |
89 } else { | 94 } else { |
90 Log("Probe failed {0} in '{1}': {2}", referenceName, ns, typeName); | 95 Log("Probe failed {0} in '{1}': {2}", referenceName, ns, typeName); |
91 } | 96 } |
95 } | 100 } |
96 | 101 |
97 Type Probe(string typeName) { | 102 Type Probe(string typeName) { |
98 var assemblies = AppDomain.CurrentDomain.GetAssemblies(); | 103 var assemblies = AppDomain.CurrentDomain.GetAssemblies(); |
99 | 104 |
100 foreach(var assembly in assemblies) { | 105 foreach (var assembly in assemblies) { |
101 var type = assembly.GetType(typeName); | 106 var type = assembly.GetType(typeName); |
102 if (type != null) | 107 if (type != null) |
103 return type; | 108 return type; |
104 } | 109 } |
105 return null; | 110 return null; |
106 } | 111 } |
107 | 112 |
108 string FormatName(string[] parts, int argc, Type[] args, bool isArray) { | 113 string FormatName(string[] parts, int argc) { |
109 var builder = new StringBuilder(); | 114 var builder = new StringBuilder(); |
110 | 115 |
111 builder.Append(String.Join(".", parts.Where(x => !string.IsNullOrEmpty(x)))); | 116 builder.Append(String.Join(".", parts.Where(x => !string.IsNullOrEmpty(x)))); |
112 if (argc > 0) { | 117 if (argc > 0) { |
113 builder.Append('`'); | 118 builder.Append('`'); |
114 builder.Append(argc); | 119 builder.Append(argc); |
115 } | 120 } |
116 | 121 |
117 if (args!= null && args.Length > 0) { | 122 return builder.ToString(); |
118 builder.Append('['); | |
119 builder.Append(string.Join(",", args.Select(x => $"[{x.AssemblyQualifiedName}]"))); | |
120 builder.Append(']'); | |
121 } | |
122 | |
123 if(isArray) | |
124 builder.Append("[]"); | |
125 | |
126 return builder.ToString(); | |
127 } | 123 } |
128 } | 124 } |
129 } | 125 } |