You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@commons.apache.org by Jeff Caddel <jc...@cox.net> on 2003/11/06 05:30:35 UTC

[Chain] ContextToRequestCommand

Any feedback on this Command implementation?

The idea is that as a chain of commands is executing objects get 
aggregated into a map.  The context holds a reference to the map.  At 
the tail end of the execution chain, this command places the objects 
from the map into the request as request attributes so that front end 
components (Tiles, JSP's etc) can display them.


Is this:
A) A terrible idea violating abstractions of the Chain of Responsibility 
pattern? 
B) A good idea demonstrating good use of the pattern?
C) Something else?


public class ContextToRequestCommand implements Command {
    String key = "contextToRequest";

    public boolean execute(Context context) throws Exception {
        HttpServletRequest request = 
(HttpServletRequest)context.get("request");
        Map map = (Map)context.get(key);
        if (map == null) {
            return false;
        }

        Iterator pairs = map.entrySet().iterator();
        while (pairs.hasNext()) {
            Map.Entry pair = (Map.Entry)pairs.next();
            request.setAttribute((String)pair.getKey(), pair.getValue());
        }

        return false;
    }
}


---------------------------------------------------------------------
To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: commons-dev-help@jakarta.apache.org


Re: [Chain] ContextToRequestCommand

Posted by Robert <ro...@bull-enterprises.com>.
I'm not a commiter, but the idea sounds reasonable to me. I do something 
very similiar in Struts when using Jelly scripts, where I have a struts 
action that takes all of the http 'stuff' and puts it into the jelly 
context, executes a script and then takes the data from the context and 
puts it back into the appropriate http scope.

If this is accepted, A couple more would be nice to have for session and 
  application scope as well.

Robert

Jeff Caddel wrote:
> Any feedback on this Command implementation?
> 
> The idea is that as a chain of commands is executing objects get 
> aggregated into a map.  The context holds a reference to the map.  At 
> the tail end of the execution chain, this command places the objects 
> from the map into the request as request attributes so that front end 
> components (Tiles, JSP's etc) can display them.
> 
> 
> Is this:
> A) A terrible idea violating abstractions of the Chain of Responsibility 
> pattern? B) A good idea demonstrating good use of the pattern?
> C) Something else?
> 
> 
> public class ContextToRequestCommand implements Command {
>    String key = "contextToRequest";
> 
>    public boolean execute(Context context) throws Exception {
>        HttpServletRequest request = 
> (HttpServletRequest)context.get("request");
>        Map map = (Map)context.get(key);
>        if (map == null) {
>            return false;
>        }
> 
>        Iterator pairs = map.entrySet().iterator();
>        while (pairs.hasNext()) {
>            Map.Entry pair = (Map.Entry)pairs.next();
>            request.setAttribute((String)pair.getKey(), pair.getValue());
>        }
> 
>        return false;
>    }
> }
> 
> 
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
> For additional commands, e-mail: commons-dev-help@jakarta.apache.org
> 



---------------------------------------------------------------------
To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: commons-dev-help@jakarta.apache.org


Re: [Chain] ContextToRequestCommand

Posted by "Craig R. McClanahan" <cr...@apache.org>.
Quoting Jeff Caddel <jc...@cox.net>:

> 
> >If your application uses WebContext (or one of it's subclasses) as the
> Context
> >object being passed down the chain, you already have access to the request
> >attributes via the getRequestScope() method.  There's also other
> Map-returning
> >methods on WebContext for lots of other useful stuff (headers, cookies,
> session
> >attributes, context attributes, context init parameters, ...).
> >
> Ahhhh.  Brain cells starting to click now.  One huge benefit of exposing 
> them as map's being that you can make use of generic bean manipulating 
> code to mess with them, right?  Instead of making API specific calls 
> like getAttribute/setAttribute.
> 

That is certainly one benefit.  A second benefit is the concept of "request
attributes" works across both servlet and portlet environments, without tying
your application code to one or the other underying API for accessing the
request object (and the same principle applies on session and application
scope).

> >
> >On the attribute collections in particular, the Map implementation is
> two-way
> >... for example, usage like this:
> >
> >  public boolean execute(Context context) throws Exception {
> >    ...
> >    WebContext wcontext = (WebContext) context;
> >    // Following is equivalent to request.getAttribute("foo")
> >    String fooValue = wcontext.getRequestScope().get("foo");
> >    // Following is equivalent to request.setAttribute("foo", "bar")
> >    wcontext.getRequestScope().put("foo", "bar");
> >    ...
> >  }
> >
> Which is better since nothing in this implementation makes a servlet 
> specific API call.  If I needed the value "bar" to be present under the 
> attribute "foo" in a portlet environment (for example), this command 
> could be re-used.
> 

Yep.

I should have noted that you can also leverage the attribute-property
transparency built in to the base Context implementation, and say:

  Map requestScope = (Map) context.get("requestScope");

without needing the explicit cast to WebContext.

> >
> >makes a request attribute named "foo" with value "bar" visible to a JSP page
> (or
> >whatever) that will ultimately create the response.
> >
> If I'm getting this right, I could also place "bar" into the request 
> under the attribute "foo" (in an API independent manner, nonetheless) by 
> simply configuring a CopyCommand:
> 
> <command className="org.apache.commons.chain.generic.CopyCommand" 
> toKey="requestScope.foo" from="foo"/>
> 

Right now this wouldn't work -- it would put the object into the Context itself
under key "requestScope.foo" -- but one could certainly create a Copy command
that interpreted the keys as expressions.

> (Assuming that some other previous bit of logic had placed "bar" into 
> the context under the key "foo".)
> 
> Holy smokes...how easy is that!!
> 

:-)

> >
> >Does this satisfy the sorts of requirements you were after?
> >
> Fit's the bill quite nicely, Craig.  Thanks.
> 

Craig


---------------------------------------------------------------------
To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: commons-dev-help@jakarta.apache.org


Re: [Chain] ContextToRequestCommand

Posted by Jeff Caddel <jc...@cox.net>.
>If your application uses WebContext (or one of it's subclasses) as the Context
>object being passed down the chain, you already have access to the request
>attributes via the getRequestScope() method.  There's also other Map-returning
>methods on WebContext for lots of other useful stuff (headers, cookies, session
>attributes, context attributes, context init parameters, ...).
>
Ahhhh.  Brain cells starting to click now.  One huge benefit of exposing 
them as map's being that you can make use of generic bean manipulating 
code to mess with them, right?  Instead of making API specific calls 
like getAttribute/setAttribute.

>
>On the attribute collections in particular, the Map implementation is two-way
>... for example, usage like this:
>
>  public boolean execute(Context context) throws Exception {
>    ...
>    WebContext wcontext = (WebContext) context;
>    // Following is equivalent to request.getAttribute("foo")
>    String fooValue = wcontext.getRequestScope().get("foo");
>    // Following is equivalent to request.setAttribute("foo", "bar")
>    wcontext.getRequestScope().put("foo", "bar");
>    ...
>  }
>
Which is better since nothing in this implementation makes a servlet 
specific API call.  If I needed the value "bar" to be present under the 
attribute "foo" in a portlet environment (for example), this command 
could be re-used.

>
>makes a request attribute named "foo" with value "bar" visible to a JSP page (or
>whatever) that will ultimately create the response.
>
If I'm getting this right, I could also place "bar" into the request 
under the attribute "foo" (in an API independent manner, nonetheless) by 
simply configuring a CopyCommand:

<command className="org.apache.commons.chain.generic.CopyCommand" 
toKey="requestScope.foo" from="foo"/>

(Assuming that some other previous bit of logic had placed "bar" into 
the context under the key "foo".)

Holy smokes...how easy is that!!

>
>Does this satisfy the sorts of requirements you were after?
>
Fit's the bill quite nicely, Craig.  Thanks.

>
>Craig
>
>
>---------------------------------------------------------------------
>To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
>For additional commands, e-mail: commons-dev-help@jakarta.apache.org
>
>
>  
>



---------------------------------------------------------------------
To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: commons-dev-help@jakarta.apache.org


Re: [Chain] ContextToRequestCommand

Posted by "Craig R. McClanahan" <cr...@apache.org>.
Quoting Jeff Caddel <jc...@cox.net>:

> Any feedback on this Command implementation?
> 
> The idea is that as a chain of commands is executing objects get 
> aggregated into a map.  The context holds a reference to the map.  At 
> the tail end of the execution chain, this command places the objects 
> from the map into the request as request attributes so that front end 
> components (Tiles, JSP's etc) can display them.
> 

If your application uses WebContext (or one of it's subclasses) as the Context
object being passed down the chain, you already have access to the request
attributes via the getRequestScope() method.  There's also other Map-returning
methods on WebContext for lots of other useful stuff (headers, cookies, session
attributes, context attributes, context init parameters, ...).

On the attribute collections in particular, the Map implementation is two-way
... for example, usage like this:

  public boolean execute(Context context) throws Exception {
    ...
    WebContext wcontext = (WebContext) context;
    // Following is equivalent to request.getAttribute("foo")
    String fooValue = wcontext.getRequestScope().get("foo");
    // Following is equivalent to request.setAttribute("foo", "bar")
    wcontext.getRequestScope().put("foo", "bar");
    ...
  }

makes a request attribute named "foo" with value "bar" visible to a JSP page (or
whatever) that will ultimately create the response.

Does this satisfy the sorts of requirements you were after?

Craig


---------------------------------------------------------------------
To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: commons-dev-help@jakarta.apache.org