Hello Frank, On Fri, 22 Feb 2008, lankvelt wrote: > http://www.slideshare.net/nielsvk/wicket-plugin-architecture. This code is > available under APL and we would like to share as much as possible with the
I finally got around watching the presentation slides (unfortunately Slideshare didn't work on my phone :)). Your project looks interesting and certainly ambitious! > phases. In the "request" phase, the message travels up the hierarchy, where > each plugin calls its parent plugin until one is found that handles it. A > message is handled by turning it into a "notification" and sending it to all > the children. Messages themselves consist of a description ("browse" or > "edit") and a model. The normal Wicket findParent() and visitChildren() seem to fit nicely in here, right? And you could use marker interfaces to denote these components. I suppose that the current version of the WICKET-1312 event mechanism might work as well, because all events are broadcasted to everybody interested in the page. However, something more is needed if you need to have communication between components on different pages. > For the event option, I think your patch provides a useful starting point. Thanks!-) > I would suggest to scope events by providing a separate interface that is > implemented by components that handle events/messages. When a component > wants to broadcast, it uses findParent() to get a broadcaster. This should > also give the possibility to override the broadcaster with a more > specialised version, e.g. to also broadcast to disconnected plugins. This might bring up problems with unit testing: in a unit test, you typically want to test a single component as much isolated as possible, and making a special parent necessary for changing the broadcaster to a test double sounds laborious. However, I just now made a better version of the patch (and attached it to the issue https://issues.apache.org/jira/browse/WICKET-1312?focusedCommentId=12579082#action_12579082 ), where the EventBroadcaster instance is being held in Application, and created in Application.newEventBroadcaster(). Now it would be trivial to override newEventBroadcaster() to return a specialised broadcaster version, for example one that uses findParent() to get a special component for dispatching the event further. > Separately, I don't really understand why the patch insists on separate > onEvent() methods for different events. Wouldn't it be easier to just have > the one, use marker interfaces to indicate what events to receive and check > the event type with instanceof? This is a matter of coding style, I suppose. I wanted to make the code using the framework as clear and simple as possible, perhaps with the cost of added complexity inside the framework, and separate onEvent() methods for different event types feels clearer and more elegant to me than the instanceof checks. That way, you can see right away from the signature of the component class which events it handles. The reflection stuff within the implementation, and the magic value "onEvent" are a bit ugly, but in practice they haven't caused a lot of problems in our project (we use something like the proposed event mechanism). Our original version actually used a generified EventReceiver<T extends Event>, and it would have been the best solution, but unfortunately it doesn't work for receivers receiving multiple event types because of the runtime type erasure of the Java generics implementation :( (You can have onEvent(Event<Foo>) and onEvent(Event<Bar>) in the same class in C++, but not in Java.) > In the "model changed" architecture, a shared model represents the state of > the application in a simple model. The model is a map that connects > descriptions to other models. Components use these referenced models and > can repaint when they change. It should be possible to maintain > composability by using an indirection between the component internal list of > model names and the descriptions in the map. This is a very simple > communication model but, since we haven't used it so far, it is difficult to > see whether it is sufficiently powerful in general. I have found sharing models a very powerful technique in a "smaller scale", when the components sharing the model are in all senses close to each other. The pull-style feels more wickety, but unfortunately the Ajax events and the need to repaint components don't fit well with it. And if the interconnected components are far away from each other, sharing the model gets tedious. I'm not sure if I understand your version of "model changed" architecture, maybe it has some improvements over plain common IModels between componenets. > If there is an interest in the plugin architecture, we can start working on > the next revision as a wicket extension. Ideally, this builds on an > existing event mechanism so I hope you'll excuse any seemingly ridiculous > requirements of flexibility. My original intention with the event mechanism is to provide something very basic and foolproof, but reusable and extendable. Let's hope that Wicket ends up with something that delivers this and helps in your project as well! Thanks for commenting and please comment more, people! Also viewpoints from the core devs would be great, for example on the issue of whether it's unthinkable or a practical possibility to include some version of the event mechanism already in the 1.3 branch (1.3.3?). Also note that the mechanism has very little code and builds on top of plain Wicket 1.3 -- you can easily copy-paste the code from the patch to your project to try and see how it feels in practice (it's under Apache license like Wicket). I'm grateful for all feedback. Best wishes, Timo -- Timo Rantalaiho Reaktor Innovations Oy <URL: http://www.ri.fi/ >