Developing with Cocoon is a fun and rewarding experience, especially because it is hard write non-scalable webapps on the platform. Alot of this has to do with the limitations on the developer, and forcing them to Do the Right Thing(TM). Most of the enhancments have come out of a real need. I believe we have one more.
The action we have has an interface that is simple, for a reason. We want to be able to encourage ThreadSafe programming. I don't ever want to lose that. However, we have to come to grips with the fact that not everything follows this ideal world. One example was that someone wanted to use an Action to obtain a resource from a database (XML:DB to be exact), but needed a way to release the resources at the end of the pipeline. I think this is a reasonable request, but it does raise some questions. * Which pipeline? One master pipeline that makes use of aggregation or the "cocoon://" protocol is made up of several shorter pipelines spliced together. * How do we handle action sets? * Should things like this be handled by a different mechanism? So, how do we come up with a model that works? The basic problem restated is that we need a way of holding on to resources for the length of the request. After the request is over, the resource is released. Logically, this makes sense, but putting something like this together is difficult in practice. The issue actually stems from our greatest asset: components. The very Component Based Design that Cocoon is built with affects how things work together. The easiest design to implement is one that acts on immediate need. As an analogy, I will use memory management. In assembly and machine language, the programmer is required to manually set up the work areas, and perform all work within those areas. This is equivalent to Pre-Cocoon days where your logic, content, and display information were all mixed together in one resource. It is the way you work with JSP, ASP, and ColdFusion. We all know this is bad, and don't want to go back to those awful working conditions if we can help it. With the advent of higher level languages like C and C++, we were given the blessing and curse of heap managed memory allocation. It was great because now we didn't need to set asside work areas ahead of time. Sure there was a performance penalty for allowing the OS to set up your memmory allocation and management, but it was worth it. If you were careful, you would allocate and deallocate your memmory as you needed to. The problem came when you had to have some allocated memmory persist between scopes. It is easy to remember to deallocate memmory when you use it all in the same method. But what if you needed to hand that memmory reference to another method--one that you may not have written? If the memmory was deallocated by that method your were SOL (S**t Out of Luck--a military acronym). This is where Cocoon is now. If a Component is asked for (looked up), you have to be careful to release it--otherwise it *may* cause resource leaks. Then cam Java and a slew of other languages that favor garbage collection to explicit deallocation. You have no direct control over when a memmory area is going to be reclaimed, but you do know it won't happen while you are still referencing it. That means you can pass the memmory reference around your program without fear of it being deallocated. This is where Cocoon needs to go. In other words, Cocoon needs a mechanism to 1 have a reference to a resource (Component or Object) last for an entire request. At the end of the request, the resources are cleaned up. So how do we design something like this without screwing our heads? The first is to narrowly define the scope and access of these objects. The second is to mark these objects with an interface so they can be handled properly. This does require some repurposing of the RequestContext I proposed recently. While many people are against using the RequestContext as a "communications" area, it is perfectly suitable for passing object references for the life of one request. In order for the RequestContext to behave properly, and enforce the contracts of mapping resouces to specific names, the put() method must be write-once. That means you can never overwrite a resource. It also means that the developer needs to be smart about the resource names he uses. We should not impose a strict naming scheme, but offer one that should be scalable--especially considering the Cocoon WebApp proposal by Stefano. One proposed naming scheme would be much like URLs: http://infoplanning.com/schematic-access/user Another would be a simpler form of the above version: infoplanning.com:schematic-access/user Still another solution would be equivalent to the java pakage/classname solution: com.infoplanning.schematic-access.user Using replacement variables, the resources would be named with these variables: ${company.domain}:${project.name}/${object.name} This ensures that the probability of you having a unique name within a system is high. The developer may find that adding one more level to the heirarchy might make sense (i.e. a ${module.name}), but it isn't necessary for most projects. Next, we need to specify where the resource collection happens. In order to maintain the simplest and most portable solution, I would propose the RequestContext be managed by the Cocoon object. That way, it is handled the same no matter what the environment is. Lastly, we need to provide a marker interface for resources that must be properly released when the request is over. Objects like Strings, and non-pooled objects can simply have their references nullified. Other objects like the resources mentioned above need a Reclaimable interface with a single method, reclaim(). For instance: public interface Reclaimable { void reclaim(); } The Reclaimable interface tells the resource to clean up after itself. It is up to the implementor of the Reclaimable interface to decide on the exact mechanism. The usual method would be to store a reference to it's pool or component manager and call put() or release() on it. This way, Cocoon is not altered too much architecturally, and the ComponentManager/Selectors are not altered from their purpose. Finally, it also means that encouraging the use of RequestContext for these types of things encourages a consistent design and method of cleanup. --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, email: [EMAIL PROTECTED]