Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Configure Restlet to Return JSPs on Google App Engine?

I have a developed a Restlet application. I would like to return a JSP file on a URL request through Restlet. How can I achieve this without using a redirect?

i.e. Let's say I have the file "contact.jsp" on mydomain.com and I want people to be able to access contact.jsp at http://mydomain.com/contact

Thus, in Restlet, I would have:

router.attach("/contact", MyResource.class);

But how can I return the "contact.jsp" page? I know that a redirect would work, but I don't want users to see the ".jsp" in "http://mydomain.com/contact.jsp"... or is there another strategy that would work without even using restlet? Maybe some modification of my web.xml file?

Edit (2009-08-14):

My answer posted below doesn't work on App-Engine and Restlet. It does work however, if I don't include Restlet, or allow Restlet to have a url-pattern of "/*"

What would be ideal is to have a subclass of the Router that allows me to do this:

router.attach("/contact", "/contact.jsp");

Thanks!

Edit (2009-08-17):

I'm surprised I haven't had any responses since I posted a bounty. Will someone comment and let me know if my question/problem isn't clear?

Edit (2009-08-17):

Interesting observation. When using the method described by "Rich Seller" below, it works when deployed on Google App-Engine and not locally. Additionally, If I call http://mydomain.com/contact.jsp on Google App-Engine it bypasses Restlet and goes straight to the JSP. But, locally, Restlet takes over. That is, http://localhost:8080/contact.jsp does not go to the JSP and goes to Restlet. Do deployed app-engine applications respond differently to URLs as their local counterpart?

like image 277
JP Richardson Avatar asked Aug 14 '09 03:08

JP Richardson


3 Answers

Restlet doesn't currently support JSPs directly. They're difficult to handle outside of the servlet container.

There's a discussion on Nabble about this issue that you may find useful, at the moment it looks like you need to either return a redirect to the JSP mapped as normal in the web.xml, or hack it to process the JSP and return the stream as the representation.

The response dated "Apr 23, 2009; 03:02pm" in the thread describes how you could do the hack:

if (request instanceof HttpRequest &&
    ((HttpRequest) request).getHttpCall() instanceof ServletCall) {

    ServletCall httpCall = (ServletCall) ((HttpRequest) request).getHttpCall();

    // fetch the HTTP dispatcher
    RequestDispatcher dispatcher = httpCall.getRequest().getRequestDispatcher("representation.jsp");

    HttpServletRequest proxyReq = new HttpServletRequestWrapper(httpCall.getRequest());

    // Overload the http response stream to grab the JSP output into a dedicated proxy buffer
    // The BufferedServletResponseWrapper is a custom response wrapper that 'hijacks' the
    // output of the JSP engine and stores it on the side instead of forwarding it to the original
    // HTTP response.
    // This is needed to avoid having the JSP engine mess with the actual HTTP stream of the
    // current request, which must stay under the control of the restlet engine.
    BufferedServletResponseWrapper proxyResp = new BufferedServletResponseWrapper(httpCall.getResponse());

    // Add any objects to be encoded in the http request scope
    proxyReq.setAttribute("myobjects", someObjects);

    // Actual JSP encoding
    dispatcher.include(proxyReq, proxyResp);

    // Return the content of the proxy buffer
    Representation rep = new InputRepresentation(proxyResp.toInputStream(),someMediaType); 

The source for the BufferedServletResponseWrapper is posted a couple of entries later.

like image 63
Rich Seller Avatar answered Oct 29 '22 20:10

Rich Seller


"I would like to return a JSP file on a URL request through Restlet" - My understanding is JSP's are converted to servlets. Since Servlets are orthogonol to Restlets not sure how you can return JSP file through Restlet.

Assuming you are asking for a way to use JSP in addition to Restlet, This is best achieved by mapping your restlets to a rootpath such as /rest instead of /* and using the .jsp as usual.

like image 28
Gmu Avatar answered Oct 29 '22 21:10

Gmu


Looks like a simple web.xml configuration.

<servlet>
     <servlet-name>contactServlet</servlet-name>
     <jsp-file>/contact.jsp</jsp-file>
</servlet>

<servlet-mapping>
     <servlet-name>contactServlet</servlet-name>
     <url-pattern>/contact</url-pattern>
</servlet-mapping>

This works without Restlet in App-Engine. But once I include Restlet, it doesn't work if I set my Reslet url-pattern to "/*"

like image 41
JP Richardson Avatar answered Oct 29 '22 21:10

JP Richardson