Hi,
It was my understanding that a method with a return type (i.e. not void) should return a 404 status when the return object is null. Not sure why I had that idea in my head.
I created another method on the resource:
@GET
@Path("/exception")
public String pingException()
{
throw new WebApplicationException(Response.Status.INTERNAL_SERVER_ERROR);
}
and when the client calls that I catch a UniformInterfaceException with the expected 500 status.
public String pingException()
{
try
{
return provisioningService.path("/exception").get(String.class);
}
catch (UniformInterfaceException ex)
{
return "Return code: " + ex.getResponse().getStatus();
}
catch (Throwable ex)
{
return "pingException caught unexpected throwable " + ex.getMessage();
}
}
Why the "real" method (querySubscriberAccount) throws a UniformInterfaceException with a 204 status is completey baffling!!!
----- Original Message -----
From: Petr Jurák <petr.jurak_at_gmail.com>
Date: Wednesday, February 1, 2012 2:30 pm
Subject: [Jersey] Re: 204 status returned instead of 500 when throwing WebApplicationException
To: users_at_jersey.java.net
> Hi,
>
> If you return null, then client have to expect 204 no content, because
> entity body is empty. It's from JAX-RS specification, chapter 3.3.3
> Return Type.
>
> But with that exception it is strange. Can you add a simple
> method (no
> params etc) a just throw an WebApplicationException whenever it is
> called?
>
> Br, Petr
>
>
> On 1 February 2012 22:10, sdoca sdoca <sdoca_at_shaw.ca> wrote:
> > Hi,
> >
> > I have written a couple other Jersey services and haven't had
> this issue
> > with them. It's a bit of a mystery.
> >
> > I updated my resource class based on the workaround in the
> issue I linke to
> > in my OP. It now looks like this:
> >
> > @GET
> > @Produces(MediaType.APPLICATION_XML)
> > @Path("/subscriber")
> > public SubscriberAccount querySubscriberAccount(
> > @QueryParam("telephone") String telephone,
> > @QueryParam("cmsFQDN") String cmsFQDN)
> > {
> > logger.debug("Entering querySubscriberAccount()
> {telephone}=["> + telephone + "] {cmsFQDN}=[" +
> cmsFQDN + "]");
> >
> > assert (null != provisionService);
> >
> > final SubscriberAccount account;
> >
> > try
> > {
> > account =
> provisionService.querySubscriber(telephone, cmsFQDN);
> >
> > if (account != null)
> > {
> > logger.debug("The {provisionService} reports
> [" + account +
> > "]");
> > }
> > else
> > {
> > logger.debug("No account was found");
> > }
> > }
> > catch (IllegalArgumentException ex)
> > {
> > logger.error("Illegal argument while executing
> query for
> > subscriber account: ",
> > ex);
> >
> > throw new
> WebApplicationException(Response.Status.BAD_REQUEST);> }
> > catch (Exception ex)
> > {
> > logger.error("Unexpected exception while executing
> query for
> > subscriber account",
> > ex);
> >
> > throw new
> > WebApplicationException(Response.serverError().build());
> >
> > // throw new
> > //
> > WebApplicationException(Response.Status.INTERNAL_SERVER_ERROR);
> > }
> >
> > logger.debug("Exiting querySubscriberAccount()");
> >
> > return account;
> > }
> >
> > The resource makes calls to another service which was throwing
> an exception
> > which was caught and the 500 error status returned.
> Unfortunately, that
> > service has now been fixed and no longer throwing the
> exception. So, now in
> > my service logs I'm seeing the log statement:
> >
> > 2012 Feb 01 13:30:52,818 MST [http-thread-pool-80(2)] DEBUG
> > ProvisionResource - No account was found
> >
> > BUT, the client is still receiving a 204 status. The client
> call to the
> > resource looks like this:
> >
> > public SubscriberAccount querySubscriberAccount(final
> String accountNum)
> > throws ProvisioningException
> > {
> > SubscriberAccount subscriberAccount = null;
> > WebResource querySubscriberResource = null;
> >
> > try
> > {
> > querySubscriberResource =
> > provisioningService.path(PATH_SUBSCRIBER)
> > .queryParam(PARAM_KEY_ACCOUNT, accountNum);
> >
> > subscriberAccount =
> > querySubscriberResource.accept(MediaType.APPLICATION_XML)
> > .get(SubscriberAccount.class);
> >
> > logger.info("SubscriberAccount retrieved for
> account number: " +
> > accountNum + " - " + subscriberAccount);
> > }
> > catch (UniformInterfaceException ex)
> > {
> > final int status = ex.getResponse().getStatus();
> >
> > if (404 == status)
> > {
> > logger.info("No subscriber account provisioned
> for account
> > number: "
> > + accountNum + "at web resource: " +
> > querySubscriberResource);
> > }
> > else
> > {
> > final String message = "Unexpected webservice
> response with
> > status code: "
> > + ex.getResponse().getStatus();
> >
> > logger.error(message, ex);
> >
> > throw new ProvisioningException(message);
> > }
> > }
> > catch (Throwable ex)
> > {
> > logger.error("querySubscriberAccount caught unexpected
> > throwable",
> > ex);
> >
> > throw new ProvisioningException(ex.getMessage());
> > }
> > finally
> > {
> > logger.debug("Exiting querySubscriberAccount - returning
> > {subscriberAccount}=["
> > + subscriberAccount + "]");
> > }
> >
> > return subscriberAccount;
> > }
> >
> > Since the resource is returning null, I would expect the
> status returned to
> > be 404. However, it is still a 204 as shown in the client logs:
> >
> > 2012 Feb 01 13:30:54,820 MST [Ejb-Async-Thread-4] ERROR
> ProvisioningClient -
> > Unexpected webservice response with status code: 204
> > com.sun.jersey.api.client.UniformInterfaceException: GET
> > http://app30/provisioning-
> service/provision/subscriber?accountNum=037005590> returned a
> response status of 204 No Content
> > at
> >
> com.sun.jersey.api.client.ClientResponse.getEntity(ClientResponse.java:528)> at
> >
> com.sun.jersey.api.client.ClientResponse.getEntity(ClientResponse.java:506)>
> > Not only was I expecting a 404 status, but I'm confused as to
> why a 204
> > response would cause a UniformInterfaceException. According
> to the API
> > doing a get on a WebResource will throw a
> UniformInterfaceException "if the
> > status of the HTTP response is greater than or equal to 300
> and c is not the
> > type ClientResponse."
> >
> > Again, if anyone can help with these issues, it would be really
> > appreciated!!
> >
> > ----- Original Message -----
> > From: Petr Jurák <petr.jurak_at_gmail.com>
> > Date: Wednesday, February 1, 2012 1:04 pm
> > Subject: [Jersey] Re: 204 status returned instead of 500 when
> throwing> WebApplicationException
> > To: users_at_jersey.java.net
> >
> >> Hi,
> >>
> >> I have similar resource and Jersey 1.9.1 and exception
> handling is
> >> behaving well (I mean that the client gets 500 as expected).
> >> Could you
> >> please double check your stack trace?
> >> And what jee server are you using?
> >>
> >> Br, Petr
> >>
> >> On 1 February 2012 19:04, <sdoca_at_shaw.ca> wrote:
> >> > I have a Jersey web service with the following a resource class:
> >> >
> >> > @Stateless
> >> > @Path("/provision")
> >> > public class ProvisionResource
> >> > {
> >> > private final Logger logger =
> >> > LoggerFactory.getLogger(ProvisionResource.class);
> >> >
> >> > @EJB
> >> > private ProvisionService provisionService;
> >> >
> >> > @GET
> >> > @Produces(MediaType.APPLICATION_XML)
> >> > @Path("/subscriber")
> >> > public SubscriberAccount querySubscriberAccount(
> >> > @QueryParam("accountNum") String accountNum)
> >> > {
> >> > logger.debug("Entering querySubscriberAccount()");
> >> >
> >> > final SubscriberAccount account;
> >> >
> >> > try
> >> > {
> >> > account =
> >> provisionService.querySubscriber(accountNum);>
> >> > if (account != null)
> >> > {
> >> > logger.debug("Retreived account = " +
> account);>> > }
> >> > else
> >> > {
> >> > logger.debug("No account was found for " +
> >> > accountNum);
> >> > }
> >> > }
> >> > catch (IllegalArgumentException ex)
> >> > {
> >> > logger.error("Illegal argument while
> executing query
> >> > for subscriber account",
> >> > ex);
> >> >
> >> > throw new
> >> > WebApplicationException(Response.Status.BAD_REQUEST);
> >> > }
> >> > catch (Exception ex)
> >> > {
> >> > logger.error("Unexpected exception while executing
> >> > query for subscriber account",
> >> > ex);
> >> >
> >> > throw new
> >> > WebApplicationException(Response.Status.INTERNAL_SERVER_ERROR);
> >> > }
> >> >
> >> > logger.debug("Exiting querySubscriberAccount()");
> >> >
> >> > return account;
> >> > }
> >> >
> >> > .... snip ....
> >> >
> >> > }
> >> >
> >> > The `provisionService.querySubscriber` throws an exception
> >> which is
> >> > caught by the second catch statement in the
> `querySubscriberAccount`>> > method (we see the log statement in
> the file). However, the
> >> client is
> >> > receiving a `204` status instead of the expected `500` error.
> >> >
> >> > I did find this issue which is similar to mine:
> >> > http://java.net/jira/browse/JERSEY-41 but is quite old and for
> >> Jersey> 1.3.1. We are using version 1.9.1.
> >> >
> >> > Has anyone else seen this issue and hopefully figured out
> what the
> >> > problem is?
> >>
>