I downloaded TestDriven.Net a free tool that integrates with Visual Studio to make Unit Testing easier. You have to register and there is a survey to take before you can download.
After installing the add-in I added my test class to the project. Previously I had been keeping it separate. I also added a reference to nunit.framework.dll in the project. After this I right clicked on the TestCalculator.cs file in the Solution Explorer and chose Run Test(s). It ran immediately and 0.11 seconds later the results were ready...
------ Test started: Assembly: calc.exe ------
18 succeeded, 0 failed, 0 skipped, took 0.11 seconds.
---------------------- Done ----------------------
But alas, no green bar! The output is just not as pretty. Well I suppose that would be difficult to do.
Then I made one of the tests fail by asserting that it would get the wrong value. Again the output was not as pretty as in NUnit.
------ Test started: Assembly: calc.exe ------
TestCase 'NUnitTest.TestClass.DisplayInitialisesToZero' failed:
String lengths differ. Expected length=2, but was length=1.
Strings differ at index 1.
expected:<"01">
but was:<"0">
------------^
d:\source\c#\calc\calc\testcalculator.cs(25,0):
at NUnitTest.TestClass.DisplayInitialisesToZero()
17 succeeded, 1 failed, 0 skipped, took 0.12 seconds.
---------------------- Done ----------------------
This gives you exactly the same information you'd get in the NUnit GUI, except there is no red/green bar. It would be nice if the output was more graphical, but even so, it is much better to have the tests running inside Visual Studio.
21 April 2005
20 April 2005
Other things
Lots of people are talking about things that are mostly not .NET...
Ruby on Rails which is an open source web framework
And Google maps which is now available in the UK.
And there is even a .NET wrapper .dll for AJAX
Ruby on Rails which is an open source web framework
And Google maps which is now available in the UK.
And there is even a .NET wrapper .dll for AJAX
16 April 2005
Music software
It's amazing what you can do with a PC these days. It seems all you need to buy in the way of music hardware is a MIDI keyboard.
Free software from Psycle
Free software from Psycle
Personal Web sites
The Personal Web Site Starter Kit is a Microsoft tool for creating personal websites.
More testing tools
Fit is a tool for unit testing. It can be used collaboratively to create user acceptance tests. The results appear as a web page. Fit was created by WardCunningham. It is free to download.
TestDriven.net is a tool for unit testing that integrates with the Visual Studio IDE. I've downloaded it and will be trying it out.
TestDriven.net is a tool for unit testing that integrates with the Visual Studio IDE. I've downloaded it and will be trying it out.
13 April 2005
TDD continued
Now my new calculator is working I have 18 tests and they all pass. I have deliberately not thought about the design too much.
There is quite a bit of duplication in the code. I'm tidying it up. It's almost refactoring, but as there is only one little class, really it's just reviewing the software as a whole. Up till now I'd been looking at just the functionality I was adding to satisfy each new test. This lead to a working program, but not one that I'd be proud to display.
To start with I moved any common code into new methods and then recompiled and ran my tests. Occasionally this warned me that I was introducing a bug and I was able to roll back and see that indeed the tests were right and it was not quite common code after all.
Then I reviewed the names I'd used. Some of them were pretty vague so I gave each method property or variable a meaningful name. The tests confirmed everything still worked.
What I plan to do now is to work on something else for a week or so, then come back to this project and try to add some more functionality. Perhaps I'll add some memory keys. The idea is that the tests should make it easy to continue development.
I added some comments as I was coding, but now I have removed these. The theory is that you don't need comments if you have unit tests and readable code. We shall see...
There is quite a bit of duplication in the code. I'm tidying it up. It's almost refactoring, but as there is only one little class, really it's just reviewing the software as a whole. Up till now I'd been looking at just the functionality I was adding to satisfy each new test. This lead to a working program, but not one that I'd be proud to display.
To start with I moved any common code into new methods and then recompiled and ran my tests. Occasionally this warned me that I was introducing a bug and I was able to roll back and see that indeed the tests were right and it was not quite common code after all.
Then I reviewed the names I'd used. Some of them were pretty vague so I gave each method property or variable a meaningful name. The tests confirmed everything still worked.
What I plan to do now is to work on something else for a week or so, then come back to this project and try to add some more functionality. Perhaps I'll add some memory keys. The idea is that the tests should make it easy to continue development.
I added some comments as I was coding, but now I have removed these. The theory is that you don't need comments if you have unit tests and readable code. We shall see...
12 April 2005
Unit Testing Notes
The continuing story of my attempts at Test Driven Development...
I'm now writing a GUI application, a simple calculator. Windows needs a new calculator.
I've structured the application so that all the logic is in a calculator.dll file, the GUI only handles input and output, just as it should. This means I can have a separate test class to test the logic of my calculator.dll. I've used some modified sample code to add an array of buttons to the calculator form dynamically when it loads. This is in a buttonarray.cs file, which I'm not testing as it is part of the GUI.
After years of writing code first and then (maybe) writing tests a lot later, it is a very difficult habit to work against. This time I forced myself to write a unit test first, test it to see that result was red, and then start writing code to turn it green.
The first few tests felt really odd; it was a bit like trying drive somewhere using only reverse gear. Once I had about 10 tests done, and had run out of short term memory to recall exactly what they were, it started to feel more sensible to add another test as a way of starting on the next bit of the problem.
I deliberately didn't spend any time on restructuring or refactorinng the code, I took the approach that if it passed the test then it was complete.
It is true, each time you run the tests and the result is green, it does begin to give you more confidence that the latest change hasn't broken anything. And, when I did break the code trying to handle a particular condition, I was able to roll back a bit and start again.
This does mean that you really can focus on just the problem at hand, the new tiny bit of functionality you are trying to add, because you don't need to worry about breaking anything. If you break it, you will know. It feels a lot safer changing the code, when your tests are automated. It only takes seconds to run all those tests again.
I can see unit tests have some real benefits, so far I am not sure about some of the other claimed benefits.
I'm now writing a GUI application, a simple calculator. Windows needs a new calculator.
I've structured the application so that all the logic is in a calculator.dll file, the GUI only handles input and output, just as it should. This means I can have a separate test class to test the logic of my calculator.dll. I've used some modified sample code to add an array of buttons to the calculator form dynamically when it loads. This is in a buttonarray.cs file, which I'm not testing as it is part of the GUI.
After years of writing code first and then (maybe) writing tests a lot later, it is a very difficult habit to work against. This time I forced myself to write a unit test first, test it to see that result was red, and then start writing code to turn it green.
The first few tests felt really odd; it was a bit like trying drive somewhere using only reverse gear. Once I had about 10 tests done, and had run out of short term memory to recall exactly what they were, it started to feel more sensible to add another test as a way of starting on the next bit of the problem.
I deliberately didn't spend any time on restructuring or refactorinng the code, I took the approach that if it passed the test then it was complete.
It is true, each time you run the tests and the result is green, it does begin to give you more confidence that the latest change hasn't broken anything. And, when I did break the code trying to handle a particular condition, I was able to roll back a bit and start again.
This does mean that you really can focus on just the problem at hand, the new tiny bit of functionality you are trying to add, because you don't need to worry about breaking anything. If you break it, you will know. It feels a lot safer changing the code, when your tests are automated. It only takes seconds to run all those tests again.
I can see unit tests have some real benefits, so far I am not sure about some of the other claimed benefits.
04 April 2005
Unit Testing with NUnit
I downloaded NUnit version 2.2.0. To test that it was working properly I opened the bin\nunit.tests.dll and ran them. NUnit performed 605 tests which all passed so I guess it must work.
I started following Ron Jefferies Unit Testing examples. I got stuck because they didn't seem to work. It was telling me that .Assertion was deprecated and I should use .Assert instead. I didn't really want to get stuck on this so I decided to look for another "Getting Started" article.
I found an article on Unit Testing with C# on 4GuysFromRolla which has some sample code.
At first the TestClass wouldn't compile as the Person class was not visible. Anyway when I changed it to public I was able to compile it.
Then I tried modifying the Person class to be a Dice class with a single method Roll(), to roll the dice and return an integer, and a single property, Max to define the maximum value. I should have written the tests first.
To compile my dice class and it's test class I created a .bat file as follows:
csc /target:library dice.cs
csc /target:library /reference:nunit.framework.dll /reference:dice.dll TestDice.cs
The TestDice class references both the nunit testing framework and the dice.dll I want to create. Both .cs files are compiled as .dll's.
I wrote a test for the Max property and ran NUnit.
It was at this point that it dawned on me that choosing a dice as my first class to test was a bit daft. How do I test the roll method? The output is going to be random, I hope. I thought about testing the distribution of a number of rolls, but that would really be testing the random number generator from the .NET framework rather than testing my code. I decided I needed to test what I'm doing with the random numbers instead, whether I am scaling them correctly. Are the results in range?
I guess most of the time you are testing things that are repeatable or shouldn't be random. I decided to call the Roll() method a 100 times and check the maximum like this:-
If I'm unlucky this could fail but most of the time it should pass. For some reason it was failing.
From having the Roll() method write a value to console and examining the Console output in NUnit I found out that I needed to create my Random object not in the Roll method but at the Dice object level, so that it is seeded once when the Dice is instantiated, not everytime Roll() is called. Otherwise with frequent calls you get the same seed value repeated for a while and then a new value.
I wrote a test for a Minimum property and found that I hadn't initialised it so the dice was actually rolling values from 0 to 6. After fixing that all the tests passed.
The code so far is…
TestDice.cs:
Dice.cs:
After this I went outside and planted three rows of potatoes because man cannot live by software alone...
I started following Ron Jefferies Unit Testing examples. I got stuck because they didn't seem to work. It was telling me that .Assertion was deprecated and I should use .Assert instead. I didn't really want to get stuck on this so I decided to look for another "Getting Started" article.
I found an article on Unit Testing with C# on 4GuysFromRolla which has some sample code.
At first the TestClass wouldn't compile as the Person class was not visible. Anyway when I changed it to public I was able to compile it.
Then I tried modifying the Person class to be a Dice class with a single method Roll(), to roll the dice and return an integer, and a single property, Max to define the maximum value. I should have written the tests first.
To compile my dice class and it's test class I created a .bat file as follows:
csc /target:library dice.cs
csc /target:library /reference:nunit.framework.dll /reference:dice.dll TestDice.cs
The TestDice class references both the nunit testing framework and the dice.dll I want to create. Both .cs files are compiled as .dll's.
I wrote a test for the Max property and ran NUnit.
[Test]public void IsMax6()It succeeded.
{
Assert.AreEqual(6,dTest.Max);
}
It was at this point that it dawned on me that choosing a dice as my first class to test was a bit daft. How do I test the roll method? The output is going to be random, I hope. I thought about testing the distribution of a number of rolls, but that would really be testing the random number generator from the .NET framework rather than testing my code. I decided I needed to test what I'm doing with the random numbers instead, whether I am scaling them correctly. Are the results in range?
I guess most of the time you are testing things that are repeatable or shouldn't be random. I decided to call the Roll() method a 100 times and check the maximum like this:-
[Test]public void isMaxRolled()
{
int j;
int maxRolled =
dTest.Min;
for(int i=0; i < j =" dTest.Roll();"> maxRolled)
{
maxRolled = j;
}
}
Assert.AreEqual(dTest.Max,maxRolled);
}
If I'm unlucky this could fail but most of the time it should pass. For some reason it was failing.
From having the Roll() method write a value to console and examining the Console output in NUnit I found out that I needed to create my Random object not in the Roll method but at the Dice object level, so that it is seeded once when the Dice is instantiated, not everytime Roll() is called. Otherwise with frequent calls you get the same seed value repeated for a while and then a new value.
I wrote a test for a Minimum property and found that I hadn't initialised it so the dice was actually rolling values from 0 to 6. After fixing that all the tests passed.
The code so far is…
TestDice.cs:
using System;
namespace NUnitTest
{
using NUnit.Framework;
///
/// TestDice for testing dice.dll
///
[TestFixture]
public class TestClass
{
Dice dTest;
public TestClass()
{
// TODO: Add constructor logic here
}
[SetUp]public void Init()
{
dTest = new Dice(1,6);
}
[Test]public void IsMax6()
{
Assert.AreEqual(6,dTest.Max);
}
[Test]public void IsMin1()
{
Assert.AreEqual(1,dTest.Min);
}
[Test]public void isMaxRolled()
{
int j;
int maxRolled = 0;
for(int i=0; i < j =" dTest.Roll();"> maxRolled)
{
maxRolled = j;
}
}
Assert.AreEqual(dTest.Max,maxRolled);
}
[Test]public void isMinRolled()
{
int j;
int minRolled =
dTest.Max;
for(int i=0; i < j =" dTest.Roll();" minrolled =" j;">
Dice.cs:
using System;
namespace NUnitTest
{
///
/// Dice - Random number generator.
///
public class Dice
{
int max;
int min;
Random
autoRand = new Random( );
[STAThread]
static void Main(string[] args)
{
Dice d = new
Dice(1,6);
}
Dice()
{
min = 1;
max = 6;
}
public Dice(int iMin, int iMax)
{
min = iMin;
max =
iMax;
}
public int Max
{
get{return max;}
set{max = value;}
}
public int Min
{
get{return min;}
set{min = value;}
}
public int Roll()
{
int i = Min + (int)((Max + 1 - Min) *
autoRand.NextDouble());
Console.WriteLine(i);
return i;
}
}
}
After this I went outside and planted three rows of potatoes because man cannot live by software alone...
28 March 2005
10 March 2005
Various things
XAML.Net is a web site dedicated to informing you of everything XAML.
An item on .NET Memory Usage by Tim Anderson.
Test Automation for ASP.NET Web Services.
An article on Web Service Enhancements and WS-* specifications
An item on .NET Memory Usage by Tim Anderson.
Test Automation for ASP.NET Web Services.
An article on Web Service Enhancements and WS-* specifications
14 February 2005
29 January 2005
02 January 2005
Dilbert...
Wally should have realised he was meant to write his own objectives, because "he owns his career".
23 December 2004
22 December 2004
03 December 2004
21 November 2004
Autism research
Brain inflammation link to autism
"Researcher Dr Carlos Pardo-Villamizar said: "These findings reinforce the theory that immune activation in the brain is involved in autism, although it is not yet clear whether it is destructive or beneficial, or both, to the developing brain.""
"Researcher Dr Carlos Pardo-Villamizar said: "These findings reinforce the theory that immune activation in the brain is involved in autism, although it is not yet clear whether it is destructive or beneficial, or both, to the developing brain.""
Subscribe to:
Posts (Atom)