How to programmatically add parameters to ServletRequest objects?

View: New views
11 Messages — Rating Filter:   Alert me  

How to programmatically add parameters to ServletRequest objects?

by Jonathan Mast-2 :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

I can't figure out how to use the pageContext.forward() method like it's
equivalent script element:

<jsp:forward page="page.jsp" >
    <jsp:param name="foo" value="bar"/>
</jsp:forward>

How do I pass the name-value pair "foo":"bar" using pageContext.forward()? I
thought there would be a method like forward(String path, Map params) but
there isn't.

Nor is there a setParameter(name, value) method available on ServletRequest
or ServletResponse (both of which are passed onto the page pointed to in
pageContext.forward().

I don't want to put the parameters in the url itself (ie "page.jsp?foo=bar")
this approach is not scalable.

And I don't want to continue doing what I'm doing now, which is:

<%
     if (blah) {
%>
<jsp:forward page="page.jsp" >
    <jsp:param name="foo" value="bar"/>
</jsp:forward>
<%
     } else if (...) {
%>
<jsp:forward ......
<%
....
%>

Not very pretty and rather error prone.

Thanks in advance

JDK 1.4.2

Re: How to programmatically add parameters to ServletRequest objects?

by Christopher Schultz-2 :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Jonathan,

Jonathan Mast wrote:
| I can't figure out how to use the pageContext.forward() method like it's
| equivalent script element:

Do you mean that you want to add parameters to a forwarded URL without
using JSP?

| How do I pass the name-value pair "foo":"bar" using
pageContext.forward()? I
| thought there would be a method like forward(String path, Map params) but
| there isn't.

Right: you just forward to another URL.

| Nor is there a setParameter(name, value) method available on
ServletRequest
| or ServletResponse (both of which are passed onto the page pointed to in
| pageContext.forward().

Right. The request is supposed to be read-only (ignore attributes ;).

| I don't want to put the parameters in the url itself (ie
"page.jsp?foo=bar")
| this approach is not scalable.

This is really the only way to do it. The other option is to create a
new request object and stuff your own parameters into it (or, better
yet, wrap the original request and add your parameters only to the wrapper).

Why do you believe that adding parameters to the URL is not scalable?

- -chris
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.9 (MingW32)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org

iEYEARECAAYFAkiZ3KwACgkQ9CaO5/Lv0PA+cQCgs/6qvuqQEcK24o6fId1K3kgs
OkMAn3HqZ2E12xFeevo8eKii7yYiKj2p
=Cixo
-----END PGP SIGNATURE-----

---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...


Re: How to programmatically add parameters to ServletRequest objects?

by Jonathan Mast-2 :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

| This is really the only way to do it. The other option is to create a
| new request object and stuff your own parameters into it (or, better
| yet, wrap the original request and add your parameters only to the
wrapper).

How would I do this?  This is basically what Jakarta Commons HTTPClient
package (org.apache.commons.httpclient.*) offers, correct?

I thought such manipulation would be achievable without additional packages.


| Why do you believe that adding parameters to the URL is not scalable?
Well, its not scalegent, to coin a term;
String munging is expensive (scalability), and
StringBuffer sb = new StringBuffer();
sb.append("page.jsp?").append("foo=").append(bar).append("&color=").append(myColor).etc()
is rough to look at (elegent).

Why not just:
HashMap myParams = new HashMap();
myParams.put("foo", bar);
...
pageContext.forward("page.jsp", myParams)   ?

much more efficient and elegent, imho.

I understand that it all eventually boils down to a bunch of String munging,
but the above hypothetical method could take of it that for us and would
really make my life easier ;-)

thanks



On Wed, Aug 6, 2008 at 1:17 PM, Christopher Schultz <
chris@...> wrote:

> -----BEGIN PGP SIGNED MESSAGE-----
> Hash: SHA1
>
> Jonathan,
>
> Jonathan Mast wrote:
> | I can't figure out how to use the pageContext.forward() method like it's
> | equivalent script element:
>
> Do you mean that you want to add parameters to a forwarded URL without
> using JSP?
>
> | How do I pass the name-value pair "foo":"bar" using
> pageContext.forward()? I
> | thought there would be a method like forward(String path, Map params) but
> | there isn't.
>
> Right: you just forward to another URL.
>
> | Nor is there a setParameter(name, value) method available on
> ServletRequest
> | or ServletResponse (both of which are passed onto the page pointed to in
> | pageContext.forward().
>
> Right. The request is supposed to be read-only (ignore attributes ;).
>
> | I don't want to put the parameters in the url itself (ie
> "page.jsp?foo=bar")
> | this approach is not scalable.
>
> This is really the only way to do it. The other option is to create a
> new request object and stuff your own parameters into it (or, better
> yet, wrap the original request and add your parameters only to the
> wrapper).
>
> Why do you believe that adding parameters to the URL is not scalable?
>
> - -chris
> -----BEGIN PGP SIGNATURE-----
> Version: GnuPG v1.4.9 (MingW32)
> Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org
>
> iEYEARECAAYFAkiZ3KwACgkQ9CaO5/Lv0PA+cQCgs/6qvuqQEcK24o6fId1K3kgs
> OkMAn3HqZ2E12xFeevo8eKii7yYiKj2p
> =Cixo
> -----END PGP SIGNATURE-----
>
> ---------------------------------------------------------------------
> To start a new topic, e-mail: users@...
> To unsubscribe, e-mail: users-unsubscribe@...
> For additional commands, e-mail: users-help@...
>
>

Re: How to programmatically add parameters to ServletRequest objects?

by Warren Killian :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

Hi Jonathan,

About ServletRequest and ServletResponse Interfaces not having a
"setParameter(name, value)" method...depending on your situation, you may
not need to do that.  Are you forwarding to another URI within your web
app?  If so, you could use request/session.setAttribute( String name, Object
obj ).  My understanding is that HttpParameters come from HTML forms and
can't really be added to using the Servlet API.  But if the web component
you are forwarding to is within your same application, you can store those
values you wish to add to the URL to the HttpServletRequest/HttpSession as
"scoped attributes".  Hope this helps.

On Wed, Aug 6, 2008 at 1:17 PM, Christopher Schultz <
chris@...> wrote:

> -----BEGIN PGP SIGNED MESSAGE-----
> Hash: SHA1
>
> Jonathan,
>
> Jonathan Mast wrote:
> | I can't figure out how to use the pageContext.forward() method like it's
> | equivalent script element:
>
> Do you mean that you want to add parameters to a forwarded URL without
> using JSP?
>
> | How do I pass the name-value pair "foo":"bar" using
> pageContext.forward()? I
> | thought there would be a method like forward(String path, Map params) but
> | there isn't.
>
> Right: you just forward to another URL.
>
> | Nor is there a setParameter(name, value) method available on
> ServletRequest
> | or ServletResponse (both of which are passed onto the page pointed to in
> | pageContext.forward().
>
> Right. The request is supposed to be read-only (ignore attributes ;).
>
> | I don't want to put the parameters in the url itself (ie
> "page.jsp?foo=bar")
> | this approach is not scalable.
>
> This is really the only way to do it. The other option is to create a
> new request object and stuff your own parameters into it (or, better
> yet, wrap the original request and add your parameters only to the
> wrapper).
>
> Why do you believe that adding parameters to the URL is not scalable?
>
> - -chris
> -----BEGIN PGP SIGNATURE-----
> Version: GnuPG v1.4.9 (MingW32)
> Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org
>
> iEYEARECAAYFAkiZ3KwACgkQ9CaO5/Lv0PA+cQCgs/6qvuqQEcK24o6fId1K3kgs
> OkMAn3HqZ2E12xFeevo8eKii7yYiKj2p
> =Cixo
> -----END PGP SIGNATURE-----
>
> ---------------------------------------------------------------------
> To start a new topic, e-mail: users@...
> To unsubscribe, e-mail: users-unsubscribe@...
> For additional commands, e-mail: users-help@...
>
>

Re: How to programmatically add parameters to ServletRequest objects?

by Tim Funk :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

I suggest you look at ServletRequest.setAttribute()

In programming Servlets - you can work with parameters which are the fun
little things which come off the query string or via the POST body.
These items should be thought readonly - and only set/sent from the
HttpClient (aka  - the web browser).

As a programmer - you wish to pass extra information along to other
Servlets, Filters, etc  - the recommended way is to attach that baggage
to the ServletRequest via setAttribute.

In a typical MVC setting - a servlet will use the request parameters to
construction objects which are then placed into the ServletRequest via
setAttribute. Then the servlet forwards to a view and the view pulls all
needed data from the ServletRequest via getAttribute. Using request
parameters in the view is typically an invitation to an XSS attack.

-Tim

Jonathan Mast wrote:

> | This is really the only way to do it. The other option is to create a
> | new request object and stuff your own parameters into it (or, better
> | yet, wrap the original request and add your parameters only to the
> wrapper).
>
> How would I do this?  This is basically what Jakarta Commons HTTPClient
> package (org.apache.commons.httpclient.*) offers, correct?
>
> I thought such manipulation would be achievable without additional packages.
>
>
> | Why do you believe that adding parameters to the URL is not scalable?
> Well, its not scalegent, to coin a term;
> String munging is expensive (scalability), and
> StringBuffer sb = new StringBuffer();
> sb.append("page.jsp?").append("foo=").append(bar).append("&color=").append(myColor).etc()
> is rough to look at (elegent).
>
> Why not just:
> HashMap myParams = new HashMap();
> myParams.put("foo", bar);
> ...
> pageContext.forward("page.jsp", myParams)   ?
>
> much more efficient and elegent, imho.
>
> I understand that it all eventually boils down to a bunch of String munging,
> but the above hypothetical method could take of it that for us and would
> really make my life easier ;-)
>
> thanks
>
>
>
> On Wed, Aug 6, 2008 at 1:17 PM, Christopher Schultz <
> chris@...> wrote:
>
>> -----BEGIN PGP SIGNED MESSAGE-----
>> Hash: SHA1
>>
>> Jonathan,
>>
>> Jonathan Mast wrote:
>> | I can't figure out how to use the pageContext.forward() method like it's
>> | equivalent script element:
>>
>> Do you mean that you want to add parameters to a forwarded URL without
>> using JSP?
>>
>> | How do I pass the name-value pair "foo":"bar" using
>> pageContext.forward()? I
>> | thought there would be a method like forward(String path, Map params) but
>> | there isn't.
>>
>> Right: you just forward to another URL.
>>
>> | Nor is there a setParameter(name, value) method available on
>> ServletRequest
>> | or ServletResponse (both of which are passed onto the page pointed to in
>> | pageContext.forward().


---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...


Re: How to programmatically add parameters to ServletRequest objects?

by Christopher Schultz-2 :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Jonathan,

Jonathan Mast wrote:
| | This is really the only way to do it. The other option is to create a
| | new request object and stuff your own parameters into it (or, better
| | yet, wrap the original request and add your parameters only to the
| wrapper).
|
| How would I do this?  This is basically what Jakarta Commons HTTPClient
| package (org.apache.commons.httpclient.*) offers, correct?

I'm pretty sure you don't want HTTPClient.

What you'd do is write your own new class called something like
AdditionalParameteHttpServletrsRequest and extend
HttpServletRequestWrapper. Override all methods that deal with
parameters and add your own parameters when appropriate.

| I thought such manipulation would be achievable without additional
packages.

It is. You just have to write some of your own code.

| | Why do you believe that adding parameters to the URL is not scalable?
| Well, its not scalegent, to coin a term;
| String munging is expensive (scalability), and
| StringBuffer sb = new StringBuffer();
|
sb.append("page.jsp?").append("foo=").append(bar).append("&color=").append(myColor).etc()
| is rough to look at (elegent).

String munging will be done whether you code it yourself or you delegate
it to some other utility (such as the JSP's version of the same code, or
to HTTPClient, or whatever).

If you don't want to look at the code, put it into a utility method with
an interface like MyParameterUtility.addParameter(String nanme, String
value). That will also give you the opportunity to properly URI-escape
both the parameter names and values.

| Why not just:
| HashMap myParams = new HashMap();
| myParams.put("foo", bar);
| ...
| pageContext.forward("page.jsp", myParams)   ?

Because that's not part of the interface, unfortunately. Feel free to
lobby a member of the JCP to add that method to the RequestDispatcher
(PageContext is a bad place to put something like that).

| much more efficient and elegent, imho.

No, it just hides the code you don't like to see behind an interface.
You are perfectly capable of writing an interface such as that: I
suggest you do it. <shrug>

- -chris
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.9 (MingW32)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org

iEYEARECAAYFAkibA3IACgkQ9CaO5/Lv0PAPxwCfVEbASNxwpcqDmwvFrfJu3BYF
4voAoJW5ZxuVUs88kgIghhVOL2pVLq0+
=5rcT
-----END PGP SIGNATURE-----

---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...


Re: How to programmatically add parameters to ServletRequest objects?

by awarnier :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

Jonathan,

I am a real beginner at Java and Tomcat, and not so good at it.
But maybe that causes my explanation below to be useful.

The hardest thing for me to understand when I wrote my first servlet
filter, was that the HttpRequest object that you receive in the filter,
is not modifiable. In other words, you cannnot just take it, and add a
HTTP header or a parameter to it, before you pass it on to something
else.  Like you, I was looking in vain for methods allowing to do that.

What you need to do is "wrap" the original HttpRequest into your own
custom version of it, and then pass this custom version to further
modules down the chain, to "make them believe" that this is the original
request.
In your custom version, you override the original properties and methods
of HttpRequest as you see fit, so that when the modules down the chain
call these standard methods to get information about the request, they
get your version, instead of the original.
In other words, your custom version of the request becomes like a "man
in the middle" : some method calls it processes itself, responding with
your modified parameters; the rest it lets through to the original
HttpRequest object.  You choose which by re-implementing a method or not
in your wrapper.

For example, suppose that your purpose was to modify the request, to add
an additional HTTP header to it (because some module further down the
chain is expecting it e.g.).
(I guess this is similar to adding a request parameter).

You would then create your own version of the original HttpRequest
(using HttpRequestWrapper), and in it, create a method "getHeaders()".
In that method, you would arrange it so that when a module down the
chain calls HttpRequest.getHeaders(), it obtains the list of headers of
the original request, *plus* the one you want to add.

It's a bit bizarre and feels a bit like overdoing it for someone used to
other environments, but that's how it works, and I suppose there were
good reasons to implement it this way.
One of the snags with it, is that when there are several possibilities
for the module down the chain to get at something in the request, you
have either to guess which one(s) they use, or redefine all of them in
your wrapper.

I attach an example for you, with lots of warnings :
- it works, but I do not guarantee the style, nor that someone more
qualified than me would find some deep flaw in it
- it contains a lot of stuff that you don't need, and I don't have time
to take it all out. But I took out some, so as it is, it may not work
anymore.

The attached filter's main purpose is to add a HTTP header to a request,
before passing it on to the servlet that it filters.
The important part for you is

CustomRequest cr = new CustomRequest(request,context); //
(create request wrapper)
cr.setHeader(authIdHeaderName,authId); // add the new Id header

  and
class CustomRequest extends HttpServletRequestWrapper {

In the CustomRequest class :
I first call the HttpRequestWrapper constructor, passing the original
request as parameter. That returns a HttpRequestWrapper object,
containing the original HttpRequest object.
Then I build my own table of HTTP headers, first copying all the headers
from the original request (there are more elegant ways to do this, I'm
sure).
The "setHeader" method is used above by the filter, to add one or more
aditional HTTP headers to this internal collection.
(You would probably need something similar to add request parameters)

Then I redefine the getHeaderNames() and getHeader() methods of the
original HttpRequest object, so that they will return the headers from
my own internal collection, instead of the headers of the original request.
Any module down the chain which calls "request".getHeaderNames() for
instance, will get the names of the original request's headers, plus the
ones I've added, and they will "believe" that they got the original article.
I only redefine these two methods, because I know that the downstream
application only calls those (referring to the headers).
In your case, you would have to redefine the methods by which downstream
applications would obtain the request parameters.
Any method of the original HttpRequest object not redefined here, will
call the original methods of the HttpRequest object, and receive data
based on that original request.

Does this help ?


---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...

SampleWrap.zip (3K) Download Attachment

Re: How to programmatically add parameters to ServletRequest objects?

by Christopher Schultz-2 :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

André,

André Warnier wrote:
| I am a real beginner at Java and Tomcat, and not so good at it.
| But maybe that causes my explanation below to be useful.

Don't forget to override getDateHeader and getIntHeader in your wrapper
class. Also, don't forget that some headers can have multiple values,
which your code does not allow:

http://tomcat.apache.org/tomcat-5.5-doc/servletapi/javax/servlet/http/HttpServletRequest.html#getHeaders(java.lang.String)

Note that your strategy is the same as my original suggestion to the OP.

- -chris

-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.9 (MingW32)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org

iEYEARECAAYFAkicTzsACgkQ9CaO5/Lv0PAvPgCgpJDdhG6PLrkRS5sQ4oV4IR3z
jhcAniaNj1PXfQ1WzH89Qk3l06hSHaPd
=t1lx
-----END PGP SIGNATURE-----

---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...


Re: How to programmatically add parameters to ServletRequest objects?

by awarnier :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

Christopher Schultz wrote:

> -----BEGIN PGP SIGNED MESSAGE-----
> Hash: SHA1
>
> André,
>
> André Warnier wrote:
> | I am a real beginner at Java and Tomcat, and not so good at it.
> | But maybe that causes my explanation below to be useful.
>
> Don't forget to override getDateHeader and getIntHeader in your wrapper
> class. Also, don't forget that some headers can have multiple values,
> which your code does not allow:
>
> http://tomcat.apache.org/tomcat-5.5-doc/servletapi/javax/servlet/http/HttpServletRequest.html#getHeaders(java.lang.String)
>
Yes, I know, shame on me.  It is mentioned as a limitation in the sample
filter code however.  For the real filter this one comes from, I know
the application that follows, so I know I can afford to do this.

>
> Note that your strategy is the same as my original suggestion to the OP.
>
I know that too.
It's just that you evidently are a much better Java and Tomcat
programmer than many of us, and sometimes your responses seem to be
overly concise for guys like me.  So I tried an explanation for the masses.

I am very pleased and proud by the way that my explanation elicited only
the two remarks above, and was not shown down infamously.
;-)

After making that filter, I thought that it would have been more elegant
to check if the header requested by getHeader() was one I added, return
it in that case, and otherwise just call the getHeader() method of the
underlying HttpRequest object.  But considering it was my first filter,
and that it worked, I was just too lazy and scared to go change it again.

André

---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...


Re: How to programmatically add parameters to ServletRequest objects?

by Christopher Schultz-2 :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

André,

André Warnier wrote:
| After making that filter, I thought that it would have been more
| elegant to check if the header requested by getHeader() was one I
| added, return it in that case, and otherwise just call the
| getHeader() method of the underlying HttpRequest object.

I would consider that a cleaner approach. Plus, it uses a bit less
memory, but we're talking bytes, here, not megabytes, so it's not that
big of a deal. It makes the wrapper feel much more like an actual
"wrapper" when you delegate calls to the wrapped instance.

| But considering it was my first filter, and that it worked, I was
| just too lazy and scared to go change it again.

Sounds good to me. If it ain't broke...

I wasn't trying to sound like a know-it-all: I was just trying to point
out places where you could improve your implementation. Your
self-deprecating writing style invites this kind of commentary, don't
you think? ;)

Keep up the good work.

- -chris
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.9 (MingW32)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org

iEYEARECAAYFAkic0FEACgkQ9CaO5/Lv0PBuvACgpHRTxSQMBrsfcqL4l88yeccu
RzoAn1B9Wjn3NfVZPEIbZKHeU9EwC4WY
=koTk
-----END PGP SIGNATURE-----

---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...


Re: How to programmatically add parameters to ServletRequest objects?

by samsam007 :: Rate this Message:

Reply to Author | View Threaded | Show Only this Message

Hi, I have just configured Eclipse 3.4 with tomcat in windows vista.
The environemt is running JDK1.6 and JRE 1.5, but I have selected
jdk1.6 for the enviornemt.
When I press the Start Tomcat menu in the Eclispe menu bar, it thrown
the following exception in the Eclispe console:

10/08/2008 12:51:14 AM org.apache.catalina.startup.Bootstrap initClassLoaders
SEVERE: Class loader creation threw exception
java.io.IOException: The filename, directory name, or volume label
syntax is incorrect
        at java.io.WinNTFileSystem.canonicalize0(Native Method)
        at java.io.Win32FileSystem.canonicalize(Win32FileSystem.java:396)
        at java.io.File.getCanonicalPath(File.java:559)
        at org.apache.catalina.startup.ClassLoaderFactory.createClassLoader(ClassLoaderFactory.java:199)
        at org.apache.catalina.startup.Bootstrap.createClassLoader(Bootstrap.java:179)
        at org.apache.catalina.startup.Bootstrap.initClassLoaders(Bootstrap.java:103)
        at org.apache.catalina.startup.Bootstrap.init(Bootstrap.java:212)
        at org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:409)

How can I troubleshoot this error and what may be the issue that
caused this error?

Thanks

---------------------------------------------------------------------
To start a new topic, e-mail: users@...
To unsubscribe, e-mail: users-unsubscribe@...
For additional commands, e-mail: users-help@...