On a previous project, I got to use a nifty tool called OpenTest to orchestrate test automation on an Android app. It's not a widely popular framework yet, but I hope it grows because it solves one particular problem quite well. OpenTest enables a QA team to write tests once that can run across multiple environments and platforms. It's a solid tool if you're looking to do something like automate an iOS and Android app that have identical UIs, or just want a shared language for your web and mobile app testing frameworks. OpenTest is also written in YAML, so it's approachable for even quite junior SDET teams, and it contains a lot of keyword-based actions that make UI tests simple to compose.
In most cases, you simply structure tests like this:
- description: Verify Text is Accurate
action: org.getopentest.appium.AssertElementText
args:
locator: $data("locators/view").area.element
text: 'Whatever text I expect to see'
In most cases, you can locate elements by their id
or text
properties, but in cases where you need to construct custom locators on the fly, it can be useful to know how OpenTest interprets Javascript.
Javascript can be dynamically inserted into OpenTest tests using the script
tag, and if a bar (|
) is inserted on the first line, then everything following it is interpreted as Javascript, so you can use multi-line Javascript blocks. For more on scripting support in OpenTest, read the docs.
For now, all you need to know is that Javascript can be dynamically inserted anywhere in a test, and that you can call all your basic OpenTest actions like AssertElementText
by using the special $runAction
command in your Javascript blocks.
Let's imagine an example interface for an administrator viewing an Employee Management System that lists employees and has a "Reset Password" button next to their names. Let's say there are just two employees in the system, Taz and Julia.
In this example, we have locators in our OpenTest /data
repository that correspond to the elements in the interface.
Taz and Julia show up in my Employee Management System, and next to each of their names, I can see a button to reset their passwords. We're going to have two separate locators for the two "Password Reset" buttons. To test this, I need to find the row with their name in it, and then find the corresponding password reset button to select. We can use string concatentation to directly insert each person's name into the xpath locator.
tazBtn: { xpath: "//ClassName[@resource-id='personRow' and @text='Taz']/following-sibling::android.widget.Button[@resource-id='passwordResetButton']" }
juliaBtn: { xpath: "//ClassName[@resource-id='personRow' and @text='Julia']/following-sibling::android.widget.Button[@resource-id='passwordResetButton']" }
OpenTest does a good job of separating test logic from test data. References to data strings, numbers, and other values can be included in tests using references formatted like: $data("fileName").parent.child
.
Here's an example of declaring a text label directly, and then using the value concatenated into a locator identifier.
- description: Verify Text Label
script: |
var label = "Some text.";
$runAction("org.getopentest.appium.AssertElementVisible",
{
locator: "//android.widget.TextView[@text='" + label + "']"
});
It's important to remember that direct string concatenation will not work in your locator strings, you'll need to explicitly declare a new variable for the string you'll use at the top of our Javascript block.
Here's an example that shows how to structure some code that relies on inserting a $data
value into a text
property so we can type it into a field. In this case, we're pulling from a list of products in our $data
directory.
- description: Enter product name into text field
script: |
var textToEnter = $data("products").product1.name
$runAction("org.getopentest.appium.SendKeys", {
locator: $data("locators/form").input,
text: textToEnter
});
You might be tempted to define your text
value directly with the $data
value, but this won't work and you must explicitly define that value first in a variable at the top of your Javascript block.
I hope this saves someone a bit of frustration. If you're using OpenTest on a project, I'd love to hear what you think of it on Twitter.
Top comments (0)