The strategy laid out in Testing strategy for validation and action methods calls for a single test per action method, to show that it actually calls the validation method.
Validation methods throwing exceptions on invalid input provide you with a handy means of checking whether it has been called by your action methods. All you need to do is supply your action methods with invalid input and wait for the exception to go off.
But what if your validation method doesn’t throw exceptions? Then there is no exception to wait for! What do you do then?
Well, you hope…
Nah, of course not.
There are two options, really. Your validation method has some other side effect besides throwing a tantrum or two, or it doesn’t. The former we’ll discuss now, the latter will have to wait for another time.
Simply put, if your validation method doesn’t throw exceptions but does have other side effects that you can check for, you are home free. All you then have to do is write a test that feeds valid or invalid input to your action method and then verify that the expected side effect did occur.
Code example
So, instead of a validation method that throws exceptions, you have a validation method that has other side effect. For example it adds an error message to an internal list.
private List<string> _Errors = new List<string>(); public void ValidateInput(string key, int index) { if (string.IsNullOrEmpty(key)) _Errors.Add("Key should not be an empty string."); // ... snip ... }
Good, now you have something to work with. Unfortunately, the list of error messages is private
so you can’t get at it from your tests.
Or can you?
Having a list of error messages somewhere without any means of getting its contents is futile to say the least. It is pretty safe to expect that this class provides some way to find out why the action method that was called didn’t have the desired result. Either a method to get the text of all the error messages or at the very least some Boolean LastValidationResult
property.
Let’s go with the error text.
private List<string> _Errors = new List<string>(); public string ErrorText { get { return string.Concat(_Errors); } } // ... snip ... public void ValidateInputAddingMessage(string key, int index) { _Errors.Clear(); if (index < 0) _Errors.Add("Index can not have a negative value."); if (index > _List.Count) _Errors.Add(String.Format("Cannot add at index {0}. The list is only {1} items long.", index, _List.Count)); if (string.IsNullOrEmpty(key)) _Errors.Add("Cannot add an empty string."); if (_List.Contains(key)) _Errors.Add(String.Format("Cannot add {0}. It is already present at index {1}.", key, _List.IndexOf(key)));
The test to check that for example the AddKey
action method indeed does call the ValidateInput
method would then be a very simple check on the value of the ErrorText
property..
[TestMethod] public void ValidateInput_EmptyString_ShouldCause_NonEmptyErrorText() { var list = MakeAugmentedList(); list.ValidateInput("", 0); Assert.AreNotEqual(list.ErrorText, ""); }
That’s it. Enjoy!
What code had you wondering how to test it? I’d love hearing from you by email or in the comments below. I read everything and will try to help where and as best I can.
Leave a Reply