Wednesday, February 6, 2013
Wednesday, August 1, 2012
Ten years of going Gorilla!
Wednesday, July 11, 2012
MonkeyTalk Beta 5 Adds Desktop Web and Adobe Flex Scripting!
Beta 5 provides comprehensive script recording and playback support for testing any html-based browser application, as well as Adobe Flex apps. Currently, only Firefox browsers are supported (on any OS), but support for all major browsers is coming soon.
Beta 5 also includes:
- A component tree browser that makes it easy to examine the user interface component hierarchy comprising the application under test.
- A screenshot command that lets you record screenshots at any point in a test script.
- Numerous enhancements and bug fixes. See the complete list here
MonkeyTalk Beta 5 is free, open source, and available for immediate download at www.gorillalogic.com/monkeytalk.
Happy Testing!
Thursday, June 7, 2012
Gorilla Logic is a "2012 Colorado Company to Watch"
Friday, May 25, 2012
Gorilla Logic is #16 on Mercury 100 List of Fastest Growing Boulder Companies
Monday, May 14, 2012
MonkeyTalk Beta 4 Adds Mobile WebApp Testing!
Wednesday, May 2, 2012
MonkeyTalk Beta 3 Adds Hybrid Native/HTML App Scripting
We have mapped html elements to MonkeyTalk logical component types, so there is no need to distinguish within a script between what is native and what is html. For example, the command for tapping on a button looks the same regardless of whether you're scripting native Android, iOS, or html.
Button OK Tap
The above command will work with html buttons created with a button tag, as well as those created with an input tag. Other html elements are similarly mapped. At runtime, MonkeyTalk searches all displayed native and html components until it finds a displayed native or html button labeled OK.
The only big difference at present between native component and html webview handling in MonkeyTalk is that we do not yet support recording html element interactions, so these need to be composed manually without recording. MonkeyTalk of course makes it very easy to whip out a script from scratch, so even without the ability to record, this is a very powerful new feature. All other MonkeyTalk features including parameterization and data-driving are fully supported for html element scripting.
You can download MonkeyTalk Beta 3 from http://www.gorillalogic.com/monkeytalk/download.
Happy testing!
Friday, April 20, 2012
MonkeyTalk Source Code Available Now!
Code contributions are extremely welcome! Anybody interested in helping out with MonkeyTalk engineering should please contact us!
Thursday, April 19, 2012
Gorilla Logic named a Top Denver Workplace 2012
Certainly we've always asserted it's the case, but it's nice to have some 3rd-party validation that Gorilla Logic is a f**king great place to work. http://denverpost.topworkplaces.com/company_survey/gorilla-logic-inc_denver/denverpost_12.
Tuesday, April 10, 2012
New MonkeyTalk Release Now Available for Download!
Thursday, March 22, 2012
The Value of Continuous QA
Wednesday, March 14, 2012
See MonkeyTalk at AnDevCon and save $200!
Tuesday, March 6, 2012
MonkeyTalk is here!
Tuesday, February 7, 2012
Rational Functional Testmonkium
Friday, December 9, 2011
FoneMonkey for Android Q&A
Monday, November 21, 2011
FoneMonkey, Objective-C, and the Dark Arts
Monday, November 14, 2011
FoneMonkey for Android has Landed!
Wednesday, November 9, 2011
Adobe kills Flash
Tuesday, October 25, 2011
Dr. Dobbs meets the monkey
Wednesday, May 11, 2011
We're the "E" in iOS: Open source projects fill Enterprise holes in Xcode
A long, long time ago, just as the internet bubble was really getting going, many pundits were talking about “internet time” to describe the radical time compression brought about by the web. Software release cycles were suddenly occurring over periods of just a few months rather than years, and technology platforms were similarly revving over just a few years whereas previously it had literally taken decades for enterprise IT to make any major changes in how they built software.
If internet time was fast, what are we to make of “mobile time”? The big bang of mobile time, the release of the first iPhone, was just four years ago. Enterprises certainly needed to move quickly to keep up with internet time, but at roughly the same four-year mark, most enterprises were doing little more than creating static websites. There has been no comparable gestation period for mobile development since Apple was nice enough to skip over infancy and adolescence and give birth on day one to fully formed, mature applications employing radically new user interfaces.
While iPhone applications have been pretty “magical” since day one, enterprise-class tool support for iOS app development has been quite a bit slower in coming. It’s hard to find many enterprise developers having anything nice to say about Apple’s Xcode IDE, which is currently the only serious game in town for developing iOS apps. Try the Google search Xcode +”piece of crap” and you’ll be treated to more than 40,000 results. There are of course many similar but more colorful searches you can try.
Back in the days of internet time, Sun created a virtually unusable IDE called Java Workshop. Fortunately for internet time, other companies including IBM, Borland, and Symantec created competing IDE’s and Java development has enjoyed robust tool support ever since. The closed nature of iOS however has understandably dampened the enthusiasm anybody outside of Apple might have for jumping into the nascent iOS development ecosystem. After all, Apple can at any time change the iOS platform in such a way as to make third-party tools incompatible, similar to the way in which iTunes was continually revved to maintain incompatibility with the Palm Pre mobile phone.
So, since the usual commercial suspects have too much business sense to enter into the iOS development ecosystem, it’s left up to those of us with little or no business sense – I am of course referring to open source software developers – to fill the gap!
Monday, April 4, 2011
FoneMonkey 5, baby!
FoneMonkey 5 is by far our most solid release yet. Go get it now at http://www.gorillalogic.com/fonemonkey!
Friday, April 1, 2011
My Podcast with Coté
Back then, it wasn't long before we woke up to the twin realities of browser compatibility and bandwidth constraints and were forced to shunt Java from the front- to the back-end of application development, and we spent several years dealing with the page-based hack that became known as MVC2.
Plentiful bandwidth and a new generation of client-side technologies such as Flex, Silverlight, Android, and iOS are finally allowing us to build user interfaces in a much more direct, natural, and efficient fashion than the page-based MVC2 approach, and arguably, provide similar advantages over the the JavaScript-meets-DOM hack now known as AJAX.
You can listen to my complete conversation with Michael here.
Thursday, March 31, 2011
Gosling@Google
Friday, March 4, 2011
FoneMonkey 4.2c improves text input handling
We very pleased to announce the availability of FoneMonkey 4.2c which improves handling for UITextField and UITextView components.
4.2c provides robust handling of keyboard input, including recording of the Return key, and fixes an issue where sometimes touch events that ended field editing would be recorded prior to recording the text input itself. On playback, FoneMonkey now triggers all appropriate delegate methods and notifications.
We believe that keyboard-related input issues were the last major problem facing us and 4.2c should reliably provide recording and playback for virtually all common user interface gestures.
Script and generated code storage has been moved back to the base Documents directory to make it easier to use iTunes to move scripts on and off iPhone and iPad devices. FoneMonkey scripts are now suffixed with .fm. You will need to rename any existing scripts.
FoneMonkey 4.2c is available for immediate download at www.gorillalogic.com/fonemonkey. Thanks for the continued feedback. Your input is the primary factor determining what we tackle next!
Tuesday, February 8, 2011
FoneMonkey 4.2 adds iOS UIAutomation Support
FoneMonkey 4.2 includes numerous bug fixes and adds several significant new features including:
- Generation of ready-to-run OCUnit test scripts - Automatically convert "native" FoneMonkey test scripts to Objective-C code that can be extended with Objective-C control logic to add control flow or data-driving logic to your tests.
- Generation of ready-to-run JavaScript-based tests for Apple's UIAutomation Framework - Automatically convert "native" FoneMonkey scripts to JavaScript code that can be run in Apple's Automation Instrument. You can uyse FoneMonkey to record UIAutomation scripts which allows for test scripts to be maintained in JavaScript rather than Objective-C. Since these UIAutomation scripts require no FoneMonkey libraries to run, they can be executed against "release" builds of your application.
- Recording and Playback of Device Rotation - You can record and playback device rotations on the simulator or on devices.
This release is a significant step forward in the maturing of the FoneMonkey project. Thanks to the members of the FoneMonkey community for providing the feedback and support essential to making FoneMonkey a continuing success.
FoneMonkey 4.2 is available for download at http://www.gorillalogic.com/fonemonkey.
Happy testing!
-Stu
Tuesday, January 18, 2011
See FoneMonkey at iPhone DevCon!
I'll be presenting Automating iOS User Interface Testing with FoneMonkey at iPhone/iPad DevCon East in April. FoneMonkey is a free and open source, record/playback functional testing tool for native iPhone and iPad apps. If you're going to DevCon, come on by and check out the monkey!
Thursday, December 16, 2010
FlexMonkium 4.1.4 Released!
FlexMonkium 4.1.4 includes some important enhancements, bug fixes and usability features including:
- Support for running FlexMonkey tests in Internet Explorer with Selenium-RC. Previous versions of FlexMonkium only supported Firefox.
- Bug fixes for the getFlexMonkeyValue command, which now reliably retrieves values from properties and table cells.
- Commands can now be made to wait for a component to appear before executing. For example, a command for clicking on a button will wait for the button to appear before attempting to click it.
- Ability to verify (or retrieve) values for property path expressions. For example, you can verify the number of rows in a DataGrid with the path expression "dataProvider.length".
- By default, all commands and verifies are now recorded as "WaitFor..." commands, which eliminates the need in most cases to slow or pause script execution to give components time to appear on the display.
- The XML recorded by Selenium-IDE for FlexMonkey commands has been simplified to make reading and editing easier.
To upgrade to FlexMokium 4.1.4, install the new console and download the new zip file. Upgrade the Firefox plugin by opening flexmonkium.xpi in Firefox. You will need to compile your app with the latest automation_monkey swc file. You will additionally need to use the new version of user-extensions.js with Selenium-RC.
Happy testing!
Thursday, November 18, 2010
Great In-Depth Guide to FlexMonkey
Monday, November 8, 2010
New FoneMonkey for iOS Release!
Thursday, November 4, 2010
See FlexMonkey at Flex Camp Wall Street
Monday, November 1, 2010
See FoneMonkey at 360|iDev
If you're going to be at the conference, come on by to see how to get the most out of FoneMonkey, and let me know what you'd like to see in future releases.
Wednesday, June 9, 2010
FlexMonkium is here!
FlexMonkium provides for the testing of hybrid applications consisting of both Flex and HTML components by seamlessly interleaving the recording and playback of Flex and HTML interactions. Recorded tests can be output as JUnit-based scripts that can be extended with Java-based testing logic, and that can be run from build scripts and continuous integration processes.
You can download FlexMonkium from http://www.gorillalogic.com/flexmonkium.
Saturday, June 5, 2010
FoneMonkey - A Closer Look (Clever Tester Managazine)
FlexMonkey 4 and FlexMonkium (DZone)
Tuesday, May 25, 2010
Flex Developer's Journal: Functional testing of Flex RIA with FlexMonkey 4
Saturday, May 15, 2010
FlexMonkium: Get ready for the 119th element!
In this pair of videos smuggled from Gorilla Logic labs, deep beneath the surface of the Earth, we see FlexMonkium interleaving Flex with HTML recording and playback, and generated JUnit test scripts being run with Selenium-RC.
Wednesday, May 5, 2010
FlexMonkey 4 is here!
Happily, we now return our attention back to FlexMonkium, our FlexMonkey/Selenium bridge, which is rapidly nearing it's first public release!
Sunday, April 18, 2010
FlexMonkey 4 is coming!
This upcoming release, which we think we're going to call "FlexMonkey 4", works perfectly with Flex 4 and handles all of the new Spark components.
Sunday, April 4, 2010
FoneMonkey 0.7.2 Released
This release fixes various bugs including problems with keyboard and scroll recording.
Tuesday, March 16, 2010
FoneMonkey 0.7.1 Released
Enhancements:
* WaitFor command - You can cause script execution to wait for views to be created or property values to be set
* "Popup Dialog" handling - You can now script UIAlertViews and UIAlertSheets.
* Better control event handling for UITextFields.
Bug fixes:
* OCUnit runner crash
* UINavigationBar rightItem playback
FoneMonkey 0.7.1 can be downloaded from FoneMonkey Project Home. We can understand if you considered 0.7 to be too early a release to try, but surely you'll feel differently about 0.7.1, which includes not one, but two, decimal points.
In all honesty, FoneMonkey, while not yet bug free, is quite stable and will definitely make your life better, at least in terms of iPhone testing.
Sunday, February 28, 2010
Selenium Assertions and waitFors in FlexMonkium
The video shows a simply script being played back at slow speed. When we then try to play the same script back at fast speed, it fails because the script navigates to the page containing a Flex app, but then attempts to interact with it before the app has finished loading.
What we would like to do is have a way to tell Selenium to wait for some condition that signals the app has finished loading. One way to do this is to have Selenium wait for the appearance of a component within the application's window. We interactively create a FlexMonkey Verify command that tests whether the name field has a blank value. Notice that when we create this command, it is also "recorded" by the Selenium IDE as an assertion, assertFlexVerify.
This assertion will fail if it is executed before the swf has finished loading. However, we can ask Selenium to wait for the condition to become true by changing the assertFlexVerify command to be a waitForFlexVerify instead. Now, when we run the script, it waits for the swf to load before continuing, and then successfullly plays the rest of the script at high speed. We can of course use a similar technique to have a Selenium script wait for other Flex application events, such as data being returned from a query to be displayed in a table.
As you can see, we have all the major mechanisms necessary to very clean integration of FlexMonkey and Selenium. There is some trivial syntactic sugar we will likely sprinkle on what the video shows here, and we've still got some code clean up to do before we'll be ready to release, but we believe all the hard problems have been solved so it won't be much longer before FlexMonkium, the FlexMonkey Plug-In for Selenium, is publicly available!
Saturday, February 27, 2010
FlexMonkium: The Movie
Last week, on this very blog, the world first learned of FlexMonkium, the FlexMonkey plug-in for Selenium. Now, we are pleased to present this exclusive video of FlexMonkium in action, allowing Selenium IDE to record both browser and Flex application interactions within a single Selenium script.
Although the recorded scenario is seemingly simple, it is actually quite wonderful. Selenium IDE begins recording on a plain html page, and continues recording as we navigate to a page containing a Flex application, and Flex application interactions are recorded to the script. Recording continues as we hit an html link ("Back") outside the Flex application in the browser page. For good measure, we continue recording as we navigate again to the page with the Flex app for further interaction, and then navigate back to the plain html page. All Flex and browser interactions have been recorded to a single Selenium script!
And of course, playback works as well.
Just a few more weeks and we'll be ready to release FlexMonkum! If you're interested in early access, please let us know.
Tuesday, February 23, 2010
We've released FoneMonkey, our record/play functional tester for iPhone
If you've been following my recent posts, you know that FoneMonkey is the world's first record/playback functional testing tool for the iPhone. FoneMonkey records user interactions with the iPhone, and replays them while verifying that actual results match expected ones.
Key FoneMonkey features:
- High fidelity recording and playback of most iPhone gestures including touches, drags, and shakes.
- Integrated script editor and test runner.
- Recording and playback on both the simulator and actual iPhone device.
- Extensible framework can be customized to provide specialized command recording and playback for custom components.
- Simple Objective-API can be used to run FoneMonkey scripts using OCUnit.
Monday, February 22, 2010
FlexMonkium: FlexMonkey/Selenium Bridge
We've been getting a lot of requests about integrating FlexMonkey with Selenium to provide testing of "hybrid" test scenarios involving both Flex and non-Flex web apps. It is of course common to embed Flex applications within web pages that also contain non-Flex, HTML components, and the combined Flex and non-Flex pieces together produce a single user experience and workflow. Ideally, such hybrid user interface scenarios could be automated within a single test case. In fact, many times the functional dependencies between Flex and non-Flex components make it impossible to test one without the other.
While we've been hearing about many efforts to combine FlexMonkey with Selenium to provide for such hybrid testing, we're not aware of anything having yet been made publicly available, and having just completed development of FoneMonkey (which we're officially announcing tomorrow), and FlexMonkey 1.0GA (which we're releasing in about a week), we've had some time to take a look ourselves at how we might go about integrating Selenium with The Monkey.
After exploring various permutations, we hit upon a very robust approach through which we "slave" FlexMonkey recording and playback beneath Selenium. We have created a bridge, which we are provisionally calling FlexMonkium, that forwards FlexMonkey commands to Selenium during recording, and forwards FlexMonkey commands from Selenium to FlexMonkey during playback. Such FlexMonkey recording and playback is seamlessly interleaved with native Selenium recording and playback to easily produce hybrid testing scenarios. For example, in a single recording session you can click on HTML components and Flex components, even across multiple browser pages, with the resulting FlexMonkey and Selenium commands being recorded into a single Selenium script which (with the aid of the FlexMonkium bridge) can then be played back with any Selenium runner.
We are fairly confident we'll have something ready for early access in a matter of weeks! If you'd like to get your hands on FlexMonkium as soon as possible, contact us here.
Wednesday, February 10, 2010
FoneMonkey is In the Launch Tube
iPhone developers of the world, get ready to monkey!
Saturday, February 6, 2010
Drupal Page Editor Bookmarklet
So, I created a bookmarklet for this purpose. Drag the link below to your browser's bookmark bar. When you're browsing a Drupal-managed site, click the bookmark to open the current page in the Drupal editor (assuming of course you have editing privilege for the page).
DrupEdit
Wednesday, February 3, 2010
Using FoneMonkey With OCUnit
You can download the latest version of FoneMonkey here.
Running Under OCUnit
OCUnit (also known as SenTestingKit) is a unit testing framework for Objective-C that's bundled with the XCode IDE. As a member of the xUnit family of testing frameworks, OCUnit is similar to other popular frameworks such as JUnit (for Java), and FlexUnit (for Adobe Flex).
Using OCUnit, you can combine FoneMonkey- and non-FoneMonkey-based tests into comprehensive test suites that can be invoked interactively, as well as from build scripts, and from continuous integration frameworks such as Hudson or Cruise Control. It is also possible to combine OCUnit tests with non-OCUnit (for example, JUnit) tests, and combine the output so as to provide considated test reporting across all front- and back-end components of your application.
Please note that to run FoneMonkey with OCUnit, you should not create a testing bundle. Instead, you use the FoneMonkeyOCUnit plug-in to launch your OCUnit tests cases, as described later in this section.
Adding OCUnit to Your Project
You add OCUnit to your project much in the same way you add any framework.
- Right click on the target that includes FoneMonkey, and select Get Info from the menu. The Target Info dialog will be displayed.
- Add a new entry to the Linked Libraries by clicking the add (+) button at the bottom of the dialog window. A selection dialog will open.
- Click the Add Other... button. A file selection dialog will open.
- Navigate to the /Developer/Library/Frameworks folder. Select SenTestingKit.framework.
- Click the Add button.
Adding the FoneMonkeyOCUnit Plug-In
The FoneMonkey distribution includes libFoneMonkeyOCUnit.a which is a static library that extends FoneMonkey with an OCUnit test launcher.
- To add the library to your project, right-click on your FoneMonkey testing target and select Get Info. The Target Info dialog will be displayed.
-
On the Build Tab, scroll down to the Linking section. Add -lFoneMonkeyOCUnit to Other Linker Flags so that it now should look something like this:
-ObjC -all_load -lFoneMonkey -lFoneMonkeyOCUnit
Writing a Test Case
You write your test cases for FoneMonkey in the same way you write any OCUnit test. To create a test case, simply subclass SenTestCase and use STAssertions to test for expected results. For more information on OCUnit (SenTestingKit), see Apple's Documentation.
Using the FoneMonkey API, you can run FoneMonkey commands from within your test case, and you use OCUnit Let's look at an example:
#import
#import
#import "FoneMonkey.h"
@interface SampleTest : SenTestCase
- (void) testSample;
@end
@implementation SampleTest
- (void) testSample {
NSString* lastResult = [[FoneMonkey sharedMonkey] playAndWait:@"Test1"];
STAssertNil(lastResult, lastResult);
}
@end
You run a FoneMonkey script from a test case by calling runScript:(NSString*)script, where script is the name of a FoneMonkey script stored in your application's Documents directory. runScript: returns nil if the script runs successfully. For example, in the script above we call:
NSString* lastResult = [[FoneMonkey sharedMonkey] runScript:@"Test1"];
If the script fails for any reason, runScript: returns the message generated from a failed Verify command, or other error message. You need to explicitly add an assertion to test for a non-nil result, and display the returned message if it's non-nil as follows:
STAssertNil(lastResult, lastResult);
You can of course do more in your test case than simply run a script and test its result. You can include addition programming logic and assertions, and run multiple scripts.
Using the FoneMonkey API, It is also possible to build scripts programatically at run time, rather than running a script previously saved.
Running OCUnit Tests
When you link your application with FoneMonkey and FoneMonkeyOCUnit, FoneMonkey will by default run all SenTestCase subclasses, and OCUnit output will be written to the console.
If you would like to exit your application after the OCUnit tests have run, set FM_ENABLE_AUTOEXIT the environment variable.
You can disable the running of OCUnit tests upon FoneMonkey start up by setting the FM_DISABLE_AUTOSTART environment variable. Omitting the -lFoneMonkeyOCUnit linker flag will also disable the running of any OCUnit tests at startup.
Sunday, January 24, 2010
Using the FoneMonkey Console
When you launch an application that has been linked with FoneMonkey (see Setup Guide), the FoneMonkey Console is displayed on top of the application’s window.
To begin recording, touch the Record button. The FoneMonkey console will hide and you can manually test your application. As you interact with it, FoneMonkey records FoneMonkey commands corresponding to each user interface gesture.
If you stop interacting with the application for longer than the timeout interval (by default, 2.5 seconds), the FoneMonkey console will reappear on top of your application window.
If you are not yet done recording, click any where over the application to hide the FoneMonkey console and resume recording.
Touching the Pause button hides the FoneMonkey window and lets you interact with your application without recording. The console will reappear after the timeout interval. Touch anywhere on your application to re-hide the console and continue without recording.
Touch the More button to view the list of recorded commands.
Commands are displayed in the Command List table. The Timeout slider can be used to set the timeout interval anywhere from 2 to 10 seconds. If the console is reappearing more quickly than you want it to while the console is recording or paused, make the timeout longer.
Touch the Play button to begin playback. The console hides and FoneMonkey executes each command in sequence, generating user interface actions corresponding to each command.
By default, FoneMonkey pauses .5 seconds between commands. Sometimes you may need FoneMonkey to wait additional time at certain points in a script. For example, a command might need to wait until an animation finishes running. Use Pause commands (see command reference) to insert pauses between commands during playback.
Editing Recorded Commands
To edit a recorded command, touch the Edit button on the row in the command list to be edited. The Command Editor will be displayed.
Using the command editor, you can change the Command, Component Class, Monkey ID, or any of the associated parameters. When you’re finished editing, touch the Done button.
Inserting and Deleting Commands
Commands can be inserted and deleted using the Insert and Delete toolbar buttons, which display the Insert or Delete buttons in each row of the displayed script.
Saving a Script
To save a script, touch the Save Script button. The Save Script dialog will be displayed.
Enter a name for the script and hit the Save button. Scripts are saved in the application's Documents directory.
Running a Saved Script
To run a saved script, touch the Open Script button. The Saved Script List will open displaying all saved scripts.
To open a script, touch its name in the list. The script will open in the console and can be played and edited.
Recording a New Script
To clear the currently opened script and begin creating a new one, click the Open Script button and then touch the New button displayed above the Saved Script List.
Deleting a Saved Script
To delete a saved script, touch the Open Script button and then click the Edit button displayed above the Saved Script List. You may then delete a saved script by touching the associated Delete Icon.
Friday, January 22, 2010
Working with FoneMonkey Command Scripts
User interface actions are directed to components. For example, you Touch a UIButton, or Scroll a UITableView to Row 5. FlexMonkey commands identify the action to be performed, and the component to receive the action. Components are identified by a combination of their Object-C class name (or superclass name) and a string identifier called a monkeyID.
All commands are written as:
CommandName ComponentType "MonkeyID" Parameters, ...
where
CommandName identifies the command to be executed.
ComponentType is the Objective-C class name of the component to receive the command. If componentType is omitted, it defaults to UIView (ie, any component).
"MonkeyID" is a quoted string that uniquely identifies which instance of the component's class should receive the command. If there is only one instance of a particular type, monkeyID may be omitted.
Parameters, .... are zero or more command-specific parameter values in CSV format.
By overriding recording and playback methods, it's easy to add your own commands to FoneMonkey or customize existing commands. See the FoneMonkey Extension Guide for more information.
Some Command Examples
Touch the "Done" button:
Touch UIButton "Done"
Touch the PaintingView at coordinate (25, 75):
Touch PaintingView 25, 75
Enter text into the "FirstName" field:
InputText UITextField "FirstName" fred
Identifying Components by ClassName and MonkeyID
As mentioned above, commands correspond to user interface actions, and actions are directed to components. For example, a command might specify to Touch a UIButton. If there is only one UIButton on the screen, FoneMonkey knows which button the command is referring to. If there are multiple buttons, however, we must tell FoneMonkey which one to use. In addition to the component's Objective-C classname, and a unique identifier called a monkeyID that's generated by FoneMonkey extensions for various UIKit classes. For any command, you can specify just a className or a monkeyID, or you can specify both.
Component Identification Examples
If there are multiple buttons on the screen:
Touch UIButton "Done"
If there is just one button on the screen:
Touch UIButton
If threre is just one button on the screen with a monkeyID of "Done":
Understanding MonkeyID's
FoneMonkey's UIView extensions provide the default monkeyID for all components. By default, the monkeyID of a component is the value of its accessbilityLabel property, if one exists, its tag property if it's non-zero, and otherwise FoneMonkey generates a unique identifier as explained below. Many component types provide specialized monkeyID's. For example, UIButton returns its titleLabel.text as its monkeyID, UITextField returns its placeholder value.
See the FoneMonkey Command Reference for a description of the monkeyID's returned by each component type.
If a component provides no monkeyID, FoneMoney generates an identifier by assigning an ordinal to each instance of each class on the screen FoneMonkey generated monkeyID's are prefix with a #-sign.
Examples of Generated MonkeyID's
Touch the first button:
Touch UIButton #0
Touch the second button:
Touch UIButton #1
Validating Tests with the Verify Command
You insert Verify commands into your script to validate during playback that actual results match expected ones. The Verify command has the following syntax:
Verify ClassName "monkeyID" propertyPath, expectedValue
As with all FoneMonkey commands, you can specify either ClassName or monkeyID or both to identify the component.
propertyPath is any valid key path to a property.
expectedValue is the expected value of the property identified by the propertyPath.
Verify Command Examples
Check that the last name label is "Smith"
Verify UILable "Last Name" text, Smith
Check that the button says "Hello"
Verify UIButton titleLabel.text, Hello
If a verify command fails, a message is displayed in the FoneMonkey Command List.
Inserting Pauses into a Script
By default, FoneMonkey pauses .5 seconds between commands during playback. Sometimes you may need a longer delay between commands, for example if an animation needs to finish running before a component is displayed.
You can insert pause commands to allow additional time between the execution of commands. It has the following syntax:
Pause milliseconds
where milliseconds is the number of milliseconds to pause before executing the next command.
The Pause command ignores class name and monkey ID, if any are supplied.
Pause Example
Pause for 1 second:
Pause 1000
Thursday, January 21, 2010
FoneMonkey: New Fat Library
The download is available here.
Saturday, January 16, 2010
FoneMonkey: The Update
The latest FoneMonkey download and release instructions can be found here.
We expect to have the official FoneMonkey project site online later this month!
Tuesday, December 29, 2009
FoneMonkey: The Download
FoneMonkey.zip
The iPhone does not yet allow installation of user-defined frameworks, so FoneMonkey is disbributed as a static library along with the image files and nibs required by the FoneMonkey user interface. FoneMonkey.zip contians libFoneMonkey.a as well as a bunch of png and xib files.
The zip file does not include the FoneMonkey source code, which we'll be releasing when we officially launch the FoneMonkey open source project in mid-January, 2010 (ie, just a few weeks from now!). At that time we'll be going live with a community forum as well. Until then, please post questions or comments to this blog.
To get started using FoneMonkey, download the zip file and extract the FoneMonkey distribution folder. Then follow the instructions below.
Happy testing! We look forward to your feedback!
Testing an iPhone application with FoneMonkey
In order to test an iPhone application with FoneMonkey, you must first link FoneMonkey with your application as shown in the 2-minute video below. Step-by-step textual instructions are also provided here.
You might need to view the video in a new window.
- Open your application's project in xcode.
- Duplicate your application's build target by right-clicking on it and selecting Duplicate from the menu. A new target will be created called YourApp copy.
- Rename YourApp copy to something like YourAppTest.
- Add the downloaded FoneMonkey folder to your project by right-clicking on the project and selecting Add > Existing Files... from the menu. Navigate to the FoneMonkey folder, select it, and click the Add button.
- When the dialog box appears, select the Recursively create groups for any added folders option.
- In the Add to Targets box, deselect YourApp and select YourAppTest.
- Click Add.
- Right-click on the YourAppTest build target and select Get Info from the menu.
- On the General tab, delete libFoneMonkey.a from the Linked Libraries. You will need to add CoreGraphics.framework and QuartzCore.framework to the Linked Libraries list they aren't already there.
- On the Build tab, scroll down to the Linking section and click on the Other Linker Flags setting. When the dialog box appears, enter:
-ObjC -lFoneMonkey -LFoneMonkey/lib -all_load - Dismiss the project Info window.
- Right-click on YourAppTest build target and select Clean from the menu.
- Right-click on YourAppTest build target again and select Build and Debug from the menu.
- Your application should start in the simulator. Immediately after it displays, the FoneMonkey console should drop down over it.
- See this post for more info about recording and playing back tests with FoneMonkey.
Wednesday, December 16, 2009
FoneMonkey: The Movie
The video demonstrates FoneMonkey recording and playing back various actions including button touches, table scrolling and selection, switches, sliders, text entry, tab selection, finger dragging (in this case, painting), and even phone shaking (which is the gesture that causes GLPaint to erase the current painting).
You might need to view this video in a new window.
As you can see, the monkey can really dance. I hope to post the library binary and installation instructions within the next few days.
Sunday, December 13, 2009
FoneMonkey: Open Source, Testing Tool for iPhone Applications
We plan to release FoneMonkey source and binaries (with attendant fanfare) in early January. Here's a sneak preview of what's coming.
Some Technical Background
FoneMonkey has been more challenging than FlexMonkey to create because the iPhone SDK, unlike the Flex SDK, provides no Automation API. Before I could develop FoneMonkey, I had to develop an automation framework. The resulting FoneMonkey API is simple, extensible and initially supports nearly all native iPhone (ie, Cocoa Touch) components.
Like FlexMonkey, FoneMonkey is designed to be used by both programmers and QA testers. Rather than simply recording and playing back low-level events, FoneMonkey records "semantic" events. In other words, FoneMonkey doesn't record that you touched a pixel at coordinate (125, 210), but instead records that you selected table row 5. The resulting scripts are relatively forgiving with respect to cosmetic UI changes. They can also be composed from scratch by directly specifying sequences of commands. (FoneMonkey Command Guide coming soon....).
Each FoneMonkey command is composed of a command name, a component identifier, and a set of command-specific arguments. For example:
Touch UIButton Send (touches the UIButton labeled "Send")
InputText UITextField, your name, Fred (types "Fred" into the UITextField with a field prompt of "your name")
The Flex Automation API provides an AutomatDelegate corresponding to each Flex UIComponent, and a delegate instance is created for each UIComponent instance created at run-time. Automation delegates subscribe to their component counterparts for all UI events, and translate these low-level keyboard and mouse events into high-level component events. FoneMonkey uses a logically similar mechanism, but is instead implemented with Objective-C categories that extend UI component classes with record and playback logic.
While recording, the FoneMonkey framework monitors all UI events and forwards them to the FoneMonkey category methods that provide recording for each component class. During playback, FoneMonkey sends each command to the playback methods also provided by the class's FoneMonkey extension category.
The FoneMonkey framework provides categories that record and play back events for instances of the UIView class and all UIView subclasses. It is straightforward to create a category for any custom UI class that requires custom recording and playback logic, or to further enhance the recording and playback logic provided out of the box by the FoneMonkey framework. (FoneMonkey Extension Guide coming soon....)
Using FoneMonkey
To test an application, you simply statically link it with the FoneMonkey library. (FoneMonkey Setup Guide coming soon....) Upon starting your application, the FoneMonkey Console "drops down" over your application window, displaying the recording and playback controls at the bottom of the screen.
The video below shows FoneMonkey being used to test Apple's "The Elements" sample application.
In the video, we touch the record button to hide the FoneMonkey Console and begin recording our interactions with "The Elements" application. FoneMonkey monitors for periods of inactivity and drops back down over the application if we stop interacting with it for more than the current inactivity timeout setting (by default, 2.5 seconds). Touching the play button replays the recorded script.
You might need to view this video in a new window.
FoneMonkey provides the ability to edit scripts and save them for later replaying.
You can add Verify commands to a script to test the values UI component properties or the values of associated object properties (ie, you can use a key-value encoded key path) . In The Elements sample application, a custom class called AtomicElementView is used to display data for the currently selected element. The AtomicElementView has a property called element that references an instance of the AtomicElement class, which in turn as a property called name. In the Verify command below, we test that the current AtomicElementView's element.name has a value of "Lead".
The next video shows how to edit a script, add a verify command, save the modified script, and then replay it.
You might need to view this video in a new window.
Saturday, October 31, 2009
Gorilla Logic gets kosher-er
Monday, August 17, 2009
FlexMonkey 1.0 Beta 2 and the FlexMonkey User Guide are here!
Most notably, Beta 2 introduces "MonkeyLink", which allows you to link FlexMonkey directly into your target SWF. If you have had any problems dynamically loading your application through the FlexMonkey Console or the MonkeyAgent, you can now instead compile MonkeyLink into your application SWF, and then launch your application directly. Using MonkeyLink, you can test virtually any Flex or AIR application. Dynamic SWF loading with the Console or the MonkeyAgent are of course still supported so you also continue to have the option of testing SWFs without having to first recompile them.
Download FlexMonkey 1.0 Beta 2 now at http://flexmonkey.gorillalogic.com/gl/stuff.flexmonkey.download.html!
The long-awaited FlexMonkey User Guide is available at http://flexmonkey.gorillalogic.com/gl/flexmonkey/FlexMonkeyUserGuideR1b2.pdf! Weighing in at nearly 60 pages, the FlexMonkey User Guide is like having your very own Eric Owens!
Happy testing!
Thursday, July 16, 2009
Who you calling ugly?
Looking closer to home, Jon Rose at Gorilla Logic has just released Flex Monkey, a free tool to automatically test your Flex UIs. I've known Jon through various events so decided to look at the site. As with many sites, it contains a fair amount of cleverness but no clear statement of what they are about. However, among the slogans I found one that I thought had promise: "The answer is not more monkeys." It's succinct, catchy, and on the right track, because it's suggesting that more things should be automated (and Flex Monkey is an example of that kind of automation). Alas, the rest of the site doesn't give me a clear idea of what they do.Now I've done some hanging with Bruce and he's someone I like and respect, so I talked to our graphic designers and had them make some changes to our home page.
Meet the Monkey
My own article, which gives an overview of FlexMonkey's advanced features and discusses user interface testing more generally, was published today on InfoQ at http://www.infoq.com/articles/flexmonkey-ui-unit-testing. Eric Owens, our lead developer on the FlexMonkey project published an intro article on Adobe Devcenter at http://www.adobe.com/devnet/flex/articles/flexmonkey.html.
If you haven't already, please take a minute to meet the monkey and let us know what you think!
Tuesday, July 14, 2009
The monkey has landed!
For the thousands of folks who are already using FlexMonkey 0.8, FlexMonkey 1.0 brings significant new functionality including a completely revamped user interface which makes it much easier to record and playback tests. We've also added the ability to take snapshots of portions of the screen or of property values to be verified during playback. In addition to testing Flex apps, FlexMonkey 1.0 for the first time provides direct support for testing AIR apps. The FlexMonkey Console is now itself an AIR app, but can launch standalone as well as browser-based SWFs for testing.
Please let us show you our monkey at http://flexmonkey.gorillalogic.com! You can also check out Gorilla Logic's Flex service offerings at http://www.gorillalogic.com/what.development.services.flex.html.
Monday, June 1, 2009
In a Perfect World....
In such an environment, the need for a great many design constraints is removed, although not completely eliminated. Even with physical constraints removed, logical constraints remain. Still, removing the physical constraints certainly simplifies software construction by removing the need to manage limited resources efficiently. Of course, in the real world of enterprise applications, there is no such environment, but not every physical or logical constraint is an issue for every application. Low volume applications or those with very small and simple data requirements can often behave almost as if they were executing in the (near-)perfect world. Consider for example an application that allows a user to update their name, address, and credit card information. As soon as the user logs in, you can easily retrieve such a small volume of data immediately, and you wouldn't have to contend with the user's name and address being changed by someone else simulataneously. You can then allow the user to update any of the returned data, updating their name and address, deleting some credit cards and adding others. If there are few simultaneous users, we can transmit each change immediately to the server where we immediately run required edit checks against it and report any errors encountered back to the client for communication to the user via the UI. Such an approach allows us to write an application in what is arguably the most “natural” way, ie, the simplest way. Physical constraints, on the other hand, force us to commit "unnatural acts", ie, they force us to write code that is more complex than it needs to be from a purely logical perspective.
With RIA's, there are a few physical constraints which are fundamental at this point in time. The client application is a separate process (on a unique platform), and all communication with the server-side must be accomplished by messaging. It is this constraint, more than anything else, that distinguishes ERIA architecture from web applications, two-tier client server applications, or one-tier local applications. And speaking of one-tier applications, it is worth noting that virtually no enterprise application allows for the data to be persisted entirely on the client box. It is virtually always the case that we cannot rely on the client itself for safe storage of business records, and there are typically large amounts of non-client-specific data (such as a product catalog) that are usually too large to make client-side distribution practical.
Another constraint is the almost universal requirement that persistence be provided by a non-object-oriented datastore, typically a relational database. There is of course a fundamental impedance mismatch between object- and a relational-centric data structures that is at the heart of many unnatural programming acts, and although there have been many variations on “object databases” over the years, relational databases continue to dominate for good reasons we’ll explore in some depth another time. In a perfect world, queries would return graphs of objects rather than lists of rows. Fortunately, persistence management frameworks such as Hibernate automate a good deal of the acrobatics involved in object-relational mapping, but unfortunately are not (yet?) fully transparent to the application developer, requiring varying amounts of explicit coding.
Coding in the real world requires more effort than coding in the perfect world because we need to add code to work around physical constraints. It would seem to be self-evident that since it takes more effort to add more code, you should only do so when there is an actual requirement to do so. In other words, the default architecture for any ERIA is essentially the simple one described above. We retrieve all the data up-front. Operate on the data as necessary. And send edits to the back-end as they occur. In pondering each of the questions posed above, the default answer in each case is this straight-forward, perfect world architecture since it requires the least effort to build. In each case however it is also necessary to consider how physical constraints can force the undertaking of more complicated strategies, but again, it should be emphasized that in the absence of any such physical constraints, the simplicity of the perfect world approach is the way to go.