3

Has anyone successfully managed to run unit tests for their Monotouch project? I have read other posts where people are told to manually add references to the appropriate assemblies. Doing this makes the project compile, but it will still not run the tests.

I have a solution with two projects; a Monotouch Navigation project and an NUnit Library Project. I added a reference to my monotouch project and to the monotouch and other needed assemblies to the test project. Tests that only runs code outside the monotouch assembly will run fine, the ones that accesses monotouch code fails with:

System.IO.IOException: Write failure ---> System.Net.Sockets.SocketException: The socket has been shut down at System.Net.Sockets.Socket.Send (System.Byte[] buf, Int32 offset, Int32 size, SocketFlags flags) [0x00000] in :0 at System.Net.Sockets.NetworkStream.Write (System.Byte[] buffer, Int32 offset, Int32 size) [0x00000] in :0 --- End of inner exception stack trace --- at System.Net.Sockets.NetworkStream.Write (System.Byte[] buffer, Int32 offset, Int32 size) [0x00000] in :0 at System.IO.BufferedStream.Flush () [0x00000] in :0 at (wrapper remoting-invoke-with-check) System.IO.BufferedStream:Flush () at System.IO.BufferedStream.Dispose (Boolean disposing) [0x00000] in :0 at System.IO.Stream.Close () [0x00000] in :0 at Mono.Remoting.Channels.Unix.ClientConnection.ProcessMessages () [0x00000] in :0

I found a post saying: "..if you're not running on the iPhone or in the iPhone simulator, there's no way to call the necessary native APIs to instantiate the components.."

So what I´m really wondering is if it´s actually possible to do unit testing in Monotouch at the moment, or if not, what all you other guys do?

Thanks!

Community
  • 1
  • 1
TenaciousG
  • 139
  • 8

4 Answers4

2

You don't actually have to create a second solution, or pull out OS-agnostic code. There are a few tricks to it though. Generally:

  1. Reference the MonoTouch assemblies, even in your .Net 3.5/Mono Test Projects
  2. A Supervisor Controller pattern helps with the amount of code you can test.

Have written up a few details on what we have found to be best practice so far. You can find it here: http://ben.phegan.name/index.php/2011/02/28/monotouch-and-unit-testing.

Ben Phegan
  • 505
  • 3
  • 6
  • Good post! In there you say: "..the primary issue that most people have with testing under MonoTouch, is that by default they reach for the “Add…Add New Project…NUnit Library Project”. ", but I couldn´t see you describing a preferred way of doing it. I tried adding all the references to the correct assemblies in the /Developer..... folder and making the paths absolute, but running them still crashed with the System.Net.Sockets.SocketException: The socket has been shut down. I haven´t gotten around to the Supervisor Controller pattern yet, but it sounds like a good idea! – TenaciousG Mar 01 '11 at 11:19
  • Sounds like something you are testing is still hooking something from monotouch.dll (or trying). I didn't recommend another way of adding a Unit Test Project, as the default is still probably the easiest, with the caveat that you need to be clean on your interfaces to MonoTouch code and be clear on the references you need. A better solution would be to have a specific "MonoTouch Unit Test" project. This isn't available yet, although it is open source if you are keen! :) – Ben Phegan Mar 02 '11 at 10:51
  • Ok, I misunderstood your "Fixing references" bit, thinking it would actually allow for testing of code using the monotouch.dll as well. Will try implementing the Supervisor Controller pattern as described in your blog. – TenaciousG Mar 06 '11 at 17:47
2

Has anyone successfully managed to run unit tests for their Monotouch project?

Yes this is now possible with the latest MonoTouch 5.1.x (beta) releases.

I found a post saying: "..if you're not running on the iPhone or in the iPhone simulator, there's no way to call the necessary native APIs to instantiate the components.."

That's true. This is why a runner, executing on iOS (simulator or devices), was built to enable the execution of MonoTouch related unit tests.

Community
  • 1
  • 1
poupou
  • 43,413
  • 6
  • 77
  • 174
0

Yes, it is possible.

The Xamarin Docs Team has added a document on using the built-in unit tests template, which operates using a modified version of the NUnitLite project.

pierceboggan
  • 317
  • 5
  • 21
0

That was my post you found. So far this is the best I've been able to do:

  1. Pull the OS-agnostic code out into separate libraries.
  2. Create a second solution, with its own project files, to compile those libraries as vanilla .NET 3.5.
  3. Unit-test the libraries.

On the bright side, this encourages separating your concerns and (in theory) should it easier to port the app to, say, MonoDroid. But keeping the two solutions in sync is a pain, and it's easy to drift away from actually writing tests when they're out of sight.

David Moles
  • 48,006
  • 27
  • 136
  • 235
  • So far I have tried to separate the OS code from the rest so that I can get most of my code unit testable, however it´s quite annoying that I can´t properly test my controllers and that I can´t have my end to end tests. I am going to try out the pattern mentioned in Phegan´s post, and hopefully also get the references right so that I get my monotouch code tested. – TenaciousG Mar 01 '11 at 11:29