#region License /* * Copyright 2002-2010 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #endregion #region Imports using System; using NUnit.Framework; using Spring.Core; #endregion namespace Spring.Objects.Support { /// <summary> /// Unit tests for the MethodInvoker class. /// </summary> /// <author>Rick Evans</author> [TestFixture] public sealed class MethodInvokerTests { [Test] public void Instantiation() { MethodInvoker vkr = new MethodInvoker(); Assert.IsNotNull(vkr.Arguments); } [Test] public void SettingNamedArgumentsToNullJustClearsOutAnyNamedArguments() { MethodInvoker vkr = new MethodInvoker(); vkr.AddNamedArgument("age", 10); vkr.NamedArguments = null; Assert.IsNotNull(vkr.NamedArguments); Assert.AreEqual(0, vkr.NamedArguments.Count); } [Test] public void PrepareWithOnlyTargetMethodSet() { MethodInvoker vkr = new MethodInvoker(); vkr.TargetMethod = "Foo"; Assert.Throws<ArgumentException>(() => vkr.Prepare(), "One of either the 'TargetType' or 'TargetObject' properties is required."); } [Test] public void ArgumentsProperty() { MethodInvoker vkr = new MethodInvoker(); vkr.Arguments = null; Assert.IsNotNull(vkr.Arguments); // should always be the empty object array, never null Assert.AreEqual(0, vkr.Arguments.Length); vkr.Arguments = new string[] {"Chank Pop"}; Assert.AreEqual(1, vkr.Arguments.Length); } [Test] public void InvokeWithStaticMethod() { MethodInvoker mi = new MethodInvoker(); mi.TargetType = typeof(Int32); mi.TargetMethod = "Parse"; mi.Arguments = new object[] { "27" }; mi.Prepare(); object actual = mi.Invoke(); Assert.IsNotNull(actual); Assert.AreEqual(typeof(int), actual.GetType()); Assert.AreEqual(27, (int)actual); } [Test] public void InvokeWithGenericStaticMethod() { MethodInvoker mi = new MethodInvoker(); mi.TargetType = typeof(Activator); mi.TargetMethod = "CreateInstance<Spring.Objects.TestObject>"; mi.Prepare(); object actual = mi.Invoke(); Assert.IsNotNull(actual); Assert.AreEqual(typeof(TestObject), actual.GetType()); } [Test] public void InvokeWithOKArguments() { Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "GrowOlder"; vkr.Arguments = new object[] {10}; vkr.Prepare(); object actual = vkr.Invoke(); Assert.AreEqual(98, actual); } [Test] public void InvokeWithOKArgumentsAndMixedCaseMethodName() { Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "growolder"; vkr.Arguments = new object[] {10}; vkr.Prepare(); object actual = vkr.Invoke(); Assert.AreEqual(98, actual); } [Test] public void InvokeWithNamedArgument() { Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "growolder"; vkr.AddNamedArgument("years", 10); vkr.Prepare(); object actual = vkr.Invoke(); Assert.AreEqual(98, actual); } [Test] public void InvokeWithMixOfNamedAndPlainVanillaArguments() { int maximumAge = 95; Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "GrowOlderUntilMaximumAgeReached"; vkr.AddNamedArgument("years", 10); vkr.Arguments = new object[] {maximumAge}; vkr.Prepare(); object actual = vkr.Invoke(); Assert.AreEqual(maximumAge, actual); } [Test] public void InvokeWithMixOfNamedAndPlainVanillaArgumentsOfDifferingTypes() { int maximumAge = 95; string expectedStatus = "Old Age Pensioner"; Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "GrowOlderUntilMaximumAgeReachedAndSetStatusName"; vkr.AddNamedArgument("years", 10); vkr.AddNamedArgument("status", expectedStatus); vkr.Arguments = new object[] {maximumAge}; vkr.Prepare(); object actual = vkr.Invoke(); Assert.AreEqual(maximumAge, actual); Assert.AreEqual(expectedStatus, foo.Status); } [Test] public void InvokeWithNamedArgumentThatDoesNotExist() { Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "growolder"; vkr.AddNamedArgument("southpaw", 10); Assert.Throws<ArgumentException>(() => vkr.Prepare(), "The named argument 'southpaw' could not be found on the 'GrowOlder' method of class [Spring.Objects.Support.MethodInvokerTests+Foo]."); } /// <summary> /// Tests CLS case insensitivity compliance... /// </summary> [Test] public void InvokeWithWeIRdLyCasedNamedArgument() { Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "gROwOldeR"; vkr.AddNamedArgument("YEarS", 10); vkr.Prepare(); object actual = vkr.Invoke(); Assert.AreEqual(98, actual); } [Test] public void InvokeWithArgumentOfWrongType() { Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "growolder"; vkr.AddNamedArgument("years", "Bingo"); vkr.Prepare(); Assert.Throws<MethodInvocationException>(() => vkr.Invoke(), "At least one of the arguments passed to this MethodInvoker was incompatible with the signature of the invoked method."); } [Test] public void NamedArgumentsOverwriteEachOther() { Foo foo = new Foo(); foo.Age = 88; MethodInvoker vkr = new MethodInvoker(); vkr.TargetObject = foo; vkr.TargetMethod = "growolder"; vkr.AddNamedArgument("years", 10); // this second setting must overwrite the first... vkr.AddNamedArgument("years", 200); vkr.Prepare(); object actual = vkr.Invoke(); Assert.IsFalse(98.Equals(actual), "The first named argument setter is sticking; must allow itslf to be overwritten."); Assert.AreEqual(288, actual, "The second named argument was not applied (it must be)."); } [Test] public void PreparedArgumentsIsNeverNull() { MyMethodInvoker vkr = new MyMethodInvoker(); Assert.IsNotNull(vkr.GetPreparedArguments(), "PreparedArguments is null even before Prepare() is called; must NEVER be null."); vkr.NullOutPreparedArguments(); Assert.IsNotNull(vkr.GetPreparedArguments(), "PreparedArguments should revert to the empty object[] when set to null; must NEVER be null."); } #region Inner Class : Foo private sealed class Foo { public Foo() { Age = 0; Status = "Baby"; } public int GrowOlder() { return GrowOlder(1); } public int GrowOlder(int years) { _age += years; return _age; } public int GrowOlderUntilMaximumAgeReached(int years, int maximumAge) { _age += years; if (_age > maximumAge) { _age = maximumAge; } return _age; } public int GrowOlderUntilMaximumAgeReachedAndSetStatusName( int years, int maximumAge, string status) { Status = status; return GrowOlderUntilMaximumAgeReached(years, maximumAge); } private int _age; private string _status; public int Age { get { return _age; } set { _age = value; } } public string Status { get { return _status; } set { _status = value; } } } #endregion #region Inner Class : MyMethodInvoker private sealed class MyMethodInvoker : MethodInvoker { public MyMethodInvoker() { } public void NullOutPreparedArguments() { PreparedArguments = null; } public object[] GetPreparedArguments() { return PreparedArguments; } } #endregion } }