I am using Java with Spring framework.
I have a multiaction controller which is having lots of service methods, and I want to to create restful URLs like as following:
http://server.com/url/events/multiActionMethod1
http://server.com/url/events/multiActionMethod2
http://server.com/url/events/multiActionMethod3
http://server.com/url/events/multiActionMethod4
http://server.com/url/events/multiActionMethod5
How can I achieve above tasks?
I think maybe something isn't coming through clearly in your question. It reads like all you're looking for is this:
#RequestMapping("/events/multiActionMethod1")
public ReturnType multiActionMethod1(SomeParameter param) {
//request handling logic
}
is there more to the question you could elaborate on?
edit: ugh no, none of that is in 2. You'd need 2.5 for annotations and 3 if you want support for using parts of the url as parameters. The easiest thing to do if you really want it to work that way in an older version is slap a URL rewriter on the front and convert it to regular query string before it hits spring.
Related
I have seen this answer
but it does not help my case.
I have a class that implements an HttpServlet. Now I want to place a URL inside it so that it has the following pattern: resource/identifier/resource.
For example, I want to make this REST call: http://example.com/owners/1234/dogs
I tried to place a URL like this in the servlet: http://example.com/owners/*/dogs, but the call never reached the servlet and was not handled.
If I understood well you want your servlet to be mapped to something like /owners/*/dogs.
Well, unfortunately Servlets can only use wildcards at the beginning or end of the mapping. So you would have to map it to /owners/* and then using request.getPathInfo() parse the rest of the url to extract the path info.
Your best options are to use the standard JAXRS or Spring MVC, both of which support path variables.
I am learning JAVA and Spring Framework. I wanted to know that is it possible in java to create Dynamic URL in spring framework using values from url and fetching from database.
I am trying to make URL Shortner in Java and I will need to lookup for url's short code in my database and as we all know, url shortner will look like "url/ShorTCode" and my script will look for "ShorTCode" keyword in database and will redirect to associated weblink.
So I wanted to know that is it even possible in JAVA and Spring? And one more thing, if I make something like this "url/yt/VIdeoCode" or "url/fb/UserProfile"
So it will look at yt object which will redirect to youtube link only and fb object which will redirect to facebook user profile.
I want to clarify that I am still learning JAVA, JSP and Spring but I want to keep this thing in my mind while I am learning so I can focus on some particular things.
Thank you all fro helping me.
If you're asking how your controller could respond with a dynamic redirect, the answer is either:
(1) Have the controller return a "redirect:" result instead of view name. It must be followed with an absolute url, and behavior might depend on your spring version and configuration, but basically it looks like this:
#RequestMapping(...)
public String myMethod(){
String url=... // database lookup, e.g. "http://myUrl"
return "redirect:"+url;
}
(2) Less elegant but sometimes useful: get direct access to the response. If your controller method has a parameter of type HttpServletResponse spring will automatically inject it. So:
#RequestMapping(...)
public String myMethod(HttpServletResponse resp){
...
response.sendRedirect(...)
}
Here we have a basic webapp using JSP which needs to provide a few JSON based REST service URLs.
These urls will all reside under /services and be generated by a MyRestServicesController.
The examples I see for settings up JSON based views all use ContentNegotiatingViewResolver. But it seems like overkill to me as this resolver seems meant for situations where the same URL might produce different output.
I just want my one RestServicesController to always produce MappingJacksonJsonView(s).
Is there a cleaner, more straight forward way to simply direct the controller to do this?
Is there a cleaner, more straight forward way to simply direct the controller to do this?
Yes there is. You can have a look at this sample I posted in Spring forums. In short the way I prefer to do it is through the following.
ApplicationContext:
<!-- json view, capable of converting any POJO to json format -->
<bean id="jsonView" class="org.springframework.web.servlet.view.json.MappingJacksonJsonView"/>
Controller
#RequestMapping("/service")
public ModelAndView getResultAsJson() {
Object jsonObj = // the java object which we want to convert to json
return new ModelAndView("jsonView", "result", jsonObj);
}
EDIT 2013: In these modern days, #skaffman's approach would be a nice alternative.
If all you need to do is output JSON, then the view layer itself is redundant. You can use the #ResponseBody annotation to instruct Spring to serialize your model directly, using Jackson. It requires less configuration than the MappingJacksonJsonView approach, and the code is less cluttered.
As long as you are using mvc:annotation-driven and Jackson is on the classpath then all you should need to do is use #ResponseBody on on your methods and the return type will be converted to JSON per Spring's standard HTTP Message Conversion functionality.
Also check out this video at around 37:00: Mastering Spring MVC.
Good day!
I am planning to do a simple CRUD application. I am planning to make my add, edit, delete and view handled by one controller. Something like this:
#WebServlet(name="ControllerServlet",
urlPatterns = {"/add","/edit","/delete","/view"}
then just use this code in my controller:
String userPath = request.getServletPath();
if (userPath.equals("/add")) {
}
But I am not sure if this is a common practice. Anyway, I am wondering what is the best practice for this? What are the pros and cons of doing this instead of separating each controller?
Thank you in advance.
Frankly, the common practice is to adopt a MVC framework. Java EE 6 offers JSF 2.0 out the box as a component based MVC framework. CRUD is possible with a single bean and a single view. You can find a basic example in this answer. The sole controller is provided by JSF itself, the FacesServlet. Other MVC frameworks follows less or more the same ideology.
If you don't want to adopt a MVC framework because you would like to learn JSP/Servlets first and/or your project won't go beyond a CRUD form, then it is hard to point out the "right" approach. At least, the use of multiple URL patterns and if/else statements is a poor sign. You have basically 2 options.
Just use 4 separate servlets. With Servlet 3.0 you don't need to fiddle with web.xml anymore and it's really easy to add another servlet class. Each servlet class functions as an "action" class and each one has a clear responsibility.
Use a single servlet, but don't use multiple URL patterns and don't use if/else blocks to determine the actions. Map it on a single URL pattern such as /action/* or *.do so that you can invoke it by URLs like action/create, action/read, etc or by create.do, read.do, etc. Then create an interface like follows
public interface Action {
void execute(HttpServletRequest request, HttpServletResponse response);
}
Implement all actions based on this interface, CreateAction, ReadAction, etc and have in your servlet a Map<String, Action> which you fill as follows during init() method:
actions.put("create", new CreateAction());
actions.put("read", new ReadAction());
// ...
And invoke it as follows (assuming an URL pattern of /action/* is been used)
actions.get(request.getPathInfo().substring(1)).execute(request, response);
That's also how the average MVC framework works deep under the covers.
See also:
Design patterns web based applications
Have you considered doing this as a RESTful service using a JAX-RS framework (like Jersey)? Then you leverage URIs and the HTTP operations: PUT, GET, POST, DELETE for CRUD:
http://bdoughan.blogspot.com/2010/08/creating-restful-web-service-part-45.html
For example:
GET http://www.example.com/customer/1
reads customer with id=1
DELETE http://www.example.com/customer/1
deletes customer with id=1
I am using the ServletTester class provided by Jetty to test one of my servlets.
The servlet reads the the body of the request using InputStream.read() to construct a byte[] which is the decoded and acted on by the servlet.
The ServletTest class provides a method getResponses(ByteArrayBuffer) but I'm unsure how to create one of these in the correct format since it would also need to contain things like headers (e.g. "Content-Type: application/octet-stream).
Can anyone show me an easy way to construct this, preferably using an existing library so that I can use it in a similar way to the HttpTester class.
If there is a "better" way to test servlets (ideally using a local connector rather than via the tcp stack) I'd like to hear that also.
Many thanks,
Why use a mock at all? Why not test the servlet by running it in jetty?
Servlet servlet = new MyServlet();
String mapping = "/foo";
Server server = new Server(0);
Context servletContext = new Context(server, contextPath, Context.SESSIONS);
servletContext.addServlet(new ServletHolder(servlet), mapping);
server.start();
URL url = new URL("http", "localhost", server.getConnectors()[0].getLocalPort(), "/foo?bar");
//get the url...assert what you want
//finally server.stop();
Edit: Just wanting to reassure people that this is very fast. Its also a very reliable indicator of what your code will actually do, because it is in fact doing it.
Spring MVC provides a small set of "mock" classes for the various javax.servlet interfaces, such as HttpServletRequest, HttpSession, and so on. This makes it easy to unit test the likes of a servlet, you just inject mocks into the e.g. doGet() method.
Even if you don't use Spring itself on the server, you can still use the mock from the library, just for your tests.
You can use HttpClient to simplify testing somewhat. Take a look at the following article:
http://roberthanson.blogspot.com/2007/12/testing-servlets-with-junit.html
That in combination with servlet tester should give you what you want unit test wise.