Passive View is another presentation pattern that can be used to increase the testability of graphical applications. It does this primarily by extracting all logic and state from your views, making it pointless to test the view itself. In fact, in the article linked above, Martin Fowler says the following:
With the view reduced to a dumb slave of the controller, you run little risk by not testing the view.
You instead test the component to which the logic and state have been extracted. This component can be referred to by names such as mediator, presenter or controller but the name itself is irrelevant. What is important is that it is not a view component (meaning it does not exist on the display list, in Flash/Flex specific terms), which are inherently hard to unit test. In the example application I have created I refer to these components as mediators.
For this post I have simply converted the Swiz example application I created using the Presentation Model pattern. The conversion took maybe 30 minutes, which includes looking up some of the specifics of the pattern, because I had not actually implemented it before.
Application :: Source
One of Swiz’s biggest strengths is the flexibility it affords you when using it. Rather than enforcing (or even suggesting) a particular architecture, it provides tools and utilities that help you to create well architected applications. I think showing the same application built with different (albeit similar) presentation patterns demonstrates this point quite well. I will also admit that I was influenced by the RobotLegs Best Practices document in selecting Passive View as the pattern to demonstrate since they demonstrate/promote the pattern there. Hell, I will even admit there was a bit of “anything you can do, we can do better” sentiment on my part. That is not meant to take anything away from the RobotLegs team as they are certainly a smart bunch of guys, but I wouldn’t have joined the Swiz team if I didn’t think it was the best thing out there.
Thoughts on Passive View
I sort of like that your views become plain MXML with no logic, state or external references whatsoever when using the Passive View pattern. What I don’t like is what your mediator/presenter/controller becomes in order to purge your view of those things. I feel like you end up with a frankenstein class that is part (presentation) model, part controller and part code behind.
It is not truly code behind since it uses composition rather than inheritance, but it feels the same. You are reaching into the view to add listeners to its child components, setting properties directly on its child components, etc. Handling events from those child components is like a controller, but you also end up storing some state for the view as well. You could obviously break that out into a separate model class but for most views that is going to be massive overkill. I suppose that presentation models are or can be somewhat of a controller and model combination as well too though. I think adding all the knowledge of the view and its internals is what creeps me out most.
I also feel like Passive View fights against the platform a bit. Since the view has no references to anything, binding is not an option. The view can only be updated by user interaction or manually from the mediator, and even for the extremely simple example I created this felt very tedious. I also wonder if testing the mediator could not potentially be complicated by needing an instance of the view it mediates for operation. Flex Unit 4 likely overcomes much of what would have been painful in the past in this area, but I feel like removing view components from the testing process completely is ideal.
In summary, I think Passive View is a decent pattern, but I won’t be abandoning Presentation Model to use it. In my opinion the drawbacks outweigh the benefits, but the same may not hold true for your particular needs and/or preferences.
Be sure to read the Martin Fowler piece linked at the beginning of this post (and anything else by Fowler you have time for), and for another example of the Passive View pattern in Flex check out Paul Williams’ post on the topic.