chevron-thin-right chevron-thin-left brand cancel-circle search youtube-icon google-plus-icon linkedin-icon facebook-icon twitter-icon toolbox download check linkedin phone twitter-old google-plus facebook profile-male chat calendar profile-male
0 votes
I have a simple test that merely mocks a class, sets one call expectation, creates a class of that type, then gives that object to a non-mocked class. I then use the non-mocked class to call the expected method on the mocked object.

This test runs fine in VS using testdrivern, but when I try to run it with nant or nunit-console, I get an error stating that the method call is still expected. I have tried variations on strict/non-strict.

Any ideas as to what may cause this?

Mark
asked by madsenma (720 points)

8 Answers

0 votes
Hi Mark,

I have a simple test ...

This test runs fine in VS using testdrivern, but when I try to run it with nant or nunit-console, I get an error stating that the method call is still expected...


Please send an example of the code. This will help us solve the problem
answered by scott (32k points)
0 votes
Upon further investigation I have found that the test works flawlessly in both VS and nunit-console when it is the only test in the suite. If I add additional nunit tests (none of which use typemock, but do instantiate objects that are of the same type as what is mocked in the typemock test) I get inconsistent results. Sometimes the tests pass and sometimes they fail. Here is the test code:

[Test] public void TestOne()
{
MockManager.Init();
Mock aMock = MockManager.Mock(typeof(ClassOne));
aMock.Strict = true;
aMock.ExpectCall("MockedMethod");
ClassOne ClassOneObject = ClassOne.GetAnObject();
ClassTwo classTwoObj = new ClassTwo(ClassOneObject);
classTwoObj.ClassTwoMethod();
MockManager.Verify();
}

ClassOne.GetAnObject() just simply uses a private constructor of ClassOne and returns the new object.

ClassTwoObj.ClassTwoMethod just calls ClassOne.MockedMethod(), nothing else.

-Mark
answered by madsenma (720 points)
0 votes
Hi Mark,
I am actually guessing here.
Please try adding Constructor.StaticNotMocked to the second line as follows:
Mock aMock = MockManager.Mock(typeof(ClassOne),Constructor.StaticNotMocked);

This will make sure that static fields are initialized. I guess that your code is not working because some static fields are not initiliazed due to Typemock mocking this part out.
answered by scott (32k points)
0 votes
Scott-
I tried your suggestion and that did not have any effect. After further investigation it seems that all the tests will pass if and only if I force a rebuild of the entire solution. Then it they will all pass only the first time the tests are run. If I attempt to run the tests a second time without rebuilding everything the typemock test will again fail.

-Mark
answered by madsenma (720 points)
0 votes
Hi Mark

After further investigation it seems that all the tests will pass if and only if I force a rebuild of the entire solution. Then it they will all pass only the first time the tests are run. If I attempt to run the tests a second time without rebuilding everything the typemock test will again fail.


This is very strange as TypeMock does not touch any assemblies, what happens if you don't rebuild, but STOP the testdriven process (Right click the rocket and select End Process)
If the tests fail, it is because the testDriven keeps Jitted Classes in memory, we will need to investigate what object is the problematic one. To do this set MockManager.Log = true - a typemock.out file will be created in the TestDriven program files directory. Do this twice once when the tests work and once when they don't. If we compare the files we can see if the type in question is Jitted - If it doesn't appear it is not jitted.
answered by scott (32k points)
0 votes
Hi,
Please read the previous mail too.

:?: Is ClassOne a singlton, if is is you have to use MockAll. See the Mocking Singleton topic in Testing Methodology & Patterns
answered by scott (32k points)
0 votes
Scott-
Even though the mocked class is definitely not a singleton, using MockAll solved the problem.

-Mark
answered by madsenma (720 points)
0 votes
Scott-
Even though the mocked class is definitely not a singleton, using MockAll solved the problem.

-Mark


Hi Mark,
I am happy that this solved the problem. Perhaps if I explain the difference between Mock and MockAll you will know why this solved the problem.
MockAll will mock ALL instances of a type, including instances that are already alive in the system. Mock will mock only the NEXT instance (or new) of the type. In Factories and Singltons, the instance needed to be mocked is already alive the next time that the test is run, so new won't be called and the mock won't be run.
As a rule it is better to use MockAll unless there are some instances that need to be mocked differently.
We should actually give a better Error when this happens and advice to use MockAll, I will add this to our feature list.
answered by scott (32k points)
...