assertTrue is the professional blog of Luke Bayes and Ali Mills

No Try..Catch from EventDispatchers in ActionScript 3.0?

Posted by: Luke Bayes Tue, 17 Oct 2006 20:59:00 GMT

Wow…

I was just doing some work on event handling with AsUnit 3.x and discovered something pretty strange. It seems that if an event handler throws an exception, there is no way to catch it from the initiating thread. For some reason, if an exception makes it to the EventDispatcher, it just passes right through all encountered catch/finally blocks and goes right up to the player as an uncaught exception.

Just copy the following code into a new ActionScript project in FlexBuilder and make it your default application to see this in action:

package {
    import flash.display.Sprite;
    import flash.errors.IllegalOperationError;
    import flash.events.Event;
    import flash.events.EventDispatcher;
    import flash.events.IEventDispatcher;

    public class EventDispatcherTest extends Sprite {

        private var dispatcher:IEventDispatcher;

        public function EventDispatcherTest() {
            runTests();
        }

        public function runTests():void {
            dispatcher = new EventDispatcher();
            dispatcher.addEventListener(Event.CHANGE, someHandler);
            try {
                // Uncomment this line to see the catch work...
                //someHandler(new Event(Event.CHANGE));
                dispatcher.dispatchEvent(new Event(Event.CHANGE));
            }
            catch(error:*) {
                trace("Exception has been caught!");
            }
        }

        private function someHandler(event:Event):void {
            trace("someHandler called");
            throw new IllegalOperationError("AnyException");
        }
    }
}

This will throw an exception up to the player with a call stack that looks like this:

Error: AnyException
    at EventDispatcherTest/EventDispatcherTest::someHandler()[...EventDispatcherTest\EventDispatcherTest.as:31]
    at flash.events::EventDispatcher/flash.events:EventDispatcher::dispatchEventFunction()
    at flash.events::EventDispatcher/dispatchEvent()
    at EventDispatcherTest/runTests()[...EventDispatcherTest\EventDispatcherTest.as:22]
    at EventDispatcherTest$iinit()[...EventDispatcherTest\EventDispatcherTest.as:13]

You can see from the call stack that the exception actually passed through the “runTests” method – but didn’t get caught!

I’m really not sure what to make of this, but I think we’re about to have to roll our own event management!

Those of you using AsUnit 3.x should know that because of this issue, the old recommended way of testing event handlers in AS 2 by throwing an “AssertionPassedError” won’t work in AS 3.

Anyone else run into this? Perhaps there is something simple that we can do differently to avoid this behavior?

Tags , ,  | no comments

Flex2 MXML Project Support in AsUnit

Posted by: Luke Bayes Thu, 05 Oct 2006 19:59:00 GMT

[Updated on 10/12/2006 because of changes to the available release]

I’m excited to announce cleaner support for MXML projects in AsUnit!

The latest framework build found in sourceforge svn now has support for Flex applications. This new build allows you to create and run unit tests against visual entities that both do extend UIComponent, and do not extend UIComponent! Just call addChild() in your setUp method and AsUnit will figure out what to do with it.

This is a huge deal if you’re working on Component development because some components may compose visual entities that don’t implement IUIComponent. If you simply build your Application test fixture using the FlexRunner base class, whenever you call addChild() in a TestCase, the framework will determine where to attach that child. If it’s an IUIComponent, it will be attached to the Application directly, if it is not an IUIComponent, it will be attached to the Application.rawChildren array.

Following is an example test Fixture using the latest sources from svn. Just copy the code into a file and name it “ProjectNameRunner.mxml” (replace ProjectName with your project name), and tell FlexBuilder to use that File as the Application root.

<?xml version="1.0" encoding="utf-8"?>
<FlexRunner xmlns="asunit.textui.*" xmlns:mx="http://www.adobe.com/2006/mxml" creationComplete="runTests()">
    <mx:Style source="../css/Lifebin.css"/>
    <mx:Script>
        <![CDATA[
            import asunit.textui.TestRunner;

            public function runTests():void {
                start(AllTests, null, TestRunner.SHOW_TRACE);
            }
        ]]>
    </mx:Script>
</FlexRunner>

Just manage the start() method the same way you always would in the past and you’re up and running!

A quick explanation of the start method:
start(test:Class, method:String=null, showTrace:Boolean=false):void;

test:Class argument should reference the Class definition of a TestCase or TestSuite – something that implements the Test interface.

method:String=null argument is an optional string name of a single method to execute. This is really important when testing visual entities because if this argument is not null, only the test method identified will be executed and tearDown/cleanUp will not be called. This gives you the ability to actually see and interact with the visual entity while testing. Once it’s working and your tests are passing, leave the argument null so that all test methods will be called.

showTrace:Boolean=false argument will send the TestResult string to the trace window when all tests have finished executing. This argument is great if you’re like me and keep closing the running swf, but then want to see some detail in a failure. It’s also essential for hooking AsUnit up to some external continuous integration tool.

Tags  | no comments

Asynchronous Test Methods in AsUnit!

Posted by: Luke Bayes Thu, 05 Oct 2006 19:40:00 GMT

Thanks to some gentle prodding from the Eyefodder “Deathmatch” and more than a small handful of requests, We finally got asynchronous test methods working in AsUnit!

We have also introduced much more robust support for Flex 2 applications.

The latest build of AsUnit 3.x (in Subversion only) has these features but we need your help to test them out.

Please pull down the latest sources from sourceforge svn by opening a terminal and performing the following steps: (you must have subversion client installed and available in your path)

mkdir asunit
svn co https://svn.sourceforge.net/svnroot/asunit/trunk/framework/as3 .
(the trailing period will put the files into the current directory without creating another subdirectory).

Here is an example of an asynchronous test method:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
public function testAsyncFeature():void {
    // create a new object that dispatches events...
    var dispatcher:IEventDispatcher = new EventDispatcher();
    // get a TestCase async event handler reference
    // the 2nd arg is an optional timeout in ms. (default=1000ms )
    var handler:Function = addAsync(changeHandler, 2000);
    // subscribe to your event dispatcher using the returned handler
    dispatcher.addEventListener(Event.CHANGE, handler);
    // cause the event to be dispatched.
    // either immediately:
    //dispatcher.dispatchEvent(new Event(Event.CHANGE));
    // or in the future < your assigned timeout
    setTimeout( dispatcher.dispatchEvent, 200, new Event(Event.CHANGE));
}

protected function changeHandler(event:Event):void {
    // perform assertions in your handler
    assertEquals(Event.CHANGE, event.type);
}

That should be enough to get you going with Asynchronous test methods!

Please let us know on this list if you have any problems.

Thanks,

Luke Bayes

www.asunit.org

Tags  | no comments

Getting Started With The AsUnit 2.5 Framework

Posted by: Luke Bayes Fri, 10 Mar 2006 08:04:00 GMT

It’s 1:48am.

I suppose it’s as good a time as any to break in the new blog…

Ali and I have been working furiously over the past few weeks cleaning up AsUnit for our Flashforward presentation. While doing all this work, we have been spending quite a bit of time thinking about all the things that bother us about AsUnit, and trying to fix them one at a time. One of the biggest things is (and has always been) the separate results panel (or AsUnitUi.swf). We recently resolved this particular issue for ActionScript 3.0, but I have been concerned about leaving the ActionScript 2.0 build as a poor, neglected child. Some recent decisions that we made about our own product releases have revived our interest in ongoing support for ActionScript 2.0 projects.

Basically, the separate results panel is the result of some pretty big architectural tradeoffs that we made back in 2004 with our first release. We originally wanted a test framework that would support applications that run in the browser, on the desktop and on mobile devices.

At the time, the newest player that ran on devices was Flash Player 6. So we got stuck in supporting the least common denominator. This meant no Try..Catch statements. We were also concerned about placing the result UI directly onto the stage because the results panel could be inadvertently clobbered by some random attachMovie call when trying to test visual entities. We had another problem in that we were using V2 Components in the results panel, and they do some pretty gross mixins to the core prototype chain. Injecting V2 Component code into the test environment for an application that doesn’t ship with the same code meant that we would be testing in an environment that was significantly different from what we were planning on shipping. The best (simplest?) thing we could come up with was a completely separate SWF file for presenting test results, and sending those results over LocalConnection.

These decisions led us down a long and slippery slope that ultimately meant we couldn’t directly port the JUnit implementation to ActionScript, and basically AsUnit has been running with some pretty big development, performance and reliability issues that have remained unresolved – until now…

Read more...

Tags  | 6 comments

Test-Driven Development with ActionScript 3.0

Posted by: Ali Mills Thu, 09 Mar 2006 15:50:00 GMT

On March 2nd, Luke and I presented at Flashfoward on the topic “Test-Driven Development with ActionScript 3.0”. The talk covered ActionScript 3.0, Flex Builder 2.0, and AsUnit. We had a blast giving it and were stunned at the level of attendence. For all who attended, we thank you for being there! For those who couldn’t make it, we’ve posted our presentation notes. They follow:

Read more...

Tags  | no comments

Older Posts

Older posts: 1 2