10
10
using System ;
11
11
using System . Collections . Concurrent ;
12
12
using System . Collections . Generic ;
13
- using System . Diagnostics . Contracts ;
14
13
using System . Linq ;
15
14
using System . Reflection ;
16
15
using System . Reflection . Emit ;
19
18
#endif
20
19
using static System . Globalization . CultureInfo ;
21
20
using static System . Guid ;
21
+ using static System . Reflection . BindingFlags ;
22
22
using static System . Reflection . Emit . AssemblyBuilderAccess ;
23
23
24
24
/// <summary>
@@ -69,45 +69,80 @@ IDictionary<EdmTypeKey, TypeInfo> GenerateTypesForEdmModel( IEdmModel model, Api
69
69
return ResolveDependencies ( context ) ;
70
70
}
71
71
72
+ static void MapEdmPropertiesToClrProperties (
73
+ IEdmModel edmModel ,
74
+ IEdmStructuredType edmType ,
75
+ Dictionary < string , IEdmProperty > structuralProperties ,
76
+ Dictionary < PropertyInfo , IEdmProperty > mappedClrProperties )
77
+ {
78
+ foreach ( var edmProperty in edmType . Properties ( ) )
79
+ {
80
+ structuralProperties . Add ( edmProperty . Name , edmProperty ) ;
81
+
82
+ var clrProperty = edmModel . GetAnnotationValue < ClrPropertyInfoAnnotation > ( edmProperty ) ? . ClrPropertyInfo ;
83
+
84
+ if ( clrProperty != null )
85
+ {
86
+ mappedClrProperties . Add ( clrProperty , edmProperty ) ;
87
+ }
88
+ }
89
+ }
90
+
72
91
static Type GenerateTypeIfNeeded ( IEdmStructuredType structuredType , BuilderContext context )
73
92
{
74
- var apiVersion = context . ApiVersion ;
75
- var edmTypes = context . EdmTypes ;
76
- var typeKey = new EdmTypeKey ( structuredType , apiVersion ) ;
93
+ var typeKey = new EdmTypeKey ( structuredType , context . ApiVersion ) ;
77
94
78
- if ( edmTypes . TryGetValue ( typeKey , out var generatedType ) )
95
+ if ( context . EdmTypes . TryGetValue ( typeKey , out var generatedType ) )
79
96
{
80
97
return generatedType ;
81
98
}
82
99
83
- var edmModel = context . EdmModel ;
84
- var clrType = structuredType . GetClrType ( edmModel ) ! ;
100
+ var clrType = structuredType . GetClrType ( context . EdmModel ) ! ;
85
101
var visitedEdmTypes = context . VisitedEdmTypes ;
86
102
87
103
visitedEdmTypes . Add ( typeKey ) ;
88
104
89
- const BindingFlags bindingFlags = BindingFlags . Public | BindingFlags . Instance ;
90
-
91
105
var properties = new List < ClassProperty > ( ) ;
92
106
var structuralProperties = new Dictionary < string , IEdmProperty > ( StringComparer . OrdinalIgnoreCase ) ;
93
107
var mappedClrProperties = new Dictionary < PropertyInfo , IEdmProperty > ( ) ;
94
- var clrTypeMatchesEdmType = true ;
95
- var hasUnfinishedTypes = false ;
96
108
var dependentProperties = new List < PropertyDependency > ( ) ;
97
109
98
- foreach ( var property in structuredType . Properties ( ) )
99
- {
100
- structuralProperties . Add ( property . Name , property ) ;
101
-
102
- var clrProperty = edmModel . GetAnnotationValue < ClrPropertyInfoAnnotation > ( property ) ? . ClrPropertyInfo ;
110
+ MapEdmPropertiesToClrProperties ( context . EdmModel , structuredType , structuralProperties , mappedClrProperties ) ;
111
+
112
+ var ( clrTypeMatchesEdmType , hasUnfinishedTypes ) =
113
+ BuildSignatureProperties (
114
+ clrType ,
115
+ structuralProperties ,
116
+ mappedClrProperties ,
117
+ properties ,
118
+ dependentProperties ,
119
+ context ) ;
120
+
121
+ return ResolveType (
122
+ typeKey ,
123
+ clrType ,
124
+ clrTypeMatchesEdmType ,
125
+ hasUnfinishedTypes ,
126
+ properties ,
127
+ dependentProperties ,
128
+ context ) ;
129
+ }
103
130
104
- if ( clrProperty != null )
105
- {
106
- mappedClrProperties . Add ( clrProperty , property ) ;
107
- }
108
- }
131
+ static Tuple < bool , bool > BuildSignatureProperties (
132
+ Type clrType ,
133
+ IReadOnlyDictionary < string , IEdmProperty > structuralProperties ,
134
+ IReadOnlyDictionary < PropertyInfo , IEdmProperty > mappedClrProperties ,
135
+ List < ClassProperty > properties ,
136
+ List < PropertyDependency > dependentProperties ,
137
+ BuilderContext context )
138
+ {
139
+ var edmModel = context . EdmModel ;
140
+ var apiVersion = context . ApiVersion ;
141
+ var visitedEdmTypes = context . VisitedEdmTypes ;
142
+ var clrTypeMatchesEdmType = true ;
143
+ var hasUnfinishedTypes = false ;
109
144
110
- foreach ( var property in clrType . GetProperties ( bindingFlags ) )
145
+ foreach ( var property in clrType . GetProperties ( Public | Instance ) )
111
146
{
112
147
if ( ! structuralProperties . TryGetValue ( property . Name , out var structuralProperty ) &&
113
148
! mappedClrProperties . TryGetValue ( property , out structuralProperty ) )
@@ -178,6 +213,21 @@ static Type GenerateTypeIfNeeded( IEdmStructuredType structuredType, BuilderCont
178
213
properties . Add ( new ClassProperty ( property , propertyType ) ) ;
179
214
}
180
215
216
+ return Tuple . Create ( clrTypeMatchesEdmType , hasUnfinishedTypes ) ;
217
+ }
218
+
219
+ static TypeInfo ResolveType (
220
+ EdmTypeKey typeKey ,
221
+ Type clrType ,
222
+ bool clrTypeMatchesEdmType ,
223
+ bool hasUnfinishedTypes ,
224
+ List < ClassProperty > properties ,
225
+ List < PropertyDependency > dependentProperties ,
226
+ BuilderContext context )
227
+ {
228
+ var apiVersion = context . ApiVersion ;
229
+ var edmTypes = context . EdmTypes ;
230
+
181
231
TypeInfo type ;
182
232
183
233
if ( clrTypeMatchesEdmType )
@@ -240,6 +290,7 @@ static TypeBuilder CreateTypeBuilderFromSignature( ModuleBuilder moduleBuilder,
240
290
ref var property = ref properties [ i ] ;
241
291
var type = property . Type ;
242
292
var name = property . Name ;
293
+
243
294
AddProperty ( typeBuilder , type , name , property . Attributes ) ;
244
295
}
245
296
@@ -253,15 +304,15 @@ static IDictionary<EdmTypeKey, TypeInfo> ResolveDependencies( BuilderContext con
253
304
254
305
for ( var i = 0 ; i < dependencies . Count ; i ++ )
255
306
{
256
- var propertyDependency = dependencies [ i ] ;
257
- var dependentOnType = edmTypes [ propertyDependency . DependentOnTypeKey ] ;
307
+ var dependency = dependencies [ i ] ;
308
+ var dependentOnType = edmTypes [ dependency . DependentOnTypeKey ] ;
258
309
259
- if ( propertyDependency . IsCollection )
310
+ if ( dependency . IsCollection )
260
311
{
261
312
dependentOnType = IEnumerableOfT . MakeGenericType ( dependentOnType ) . GetTypeInfo ( ) ;
262
313
}
263
314
264
- AddProperty ( propertyDependency . DependentType ! , dependentOnType , propertyDependency . PropertyName , propertyDependency . CustomAttributes ) ;
315
+ AddProperty ( dependency . DependentType ! , dependentOnType , dependency . PropertyName , dependency . CustomAttributes ) ;
265
316
}
266
317
267
318
var keys = edmTypes . Keys . ToArray ( ) ;
@@ -338,7 +389,7 @@ internal BuilderContext( IEdmModel edmModel, ApiVersion apiVersion, Func<ModuleB
338
389
339
390
internal IDictionary < EdmTypeKey , TypeInfo > EdmTypes { get ; } = new Dictionary < EdmTypeKey , TypeInfo > ( ) ;
340
391
341
- internal ICollection < EdmTypeKey > VisitedEdmTypes { get ; } = new HashSet < EdmTypeKey > ( ) ;
392
+ internal ISet < EdmTypeKey > VisitedEdmTypes { get ; } = new HashSet < EdmTypeKey > ( ) ;
342
393
343
394
internal IList < PropertyDependency > Dependencies { get ; } = new List < PropertyDependency > ( ) ;
344
395
}
0 commit comments