1- using System ;
2- using System . Linq . Expressions ;
3- using System . Reflection ;
4- using RefactorThis . GraphDiff . Internal . Graph ;
5-
6- namespace RefactorThis . GraphDiff . Internal
7- {
8- /// <summary>
9- /// Reads an IUpdateConfiguration mapping and produces an GraphNode graph.
10- /// </summary>
11- /// <typeparam name="T"></typeparam>
12- internal class ConfigurationVisitor < T > : ExpressionVisitor
13- {
14- private GraphNode _currentMember ;
15- private string _currentMethod = "" ;
16-
17- public GraphNode GetNodes ( Expression < Func < IUpdateConfiguration < T > , object > > expression )
18- {
19- var initialNode = new GraphNode ( ) ;
20- _currentMember = initialNode ;
21- Visit ( expression ) ;
22- return initialNode ;
23- }
24-
25- protected override Expression VisitMember ( MemberExpression memberExpression )
26- {
27- var accessor = GetMemberAccessor ( memberExpression ) ;
28- var newMember = CreateNewMember ( accessor ) ;
29-
30- _currentMember . Members . Push ( newMember ) ;
31- _currentMember = newMember ;
32-
33- return base . VisitMember ( memberExpression ) ;
34- }
35-
36- protected override Expression VisitMethodCall ( MethodCallExpression expression )
37- {
38- _currentMethod = expression . Method . Name ;
39-
40- // go left to right in the subtree (ignore first argument for now)
41- for ( int i = 1 ; i < expression . Arguments . Count ; i ++ )
42- {
43- Visit ( expression . Arguments [ i ] ) ;
44- }
45-
46- // go back up the tree and continue
47- _currentMember = _currentMember . Parent ;
48- return Visit ( expression . Arguments [ 0 ] ) ;
49- }
50-
51- private GraphNode CreateNewMember ( PropertyInfo accessor )
52- {
53- GraphNode newMember ;
54- switch ( _currentMethod )
55- {
56- case "OwnedEntity" :
57- newMember = new OwnedEntityGraphNode ( _currentMember , accessor ) ;
58- break ;
59- case "AssociatedEntity" :
60- newMember = new AssociatedEntityGraphNode ( _currentMember , accessor ) ;
61- break ;
62- case "OwnedCollection" :
63- newMember = new CollectionGraphNode ( _currentMember , accessor , true ) ;
64- break ;
65- case "AssociatedCollection" :
66- newMember = new CollectionGraphNode ( _currentMember , accessor , false ) ;
67- break ;
68- default :
69- throw new NotSupportedException ( "The method used in the update mapping is not supported" ) ;
70- }
71- return newMember ;
72- }
73-
74- private static PropertyInfo GetMemberAccessor ( MemberExpression memberExpression )
75- {
76- PropertyInfo accessor = null ;
77- var expression = memberExpression . Expression ;
78- var constantExpression = expression as ConstantExpression ;
79-
80- if ( constantExpression != null )
81- {
82- var container = constantExpression . Value ;
83- var member = memberExpression . Member ;
84-
85- var fieldInfo = member as FieldInfo ;
86- if ( fieldInfo != null )
87- {
88- dynamic value = fieldInfo . GetValue ( container ) ;
89- accessor = ( PropertyInfo ) value . Body . Member ;
90- }
91-
92- var info = member as PropertyInfo ;
93- if ( info != null )
94- {
95- dynamic value = info . GetValue ( container , null ) ;
96- accessor = ( PropertyInfo ) value . Body . Member ;
97- }
98- }
99- else
100- {
101- accessor = ( PropertyInfo ) memberExpression . Member ;
102- }
103-
104- if ( accessor == null )
105- throw new NotSupportedException ( "Unknown accessor type found!" ) ;
106-
107- return accessor ;
108- }
109- }
1+ using System ;
2+ using System . Linq . Expressions ;
3+ using System . Reflection ;
4+ using RefactorThis . GraphDiff . Internal . Graph ;
5+
6+ namespace RefactorThis . GraphDiff . Internal
7+ {
8+ /// <summary>
9+ /// Reads an IUpdateConfiguration mapping and produces an GraphNode graph.
10+ /// </summary>
11+ /// <typeparam name="T"></typeparam>
12+ internal class ConfigurationVisitor < T > : ExpressionVisitor
13+ {
14+ private GraphNode _currentMember ;
15+ private string _currentMethod = "" ;
16+
17+ public GraphNode GetNodes ( Expression < Func < IUpdateConfiguration < T > , object > > expression )
18+ {
19+ var initialNode = new GraphNode ( ) ;
20+ _currentMember = initialNode ;
21+ Visit ( expression ) ;
22+ return initialNode ;
23+ }
24+
25+ protected override Expression VisitMember ( MemberExpression memberExpression )
26+ {
27+ var accessor = GetMemberAccessor ( memberExpression ) ;
28+ var newMember = CreateNewMember ( accessor ) ;
29+
30+ _currentMember . Members . Push ( newMember ) ;
31+ _currentMember = newMember ;
32+
33+ return base . VisitMember ( memberExpression ) ;
34+ }
35+
36+ protected override Expression VisitMethodCall ( MethodCallExpression expression )
37+ {
38+ _currentMethod = expression . Method . Name ;
39+
40+ // go left to right in the subtree (ignore first argument for now)
41+ for ( int i = 1 ; i < expression . Arguments . Count ; i ++ )
42+ {
43+ Visit ( expression . Arguments [ i ] ) ;
44+ }
45+
46+ // go back up the tree and continue
47+ _currentMember = _currentMember . Parent ;
48+ return Visit ( expression . Arguments [ 0 ] ) ;
49+ }
50+
51+ private GraphNode CreateNewMember ( PropertyInfo accessor )
52+ {
53+ GraphNode newMember ;
54+ switch ( _currentMethod )
55+ {
56+ case "OwnedEntity" :
57+ newMember = new OwnedEntityGraphNode ( _currentMember , accessor ) ;
58+ break ;
59+ case "AssociatedEntity" :
60+ newMember = new AssociatedEntityGraphNode ( _currentMember , accessor ) ;
61+ break ;
62+ case "OwnedCollection" :
63+ newMember = new CollectionGraphNode ( _currentMember , accessor , true ) ;
64+ break ;
65+ case "AssociatedCollection" :
66+ newMember = new CollectionGraphNode ( _currentMember , accessor , false ) ;
67+ break ;
68+ default :
69+ throw new NotSupportedException ( "The method used in the update mapping is not supported" ) ;
70+ }
71+ return newMember ;
72+ }
73+
74+ private static PropertyInfo GetMemberAccessor ( MemberExpression memberExpression )
75+ {
76+ PropertyInfo accessor = null ;
77+ var expression = memberExpression . Expression ;
78+ var constantExpression = expression as ConstantExpression ;
79+
80+ if ( constantExpression != null )
81+ {
82+ var container = constantExpression . Value ;
83+ var member = memberExpression . Member ;
84+
85+ var fieldInfo = member as FieldInfo ;
86+ if ( fieldInfo != null )
87+ {
88+ dynamic value = fieldInfo . GetValue ( container ) ;
89+ accessor = ( PropertyInfo ) value . Body . Member ;
90+ }
91+
92+ var info = member as PropertyInfo ;
93+ if ( info != null )
94+ {
95+ dynamic value = info . GetValue ( container , null ) ;
96+ accessor = ( PropertyInfo ) value . Body . Member ;
97+ }
98+ }
99+ else
100+ {
101+ accessor = ( PropertyInfo ) memberExpression . Member ;
102+ }
103+
104+ if ( accessor == null )
105+ throw new NotSupportedException ( "Unknown accessor type found!" ) ;
106+
107+ return accessor ;
108+ }
109+ }
110110}
0 commit comments