See below for inserted comments.
Jari Worsley wrote:
> I too followed the thread, some good ideas here - keep them "open" in
> this forum and we can all use them :)
>
> As we're back onto this, I've got a few questions below about
> responsibilities and behaviour. It'd be good to get opinions of those
> "at the coal face" who have written large jsp projects.
>
> <snip>
> > The general organization of request processing in my apps goes like this:
> >
> > * Input form is created by a JSP page (normally using beans
> > found in the user session to remember previous input values).
> >
> > * When the user presses submit, the form is posted to a servlet
> > with a URL that lets the servlet figure out what processing is
> > required (see below for more on this).
> >
> > * Servlet receives the request, figures out which action class to use,
> > and calls that action class. The action class is usually very short --
> > its main purpose is to serve as an adapter between the HTTP request
> > view of the input parameters and the bean properties (and method
> > calls) that implement the business logic.
>
> >
> > * The action procedure stores the results of its processing as either
> > request beans or session beans (depending on how long the results
> > need to be alive).
>
> It sounds indeed like the "Adapter" pattern out of the Gang of 4 Design
> patterns book. So "Actions" are presumably very light weight classes,
> and stateless?
That is a good description of the way I use actions. They primarily adapt from the
HTTP-centric view of the data (requests with parameters) to the JavaBeans-centric view
of the data used by the rest of my application logic.
I just sent a separate response that describes how this works in a little more detail.
>
> However:
> Clarification here for the architecture. Do you
> - implement business processing inside the action classes, or do you
No
>
> - use the action merely to turn an html request into a sensible, sanity
> checked and validated Java method call, and then handle the business
> logic using a different pattern, like the "command" pattern.
>
Yes.
The business logic is encapsulated in beans, which might be remote references to EJB or
RMI objects, or might be local to the JVM. From the viewpoint of the action procedure,
it does not know -- my CustomerBean is actually an interface that can be implemented in
multiple ways, and I choose the appropriate one when I glue the whole thing together.
>
> The latter approach could be more flexible if there is a need to have
> many different interfaces onto the same business process logic. I.e. you
> have stateful business objects, like "Customer", "Order" etc (and why do
> we _always_ use Customer and Order as the examples... ;),
That is the curse of e-commerce systems ... everyone knows what they are :-)
> then you have
> either behaviour on the object, or series of "Processes" that can happen
> to these objects, like "PrintOrders" (sort of single Use Case
> granularity). Then the core business object code, _and_ the process
> control logic can be accessed via JSP (and an "Action" adapter class),
> or by a windows or unix standalone application, by a batch script etc.
> The "Action" adapter classes then contain no business control logic at
> all.
>
> How much can this separation happen. And if this approach were followed,
> what of validation, or authentication? In which layer would you put the
> authentication logic? On the Action? or on the "Command" classes? or
> anywehere and everywhere ;) ?
>
For validation, it works the way I described in my previous response -- the
CustomerBean includes a validate method that returns either an error message string, or
a null (if everything works right).
For authentication, again I've used two different approaches. Prior to servlet API 2.2
I implemented a really simple authentication and access control mechanism in my
controller servlet (which received every request to do anything interesting, so was
convenient for enforcing centralized control). In some cases, action procedures had to
include checks for specific user capabilities.
Now that servlet 2.2 is out and becoming available, I will happily start using
container-managed security and never have to worry about this stuff ever again. At the
moment, the integration between the servlet container and your authentication database
is specific to each container vendor, but it's not too tough to centralize these
dependencies into a single class.
>
> >
> > * The controller servlet then forwards (RequestDispatcher.forward())
> > to the appropriate JSP page to display the results.
>
> .. and presumably you get the appropriate page from the Action class
> itself?
>
It forwards to the appropriate JSP page to display the results, as described in more
detail in my other response. The main reason for this is that there is more than one
possible appropriate page -- for example, an input error should return to the original
form, while successful completion should go somewhere else -- and I my action procedure
is essentially an extension of the servlet's doGet()/doPost() methods, so it can use
RequestDispatcher.forward() for this.
>
> I wonder if it's possible to do it slightly differently, and allow the
> Action class to do the forward itself.
Great minds think alike! :-)
> It is after all in the best
> position to "know" whether it needs to throw to an error page, or a
> login page, or display results etc. Also, if the Action is allowed to do
> the forward itself, then you could potentially chain actions together
> (Chain of Responsibility pattern). So an "Authenticate" Action can be
> written. The first time someone hits the authenticate action, it can
> immediately forward to a login page, then back to the protected action.
> Subsequent times, the Authenticate action happens transparently, and
> allows the protect action to run. This "chain" could be extended to
> include things like site logging, or user tracking etc. What I can't
> decide is if this behaviour belongs in the "Actions" or whether at a
> more business focused level (or everywhere).
>
> So should actions be chainable?
> More thoughts on chaining? and action granularity?
>
I've written a lot of applications over the years, and have never really found much
value in "chaining" as you describe at the application level. I prefer to keep my
application layer functionality as simple as possible (although you could say that my
use of the controller servlet to implement authentication checking is sort of chaining
in the sense you describe).
However, at the server level (I'm currently authoring a proposal for the insides of the
Tomcat servlet engine in the Jakarta project -- http://jjakarta.apache.org), the
ability to add layers of request processing functionality is very valuable. For
instance, if you install Tomcat stand alone (without a web server), you might want to
add a request processing layer to produce a web-server-like access log, but if you are
attached to Apache you don't need it. Likewise, you should only incur the overhead of
the container-managed security stuff if you're actually using it for a particular app.
This is easily done if the configuration of the server allows you to add these layers
per application.
Craig McClanahan
===========================================================================
To unsubscribe: mailto [EMAIL PROTECTED] with body: "signoff JSP-INTEREST".
FAQs on JSP can be found at:
http://java.sun.com/products/jsp/faq.html
http://www.esperanto.org.nz/jsp/jspfaq.html