A layer below the GUI

I wanted to expand on the main point of my last post – specifically on what a “layer below the GUI” means. All I mean is – don’t write automation that interacts with the GUI directly – instead, write automation that tests using an object model, or another method of testing the logic under the UI.

For example, code like this:

 button_press("Next");
type_text("My Name");
button_press("Next");

Or this c# code:

 Process wordApp = Process.Start("Winword.exe");
if (wordApp.WaitForInputIdle(1000))
{
    SendKeys.SendWait("This is input to WinWord");
    SendKeys.SendWait("^a"); // send ctrl+a (select all text)
    SendKeys.SendWait("^b"); // send ctrl + b (make text bold)
}

…is usually a waste of time (note – I made up the first code example based on what I remember about QTP). Why not write automation that tests the functionality at a level that can be more robust?

Many apps have an object model that makes stuff like this a lot easier. For example:

 Object template = Type.Missing;
Object newTemplate = Type.Missing;
Object docType = Type.Missing;
Object visible = Type.Missing;

Word.Application wordApp = new Word.Application();
Word.Document wordDoc = new Word.Document();
wordApp.Visible = true;
// the following line is equivalent to selecting File, and then New
// to create a new document based on Normal.dot.
wordDoc = wordApp.Documents.Add(ref template, ref newTemplate, 
                                ref docType, ref visible); 

wordDoc.Selection.TypeText(“This is input to WinWord”);
wordDoc.Selection.WholeStory();
wordDoc.Selection.Font.Bold = 1;

Same functionality, except now it will run on any language version of word, and may even keep working in the future. Many automation frameworks allow you to write similar code, but many testers just default to the fragile implementations.

If you have any other way to automatically test the functionality without going through the GUI, do that. If you’re testing an application that doesn’t have an object model (it’s certainly not a requirement), you can access windows controls through the IAccessible interface (it’s handy for much more than accessibility) – you can also ask your developers to implement IAccessible for any custom controls. This way, you can test the functionality of your GUI even if the UI is completely rearranged and the default language is changed to pig latin.

One final point – I’m not saying that you shouldn’t test your GUI at all – it’s just probably a better use of your time to focus your automation efforts somewhere other than button clicks and text. Most UI automation is probably better done manually. Once your product ships a few versions, and you’re up to several SKUs and dozens of languages, you can begin to justify UI automation – but by then, you’ve probably already realized that you need to write robust UI automation…or you’re about to.