Merge pull request #1812 from masterofjellyfish/mvc5-missingmethods
[mono.git] / mcs / class / System.Core / Test / System.Linq.Expressions / ExpressionTest_Property.cs
1 // Permission is hereby granted, free of charge, to any person obtaining
2 // a copy of this software and associated documentation files (the
3 // "Software"), to deal in the Software without restriction, including
4 // without limitation the rights to use, copy, modify, merge, publish,
5 // distribute, sublicense, and/or sell copies of the Software, and to
6 // permit persons to whom the Software is furnished to do so, subject to
7 // the following conditions:
8 //
9 // The above copyright notice and this permission notice shall be
10 // included in all copies or substantial portions of the Software.
11 //
12 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
13 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
14 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
15 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
16 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
17 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
18 //
19 // Authors:
20 //              Federico Di Gregorio <fog@initd.org>
21
22 using System;
23 using System.Reflection;
24 using System.Linq;
25 using System.Linq.Expressions;
26 using NUnit.Framework;
27
28 namespace MonoTests.System.Linq.Expressions
29 {
30         [TestFixture]
31         public class ExpressionTest_Property
32         {
33                 [Test]
34                 [ExpectedException (typeof (ArgumentNullException))]
35                 public void Arg1Null ()
36                 {
37                         Expression.Property (null, "NoProperty");
38                 }
39
40                 [Test]
41                 [ExpectedException (typeof (ArgumentNullException))]
42                 public void Arg2Null1 ()
43                 {
44                         Expression.Property (Expression.Constant (new MemberClass()), (string)null);
45                 }
46
47                 [Test]
48                 [ExpectedException (typeof (ArgumentNullException))]
49                 public void Arg2Null2 ()
50                 {
51                         Expression.Property (Expression.Constant (new MemberClass()), (PropertyInfo)null);
52                 }
53
54                 [Test]
55                 [ExpectedException (typeof (ArgumentNullException))]
56                 public void Arg2Null3 ()
57                 {
58                         Expression.Property (Expression.Constant (new MemberClass()), (MethodInfo)null);
59                 }
60
61                 [Test]
62                 [ExpectedException (typeof (ArgumentException))]
63                 public void NoProperty ()
64                 {
65                         Expression.Property (Expression.Constant (new MemberClass()), "NoProperty");
66                 }
67
68                 [Test]
69                 public void InstanceProperty1 ()
70                 {
71                         MemberExpression expr = Expression.Property (Expression.Constant (new MemberClass()), "TestProperty1");
72                         Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#01");
73                         Assert.AreEqual (typeof (int), expr.Type, "Property#02");
74                         Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestProperty1", expr.ToString(), "Property#03");
75                 }
76
77                 [Test]
78                 public void InstanceProperty2 ()
79                 {
80                         MemberExpression expr = Expression.Property (Expression.Constant (new MemberClass()), MemberClass.GetRoPropertyInfo());
81                         Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#04");
82                         Assert.AreEqual (typeof (int), expr.Type, "Property#05");
83                         Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestProperty1", expr.ToString(), "Property#06");
84                 }
85
86                 [Test]
87                 public void InstanceProperty3 ()
88                 {
89                         MethodInfo mi = typeof(MemberClass).GetMethod("get_TestProperty1");
90
91                         MemberExpression expr = Expression.Property (Expression.Constant (new MemberClass()), mi);
92                         Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#07");
93                         Assert.AreEqual (typeof (int), expr.Type, "Property#08");
94                         Assert.AreEqual ("value(MonoTests.System.Linq.Expressions.MemberClass).TestProperty1", expr.ToString(), "Property#09");
95                         Assert.AreEqual (MemberClass.GetRoPropertyInfo(), expr.Member, "Property#10");
96                 }
97
98                 [Test]
99                 [ExpectedException (typeof (ArgumentException))]
100                 public void StaticProperty1 ()
101                 {
102                         // This will fail because access to a static field should be created using a PropertyInfo and
103                         // not an instance plus the field name.
104                         Expression.Property (Expression.Constant (new MemberClass()), "StaticProperty");
105                 }
106
107                 [Test]
108                 public void StaticProperty2 ()
109                 {
110                         MemberExpression expr = Expression.Property (null, MemberClass.GetStaticPropertyInfo());
111                         Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#11");
112                         Assert.AreEqual (typeof (int), expr.Type, "Property#12");
113                         Assert.AreEqual ("MemberClass.StaticProperty", expr.ToString(), "Property#13");
114                 }
115
116                 [Test]
117                 public void StaticProperty3 ()
118                 {
119                         MethodInfo mi = typeof(MemberClass).GetMethod("get_StaticProperty");
120
121                         MemberExpression expr = Expression.Property (null, mi);
122                         Assert.AreEqual (ExpressionType.MemberAccess, expr.NodeType, "Property#14");
123                         Assert.AreEqual (typeof (int), expr.Type, "Property#15");
124                         Assert.AreEqual ("MemberClass.StaticProperty", expr.ToString(), "Property#16");
125                         Assert.AreEqual (MemberClass.GetStaticPropertyInfo(), expr.Member, "Property#17");
126                 }
127
128                 public class Foo {
129                         public string Prop { get; set; }
130
131                         public static string StatProp
132                         {
133                                 get { return "StaticFoo"; }
134                         }
135                 }
136
137                 [Test]
138                 public void TestCompileGetInstanceProperty ()
139                 {
140                         var p = Expression.Parameter (typeof (Foo), "foo");
141                         var fooer = Expression.Lambda<Func<Foo, string>> (
142                                 Expression.Property (p, typeof (Foo).GetProperty ("Prop")), p).Compile ();
143
144                         Assert.AreEqual ("foo", fooer (new Foo { Prop = "foo" }));
145                 }
146
147                 [Test]
148                 public void TestCompileGetStaticProperty ()
149                 {
150                         var sf = Expression.Lambda<Func<string>> (
151                                 Expression.Property (null, typeof (Foo).GetProperty (
152                                 "StatProp", BindingFlags.Public | BindingFlags.Static))).Compile ();
153
154                         Assert.AreEqual ("StaticFoo", sf ());
155                 }
156
157                 public struct Bar {
158                         private string slot;
159
160                         public string Prop {
161                                 get { return slot; }
162                                 set { slot = value; }
163                         }
164
165                         public Bar (string slot)
166                         {
167                                 this.slot = slot;
168                         }
169                 }
170
171                 [Test]
172                 public void TestCompileGetInstancePropertyOnStruct ()
173                 {
174                         var p = Expression.Parameter (typeof (Bar), "bar");
175                         var barer = Expression.Lambda<Func<Bar, string>> (
176                                 Expression.Property (p, typeof (Bar).GetProperty ("Prop")), p).Compile ();
177
178                         Assert.AreEqual ("bar", barer (new Bar ("bar")));
179                 }
180
181                 public static int StaticProperty {
182                         get { return 42; }
183                 }
184
185                 [Test]
186                 [Category ("NotDotNet")] // http://connect.microsoft.com/VisualStudio/feedback/ViewFeedback.aspx?FeedbackID=339351
187                 [ExpectedException (typeof (ArgumentException))]
188                 public void StaticPropertyWithInstanceArgument ()
189                 {
190                         Expression.Property (
191                                 Expression.Parameter (GetType (), "t"),
192                                 GetType ().GetProperty ("StaticProperty"));
193                 }
194         }
195 }