JAX-RS CXF Exception wrapping - java

I would like to add an ExceptionMapper to CXF (2.6.1) which not only communicates the Response code, but also ships the exception in the payload format (I'm using JSON for now).
#Provider
public class CustomExceptionMapper
implements
ExceptionMapper<MyException>
{
...
#Override
public Response toResponse(MyException mex)
{
//I need something here which can convert mex object to JSON and ship it in response
// I want this to be de-serialized on client
//the following returns the status code
return Response.status(Response.Status.BAD_REQUEST).build();
}
...
}
Is there a way to do this ?

You may need to use #Produces to serialize your object to JSON like:
#Produces(MediaType.APPLICATION_JSON)
And then return Response.ok().entity(OBJECT).build();
The way that you can test your service:
ClientConfig config = new DefaultClientConfig();
Client client = Client.create(config);
WebResource service = client.resource(getBaseURI());
ClientResponse response = service.path(ADDRESS).type("application/json").get(ClientResponse.class);
String s = response.getEntity(String.class);
System.out.println(s);
private static URI getBaseURI() {
return UriBuilder.fromUri(SERVER ADDRESS).build();
}

Related

set ClientRequestContext property dynamically in ClientRequestFilter

hey everyone i just want to know how can we set a property on ClientRequestContext object to a dynamic value when using ClientRequestFilter in jax-rs web service. just like this
Suppose i have an object
MyObject obj=new MyObject();
obj.nmae="simon";
obj.vendor=209;
Now i want to call a web service for which i create a jersey client and for that client i created the filter.Now what i want to know how to get my object passed down to clientFilter so i can set ClientRequestContext property to myObject?
#Provider
public class RequestClientFilter implements ClientRequestFilter {
#Override
public void filter(ClientRequestContext requestContext) throws IOException {
// how to set this to a variable value passed from a function in my code
requestContext.setProperty("test", "test client request filter");
//something along these lines
requestContext.setProperty("myobj",obj);
}
}
this is what is happening
MyObject obj=new MyObject();
obj.nmae="simon";
obj.vendor=209;
ClientConfig config = new ClientConfig();
config.register(EntityLoggingFilter.class);
config.register(GsonMessageBodyHandler.class);
config.register(ClFilter.class);
// config.property(ClientProperties.CONNECT_TIMEOUT, 1000);
config.property(ClientProperties.READ_TIMEOUT, 10000);
try {
Client client = ClientBuilder.newClient(config);
WebTarget webTarget = client.target("http://localhost:8081/ServicB").path("Register")
.path("Service");
System.out.println(webTarget.getUri());
Invocation.Builder invocationBuilder = webTarget.request().accept(MediaType.APPLICATION_JSON);
Response response = invocationBuilder.post(Entity.json("anything"));
System.out.println(response.getStatus());
String bresponse = response.readEntity(String.class);
if (bresponse == null) {
System.out.println("null response");
}
System.out.println(bresponse);
} catch (Exception ex) {
System.out.println(ex.getMessage());
}
You can register the filter as a class or an instance. If MyObject is just a one time object, you can simply pass the object through the constructor of the filter and then register it.
config.register(new RequestClientFilter(myObject));
If MyObject will change for each request, then you can also register the filter with the WebTarget instead. So with each different request, you can use a different object.
Response response1 = client.target(uri)
.register(new RequestClientFilter(myObjectOne))
.request()
.get();
Response response2 = client.target(uri)
.register(new RequestClientFilter(myObjectTwo))
.request()
.get();

Jersey Client returns HTTP 204 in a post method while trying to send jsonObject

Hey so I'm trying to send some json-object to a rest web service, then get the value of some specific keys, then process the data to finally return a new json-object which is going to be used in another place. Anyway, I'm getting HTTP 204 when I try to communicate with the service.
My rest service looks like this
#Path("/example")
public class PdfMaker {
#POST
#Path("/post")
#Consumes(MediaType.APPLICATION_JSON)
#Produces(MediaType.APPLICATION_JSON)
public Response PruebasMet(JSONObject json) throws IOException, JSONException{
try{
String xml = json.getString("xml");
String plantilla = json.getString("plant");
//method that uses "xml" and "plant" and returns "pdf"
JSONObject response = new JSONObject();
response.put("pdf", pdf);
return Response.status(200).entity(pdfb64.toString()).build();
}catch(Exception e){
e.getStackTrace();
return null;
}
}
and I'm trying to communicate with this
public class Jersey {
public static String baseuri = "http://localhost:8080/PdfMakerGF/rest/example/post";
public static void main(String[] args) {
try {
ClientConfig config = new DefaultClientConfig();
Client client = Client.create(config);
WebResource webResource = client.resource(baseuri);
JSONObject objTest = new JSONobject();
objTest.put("xml","Data1");
objTest.put("plan", "Data2");
ClientResponse res = webResource.header("Content-Type","application/json;charset=UTF-8")
.post(ClientResponse.class, objTest.toString());
System.out.println("output..." + "\n");
System.out.println("Answer "+res);
} catch (Exception e) {
e.printStackTrace();
}
}
But the response that I receive is this one
Answer POST http://localhost:8080/PdfMakerGF/rest/example/post
returned a response status of 204 No Content
Obviously there is something wrong but can't see what is it.
Since I'm stuck with this. Any kind of help would be appreciated.
I'm using netbeans 8.1, Glassfish 4.1 and Jersey.
Thanks
If your server runs into an exception and goes to the catch block, it returns null which corresponds to HTTP 204 (No Content). As sisyphus commented, there should be some exception in the server standard output.
So you probably need to:
Return a different response code (e.g. INTERNAL_SERVER_ERROR or
BAD_REQUEST) in the catch block
Check why the server code is throwing
the exception
Most likely you get an Exception. I guess it is because you have "plant" in one place and "plan" in another.
okey so finaly it works what i need to change was the way that the service was reciving the data, with a inner class in my case, end up working like this ..
Class Aux{
String xml;
String plant;
//generate gettes and setters :)
}
#Path("/example")
public class PdfMaker {
#POST
#Path("/post")
#Consumes(MediaType.APPLICATION_JSON)
#Produces(MediaType.APPLICATION_JSON)
public Response PruebasMet(Aux json) throws IOException,
JSONException{
try{
String xml = json.getXml();
String plant = json.getPlant();
//method that uses "xml" and "plant" and returns "pdf"
JSONObject response = new JSONObject();
response.put("pdf", pdf);
return Response.status(200).entity(pdf)).build();
}catch(Exception e){
e.getStackTrace();
return null;
}
}
and the client is ..
Client client = new Client();
WebResource wresource = client.resource("http://localhost:8080/PdfMakerGF/rest/example/post");
JSONObject json = new JSONObject();
json.put("xml", DATA);
json.put("plant", DATA);
ClientResponse response =
wresource.type("application/json").post(ClientResponse.class,
json.toString());
out = response.getEntity(String.class);
System.out.println("RES = "+response);
System.out.println("OUT = "+out);
out has the info that the service is Providing

How to send the list of entities from the jersey service endpoint?

I am sending the list of entities from the jersey server. At client side i am trying to get those list of entities. But it is giving unmarshal excepiton.
Why it is adding 's' at the end of elementname i.e "emps" instead of "emp".
#XmlRootElement
public class Emp{
...
}
Server side code:
#POST
#Path("/getallemps")
#Produces(MediaType.APPLICATION_XML)
#Consumes(MediaType.APPLICATION_XML)
public List<Emp> getAllEmployees2(#Context HttpServletRequest request, #Context HttpServletResponse response) throws IOException{
List<Emp> el = new ArrayList<Emp>();
....
return el;
}
client side code:
public void testGetAllEmployees(){
String res = null;
ClientConfig config = new DefaultClientConfig();
Client client = Client.create(config);
WebResource resource = client.resource(uri);
...
ClientResponse response = resource.type(MediaType.APPLICATION_XML).post(ClientResponse.class);
List<Emp> li = response.getEntity(new GenericType<List<Emp>>(Emp.class));
}
Exception is:
....unmarshalexception unexpected element(url="" local="emps") expected element {}emp
Instead of response.getEntity(new GenericType<List<Emp>>(Emp.class));
use response.getEntity(new GenericType<List<Emp>>(){});
Not quite sure why the former does not work, but I tested with the latter and it works fine.

send XML string to web service in Jersery

I am new to web service in jersey. I have created a web service the code is below
#Path("/remotedb")
public class RemoteDb {
#GET
#Path("/save/{xmlData}")
#Produces(MediaType.TEXT_XML)
public String saveData(#PathParam("xmlData") String xml) {
return xml;
}
}
I have this code at client side
public class WebServiceClient {
public static void callWebService() {
String xml = "<data>" +
"<table><test_id>t4</test_id><dateprix>2013-06-06 22:50:40.252</dateprix><nomtest>NOMTEST</nomtest><prixtest>12.70</prixtest><webposted>N</webposted><posteddate>2013-06-06 21:51:42.252</posteddate></table>" +
"</data>";
ClientConfig config = new DefaultClientConfig();
Client client = Client.create(config);
WebResource service = client.resource(getBaseURI());
System.out.println(service.path("restful").path("remotedb").path("save").path(xml).accept(MediaType.TEXT_XML).get(String.class));
}
private static URI getBaseURI() {
return UriBuilder.fromUri("http://localhost:8080/WebServiceModule").build();
}
}
Now when i called the web service i got the following exception
Exception in thread "main" com.sun.jersey.api.client.UniformInterfaceException: GET http://localhost:8080/WebServiceModule/restful/remotedb/save/%3Cdata%3E%3Ctable%3E%3Ctest_id%3Et4%3C/test_id%3E%3Cdateprix%3E2013-06-06%2022:50:40.252%3C/dateprix%3E%3Cnomtest%3ENOMTEST%3C/nomtest%3E%3Cprixtest%3E12.70%3C/prixtest%3E%3Cwebposted%3EN%3C/webposted%3E%3Cposteddate%3E2013-06-06%2021:51:42.252%3C/posteddate%3E%3C/table%3E%3C/data%3E returned a response status of 404 Not Found
at com.sun.jersey.api.client.WebResource.handle(WebResource.java:686)
at com.sun.jersey.api.client.WebResource.access$200(WebResource.java:74)
at com.sun.jersey.api.client.WebResource$Builder.get(WebResource.java:507)
at com.main.WebServiceClient.callWebService(WebServiceClient.java:25)
at com.main.Test.main(Test.java:7)
Passing XML data in a path segment is very unorthodox and likely to raise all kind of issues. You should pass it as a query parameter, e.g. /WebServiceModule/restful/remotedb/save?xmlData=
%3Cdata...
#GET
#Path("/save")
#Produces(MediaType.TEXT_XML)
public String saveData(#QueryParam("xmlData") String xml) {
return xml;
}
}
or even better if it is a write operation as the name suggests then it should be a POST /WebServiceModule/restful/remotedb/save with the xmlData passed in the request body.
#POST
#Path("/save")
#Produces(MediaType.TEXT_XML)
public String saveData(String xml) {
return xml;
}
}
or even better yet, if you can map your xmlData to a POJO with JAXB's #XmlRootElement annotation, then you can get jersey to parse it for you:
#POST
#Path("/save")
#Consumes(MediaType.APPLICATION_XML)
public String saveData(YourXmlDataObject obj) {
return obj.getField();
}
}

How to access JSON request body of POST/PUT Request in Apache Camel/CXF REST webservice

I am trying to pass a JSON request body to a REST Webservice which is made using CXFRS in my Apache Camel application.
I want to access the request JSON passed in my Processor.
REST URL:
http://localhost:8181/mywebservice/Hello/name/{request_param}
Though i am posting a JSON in request body, still in my processor exchange.getIn().getBody() always return the {request_param} not the Request JSON.
My REST webservice is as follows:
#Path("/name/")
#Consumes({"application/json" ,"application/xml"})
public class HelloRest {
#POST
#Path("/{name}")
public TestPojo sayHi(#PathParam("name") String name) {
return new TestPojo(name);
}
}
Server part:
#POST
#Path("/")
#Produces(MediaType.TEXT_PLAIN)
#Consumes(MediaType.APPLICATION_JSON)
public String add(MappingUser newUser){
UserEntity userEntity = new UserEntity(newUser.getNickname(), newUser.getPassword());
boolean ret = myDB.addUser(userEntity);
//sends the return value (primitive type) as plain text over network
return String.valueOf(ret);
}
Client part:
public boolean addUser(User user){
WebResource resource = client.resource(url).path("/");
String response = resource
//type of response
.accept(MediaType.TEXT_PLAIN_TYPE)
//type of request
.type(MediaType.APPLICATION_JSON_TYPE)
//method
.post(String.class, user);
return Boolean.valueOf(response);
}

Categories

Resources