1 // Licensed to the .NET Foundation under one or more agreements.
2 // See the LICENSE file in the project root for more information.
3 
4 //
5 // ContextStackTest.cs - Unit tests for
6 //	System.ComponentModel.Design.Serialization.ContextStack
7 //
8 // Author:
9 //	Ivan N. Zlatev <contact@i-nz.net>
10 //
11 // Copyright (C) 2007 Ivan N. Zlatev <contact@i-nz.net>
12 //
13 // Permission is hereby granted, free of charge, to any person obtaining
14 // a copy of this software and associated documentation files (the
15 // "Software"), to deal in the Software without restriction, including
16 // without limitation the rights to use, copy, modify, merge, publish,
17 // distribute, sublicense, and/or sell copies of the Software, and to
18 // permit persons to whom the Software is furnished to do so, subject to
19 // the following conditions:
20 //
21 // The above copyright notice and this permission notice shall be
22 // included in all copies or substantial portions of the Software.
23 //
24 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
25 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
26 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
27 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
28 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
29 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
30 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
31 //
32 
33 
34 using System;
35 using System.ComponentModel.Design.Serialization;
36 using Xunit;
37 
38 namespace System.ComponentModel.Tests
39 {
40     public class ContextStackTest
41     {
42         [Fact]
IntegrityTest()43         public void IntegrityTest()
44         {
45             ContextStack stack = new ContextStack();
46 
47             string one = "one";
48             string two = "two";
49             stack.Push(two);
50             stack.Push(one);
51             Assert.Same(one, stack[typeof(string)]);
52             Assert.Same(one, stack[0]);
53             Assert.Same(one, stack.Current);
54 
55             Assert.Same(one, stack.Pop());
56 
57             Assert.Same(two, stack[typeof(string)]);
58             Assert.Same(two, stack[0]);
59             Assert.Same(two, stack.Current);
60 
61             string three = "three";
62             stack.Append(three);
63 
64             Assert.Same(two, stack[typeof(string)]);
65             Assert.Same(two, stack[0]);
66             Assert.Same(two, stack.Current);
67 
68             Assert.Same(two, stack.Pop());
69 
70             Assert.Same(three, stack[typeof(string)]);
71             Assert.Same(three, stack[0]);
72             Assert.Same(three, stack.Current);
73             Assert.Same(three, stack.Pop());
74 
75             Assert.Null(stack.Pop());
76             Assert.Null(stack.Current);
77         }
78 
79         [Fact]
Append_Context_Null()80         public void Append_Context_Null()
81         {
82             ContextStack stack = new ContextStack();
83             ArgumentNullException ex = Assert.Throws<ArgumentNullException>(() => stack.Append(null));
84             Assert.Equal(typeof(ArgumentNullException), ex.GetType());
85             Assert.Null(ex.InnerException);
86             if (!PlatformDetection.IsNetNative) // .Net Native toolchain optimizes away exception messages and paramnames.
87             {
88                 Assert.NotNull(ex.Message);
89                 Assert.Equal("context", ex.ParamName);
90             }
91         }
92 
93         [Fact] // Item (Int32)
Indexer1()94         public void Indexer1()
95         {
96             ContextStack stack = new ContextStack();
97             string one = "one";
98             string two = "two";
99 
100             stack.Push(one);
101             stack.Push(two);
102 
103             Assert.Same(two, stack[0]);
104             Assert.Same(one, stack[1]);
105             Assert.Null(stack[2]);
106             Assert.Same(two, stack.Pop());
107             Assert.Same(one, stack[0]);
108             Assert.Null(stack[1]);
109             Assert.Same(one, stack.Pop());
110             Assert.Null(stack[0]);
111             Assert.Null(stack[1]);
112         }
113 
114         [Fact] // Item (Int32)
Indexer1_Level_Negative()115         public void Indexer1_Level_Negative()
116         {
117             ContextStack stack = new ContextStack();
118             stack.Push(new Foo());
119             ArgumentOutOfRangeException ex;
120 
121             ex = Assert.Throws<ArgumentOutOfRangeException>(() => stack[-1]);
122             Assert.Equal(typeof(ArgumentOutOfRangeException), ex.GetType());
123             Assert.Null(ex.InnerException);
124             if (!PlatformDetection.IsNetNative) // .Net Native toolchain optimizes away exception messages and paramnames.
125             {
126                 Assert.Equal(new ArgumentOutOfRangeException("level").Message, ex.Message);
127                 Assert.Equal("level", ex.ParamName);
128             }
129 
130 
131             ex = Assert.Throws<ArgumentOutOfRangeException>(() => stack[-5]);
132             Assert.Equal(typeof(ArgumentOutOfRangeException), ex.GetType());
133             Assert.Null(ex.InnerException);
134             if (!PlatformDetection.IsNetNative) // .Net Native toolchain optimizes away exception messages and paramnames.
135             {
136                 Assert.Equal(new ArgumentOutOfRangeException("level").Message, ex.Message);
137                 Assert.Equal("level", ex.ParamName);
138             }
139         }
140 
141         [Fact] // Item (Type)
Indexer2()142         public void Indexer2()
143         {
144             ContextStack stack = new ContextStack();
145 
146             Foo foo = new Foo();
147             FooBar foobar = new FooBar();
148 
149             stack.Push(foobar);
150             stack.Push(foo);
151             Assert.Same(foo, stack[typeof(Foo)]);
152             Assert.Same(foo, stack[typeof(IFoo)]);
153             Assert.Same(foo, stack.Pop());
154             Assert.Same(foobar, stack[typeof(Foo)]);
155             Assert.Same(foobar, stack[typeof(FooBar)]);
156             Assert.Same(foobar, stack[typeof(IFoo)]);
157             Assert.Null(stack[typeof(string)]);
158         }
159 
160         [Fact] // Item (Type)
Indexer2_Type_Null()161         public void Indexer2_Type_Null()
162         {
163             ContextStack stack = new ContextStack();
164             stack.Push(new Foo());
165             ArgumentNullException ex = Assert.Throws<ArgumentNullException>(() => stack[(Type)null]);
166             Assert.Equal(typeof(ArgumentNullException), ex.GetType());
167             Assert.Null(ex.InnerException);
168             if (!PlatformDetection.IsNetNative) // .Net Native toolchain optimizes away exception messages and paramnames.
169             {
170                 Assert.NotNull(ex.Message);
171                 Assert.Equal("type", ex.ParamName);
172             }
173         }
174 
175         [Fact]
Push_Context_Null()176         public void Push_Context_Null()
177         {
178             ContextStack stack = new ContextStack();
179             ArgumentNullException ex= Assert.Throws<ArgumentNullException>(()=> stack.Push(null));
180             Assert.Equal(typeof(ArgumentNullException), ex.GetType());
181             Assert.Null(ex.InnerException);
182             if (!PlatformDetection.IsNetNative) // .Net Native toolchain optimizes away exception messages and paramnames.
183             {
184                 Assert.NotNull(ex.Message);
185                 Assert.Equal("context", ex.ParamName);
186             }
187         }
188 
189         public interface IFoo
190         {
191         }
192 
193         public class Foo : IFoo
194         {
195         }
196 
197         public class FooBar : Foo
198         {
199         }
200     }
201 }