Retrieving data through a REST web service throws an exception

I am trying to create a web service that uses REST to pass data to a client. I am now stuck in two problems: one on the client side and one on the server side. I have tried many things and I am even more stuck than before. I hope one of you can help me.

I tried to get closer to the web service through the browser and through the application. If I directly access the server, I get the following error message:

SEVERE: A message body writer for Java class java.util.ArrayList, and Java type java.util.Collection<domain.Tweet>, and MIME media type text/plain was not found SEVERE: The registered message body writers compatible with the MIME media type are: text/plain -> com.sun.jersey.core.impl.provider.entity.StringProvider com.sun.jersey.core.impl.provider.entity.ReaderProvider */* -> com.sun.jersey.core.impl.provider.entity.FormProvider com.sun.jersey.core.impl.provider.entity.MimeMultipartProvider com.sun.jersey.core.impl.provider.entity.StringProvider com.sun.jersey.core.impl.provider.entity.ByteArrayProvider com.sun.jersey.core.impl.provider.entity.FileProvider com.sun.jersey.core.impl.provider.entity.InputStreamProvider com.sun.jersey.core.impl.provider.entity.DataSourceProvider com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$General com.sun.jersey.core.impl.provider.entity.ReaderProvider com.sun.jersey.core.impl.provider.entity.DocumentProvider com.sun.jersey.core.impl.provider.entity.StreamingOutputProvider com.sun.jersey.core.impl.provider.entity.SourceProvider$SourceWriter com.sun.jersey.server.impl.template.ViewableMessageBodyWriter com.sun.jersey.json.impl.provider.entity.JSONJAXBElementProvider$General com.sun.jersey.json.impl.provider.entity.JSONArrayProvider$General com.sun.jersey.json.impl.provider.entity.JSONObjectProvider$General com.sun.jersey.json.impl.provider.entity.JSONWithPaddingProvider com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$General com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$General com.sun.jersey.json.impl.provider.entity.JSONRootElementProvider$General com.sun.jersey.json.impl.provider.entity.JSONListElementProvider$General com.sun.jersey.json.impl.provider.entity.JacksonProviderProxy com.sun.jersey.moxy.MoxyMessageBodyWorker com.sun.jersey.moxy.MoxyListMessageBodyWorker 

If I run the client application, I get the following error message:

 Exception in thread "AWT-EventQueue-0" com.sun.jersey.api.client.UniformInterfaceException: GET http://localhost:8080/KwetterSOAP/resources/rest/user/Hans/tweets returned a response status of 500 Internal Server Error at com.sun.jersey.api.client.WebResource.handle(WebResource.java:688) at com.sun.jersey.api.client.WebResource.access$300(WebResource.java:74) at com.sun.jersey.api.client.WebResource$Builder.get(WebResource.java:508) at service.RestClient.getTweets(RestClient.java:52) at kwettermonitor.KwetterFollowing.btnZoekFollowersActionPerformed(KwetterFollowing.java:103) at kwettermonitor.KwetterFollowing.access$000(KwetterFollowing.java:20) at kwettermonitor.KwetterFollowing$1.actionPerformed(KwetterFollowing.java:54) at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2018) at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2341) at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402) at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259) at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252) at java.awt.Component.processMouseEvent(Component.java:6505) at javax.swing.JComponent.processMouseEvent(JComponent.java:3321) at java.awt.Component.processEvent(Component.java:6270) at java.awt.Container.processEvent(Container.java:2229) at java.awt.Component.dispatchEventImpl(Component.java:4861) at java.awt.Container.dispatchEventImpl(Container.java:2287) at java.awt.Component.dispatchEvent(Component.java:4687) at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4832) at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4492) at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4422) at java.awt.Container.dispatchEventImpl(Container.java:2273) at java.awt.Window.dispatchEventImpl(Window.java:2713) at java.awt.Component.dispatchEvent(Component.java:4687) at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:707) at java.awt.EventQueue.access$000(EventQueue.java:101) at java.awt.EventQueue$3.run(EventQueue.java:666) at java.awt.EventQueue$3.run(EventQueue.java:664) at java.security.AccessController.doPrivileged(Native Method) at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76) at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:87) at java.awt.EventQueue$4.run(EventQueue.java:680) at java.awt.EventQueue$4.run(EventQueue.java:678) at java.security.AccessController.doPrivileged(Native Method) at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76) at java.awt.EventQueue.dispatchEvent(EventQueue.java:677) at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:211) at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:128) at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:117) at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:113) at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:105) at java.awt.EventDispatchThread.run(EventDispatchThread.java:90) 

The web service is created as follows:

 @Path("/rest") @Stateless public class RESTService { @Inject @Named(value = "kwetterService") private KwetterService service; @GET @Path("/user/{user}") @Produces(MediaType.TEXT_PLAIN) public User getUser(@PathParam("user") String userName) { return service.findByName(userName); } @GET @Path("/user/{user}/tweets") @Produces(MediaType.TEXT_PLAIN) public Collection<Tweet> getTweets(@PathParam("user") String userName) { System.out.println("Service: " + service); User user = service.findByName(userName); System.out.println(userName); System.out.println(user); return user.getTweets(); } 

The client is as follows:

 public class RestClient { private WebResource webResource; private Client client; private static final String BASE_URI = "http://localhost:8080/KwetterSOAP/resources"; public RestClient() { DefaultClientConfig config = new DefaultClientConfig(); client = Client.create(config); webResource = client.resource(BASE_URI).path("rest"); } public User getUser(String userName) throws UniformInterfaceException { final WebResource.Builder userResource = webResource .path(String.format("/user/%s", userName)) .accept(MediaType.TEXT_PLAIN) ; return userResource.get(User.class); } public Collection<Tweet> getTweets(String userName) throws UniformInterfaceException { final WebResource.Builder tweetResource = webResource .path(String.format("/user/%s/tweets", userName)) .accept(MediaType.TEXT_PLAIN); return tweetResource.get(new GenericType<Collection<Tweet>>(){}); } 

The point that I'm embarrassing a little bit is where to put @XML ... annotations. I annotated the service as a root element:

 @Named(value = "kwetterService") @Stateless @XmlRootElement public class KwetterService { 

I did not comment on the method used:

 public User findByName(String name) { return userDAO.getUser(name); } 

UserDAO approaches data in a database. I have not added anything for REST / XML. I also made User XMLRootElement:

 @Entity @XmlRootElement @Table(name="Users") public class User implements Serializable { 

In the getTweets () method, I added an XMLElement annotation:

 @XmlElement public Collection<Tweet> getTweets() { List<Tweet> temp = new ArrayList<Tweet>(tweets); Collections.reverse(temp); return temp; } 

My own guess is that my whole annotation of methods and classes is incorrect. What errors can you see?

+3
java rest web-services netbeans glassfish-3
source share
1 answer

Remember that at its core, JAX-RS is built on top of HTTP, and HTTP does not know or care about Java objects. When you return objects from the resource method, they must be translated into data that can be used by the requesting client. This translation is done by objects called MessageBodyWriters , and the entire JAX-RS implementation must come with a pre-packaged set of them. Unfortunately, there is no need for the implementation to translate your objects to TEXT_PLAIN. From the stacktrace laid out, you can see that there is no provider capable of handling this type of media:

 com.sun.jersey.core.impl.provider.entity.FormProvider com.sun.jersey.core.impl.provider.entity.MimeMultipartProvider com.sun.jersey.core.impl.provider.entity.StringProvider com.sun.jersey.core.impl.provider.entity.ByteArrayProvider com.sun.jersey.core.impl.provider.entity.FileProvider com.sun.jersey.core.impl.provider.entity.InputStreamProvider com.sun.jersey.core.impl.provider.entity.DataSourceProvider com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$General com.sun.jersey.core.impl.provider.entity.ReaderProvider com.sun.jersey.core.impl.provider.entity.DocumentProvider com.sun.jersey.core.impl.provider.entity.StreamingOutputProvider com.sun.jersey.core.impl.provider.entity.SourceProvider$SourceWriter 

One of the translations that all JAX-RS implementations should provide is one of the Java objects in XML. That way you can safely use this as a data format. Showing only the changes, you need to merge into your existing code:

Java Bean :

 @Entity @XmlRootElement @Table(name="Users") public class User implements Serializable { @XmlWrapperElement("tweets") public Collection<Tweet> getTweets() { List<Tweet> temp = new ArrayList<Tweet>(tweets); Collections.reverse(temp); return temp; } } 

Server

 @Path("/rest") @Stateless public class RESTService { @GET @Path("/user/{user}") @Produces(MediaType.APPLICATION_XML) public User getUser(@PathParam("user") String userName); @GET @Path("/user/{user}/tweets") @Produces(MediaType.APPLICATION_XML) public Collection<Tweet> getTweets(@PathParam("user") String userName); } 

Client

 public class RestClient { public User getUser(String userName) throws UniformInterfaceException { final WebResource.Builder userResource = webResource .path(String.format("/user/%s", userName)) .accept(MediaType.APPLICATION_XML) ; return userResource.get(User.class); } public Collection<Tweet> getTweets(String userName) throws UniformInterfaceException { final WebResource.Builder tweetResource = webResource .path(String.format("/user/%s/tweets", userName)) .accept(MediaType.APPLICATION_XML); return tweetResource.get(new GenericType<Collection<Tweet>>(){}); } } 
+6
source share

All Articles