How to test a Command with FlexUnit4?

Gert-Jan van der Wel's Avatar

Gert-Jan van der Wel

12 Dec, 2009 03:58 PM

We're doing some tests with Robotlegs for a new application and it looks very promising! For this app we're also starting to use FlexUnit4.

I was wondering how I could test a single Command. Do I have to instantiate it myself or do I have to use the Injector for this? If I do this, are the dependencies injected by Robotlegs?

Another thought was to create a mock Context, register the Command and throw an Event from my test. I guess the dependencies are injected like they should. Is this the way to go?

  1. Support Staff 1 Posted by Joel Hooks on 12 Dec, 2009 05:05 PM

    Joel Hooks's Avatar

    I don't think you need to test that Robotlegs actually fires a command. The framework itself has rather good unit tests.

    If you are integration testing, I'd say the important bit is if the Command execute method does the work it is supposed to do. This would entail creating an instance of the Command, supplying its dependencies (manually), calling execute, and then testing that the work is performed properly on the dependencies.

  2. Support Staff 2 Posted by Shaun Smith on 12 Dec, 2009 07:53 PM

    Shaun Smith's Avatar

    Another way, which is almost the same as Joel's suggestion above, is to use an injector to instantiate your command - that way an Error will be thrown if you forget to supply any of the Command's dependencies. Something like this:

    var injector:Injector = new Injector();
    injector.mapValue( SomeDependency, new SomeMockDependency() );
    var command:Command = injector.instantiate( Command );
    command.execute();

    If you are testing a suite of Commands, you could shift some of that into setup/teardown methods.

  3. 3 Posted by Gert-Jan van de... on 12 Dec, 2009 09:22 PM

    Gert-Jan van der Wel's Avatar

    @Joel No, I'm not creating tests for the framework, I'm having a hard enough time with my own apps :-)

    I tried to instantiate my command directly, but in a certain case, an event is thrown from within the command (which I forgot to mention in my first post...). It would be nice to test the handling of that event too.

    @Shaun Would this work if I'd use the Injector? Btw, where can I find the Injector class to import, or does my test class needs to extend some base class?

  4. Support Staff 4 Posted by Joel Hooks on 12 Dec, 2009 09:32 PM

    Joel Hooks's Avatar

    If you want to test for an event create an async test method and
    listen for the event.

    Isolation and explicitness is the key. Test for one thing.

    I personally don't think automated dependency injection has any place
    in unit tests, but I'm a bit pedantic about the whole thing ;)

  5. 5 Posted by Gert-Jan van de... on 12 Dec, 2009 09:45 PM

    Gert-Jan van der Wel's Avatar

    Okay, so if I understand correctly I should be able to test my command without any knowledge from the outside world (in isolation). I guess this means that throwing events from a command isn't best practise and I should refactor it?

  6. Support Staff 6 Posted by Joel Hooks on 12 Dec, 2009 10:00 PM

    Joel Hooks's Avatar

    Commands are perfectly suited for dispatching events. You can simply
    test that the event is in fact dispatched (but not be concerned with
    other classes in the broader app that would listen/respond to the event)

  7. Support Staff 7 Posted by Shaun Smith on 12 Dec, 2009 10:07 PM

    Shaun Smith's Avatar

    Regarding the injector route:

    You can use org.robotlegs.adapters.SwiftSuspendersInjector or SwiftSuspender's Injector directly.

    One (major) annoyance with going this route is that you will have to supply rules for all the injection points (dependencies) declared on the base Command (org.robotlegs.mvcs.Command) if you extended it, of which there are 5 (!), which seems like quite a big price to pay for the single benefit of dependency checking.

    Perhaps it's simpler and cleaner to just instantiate the Command yourself and supply the required dependencies manually (just the ones you actually need). At the end of the day, your test will explode if it is missing a dependency in any case.

    If your Command dispatches an event, be sure to supply it's IEventDispatcher dependency:

    var command:MyTestCommand = new MyTestCommand();
    command.eventDispatcher = new EventDispatcher();
    command.someOtherDependency = new SomeOtherDependency();
    command.execute();

  8. 8 Posted by Gert-Jan van de... on 12 Dec, 2009 10:24 PM

    Gert-Jan van der Wel's Avatar

    Thanks guys! This was really helpful.

  9. Joel Hooks closed this discussion on 14 Dec, 2009 05:42 AM.

Comments are currently closed for this discussion. You can start a new one.

Keyboard shortcuts

Generic

? Show this help
ESC Blurs the current field

Comment Form

r Focus the comment reply box
^ + ↩ Submit the comment

You can use Command ⌘ instead of Control ^ on Mac