Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

JAX-RS Resource not found in GlassFish Server

I've been trying to create a simple Restful WebService, using NetBeans Ide.
My Java EE Version is: Java EE 7 Web.

I created a new Java Web Application, setting this ContexPath: /DukesAgeService.

Now, running my application, browser display my Index.html page at:

http://localhost:8080/DukesAgeService/

so, everything works fine.

Then, I tried to create a simple restful resource using the RESTful Web Service Wizard.

So, I created this class:

package firstcup.webservice;

import javax.ws.rs.core.Context;
import javax.ws.rs.core.UriInfo;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.Consumes;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.PUT;

/**
 * REST Web Service
*
* @author nolanof
*/
@Path("dukesAge")
public class DukesAgeResource {

@Context
private UriInfo context;

/**
 * Creates a new instance of DukesAgeResource
 */
public DukesAgeResource() {
}

/**
 * Retrieves representation of an instance of firstcup.webservice.DukesAgeResource
 * @return an instance of java.lang.String
 */
@GET
@Produces("text/plain")
public String getText() {        
    return "hello world";
}
}

But running my application, at url: http://localhost:8080/DukesAgeService/dukesAge I get a 404-not found page.

I exptected that any incoming get request that has the url of "/dukesAge" was handled by DukesAgeResource class getText method. Whats' wrong?

Thanks

like image 559
nolanofra Avatar asked Jan 24 '15 18:01

nolanofra


1 Answers

You're probably missing the JAX-RS application servlet. You can either define it in the web.xml or if you want to go xml-less, you can use an Application subclass. The easiest way IMO is just to use the Application subclass annotated with @ApplicationPath. A servlet will be created and the servlet path will be set to the value in the annotation. Something like

@ApplicationPath("/rest")
public class RestApplication extends Application {
    // All request scoped resources and providers
    @Override
    public Set<Class<?>> getClasses() {
        Set<Class<?>> classes = new HashSet<>();
        classes.add(DukesAgeResource.class);
        return classes;
    }

    // all singleton resources and providers
    @Override
    public Set<Object> getSingletons() {
        Set<Object> singletons = new HashSet<>();
        return singletons;
    }
}

Then the resource should be accessed via

http://localhost:8080/DukesAgeService/rest/dukesAge.

There are other ways, but this is the portable way. Glassfish uses Jersey, but creating a Java EE web application from scratch in Netbeans will only import compile time Java EE standard classes (no Jersey dependencies). So the above is really your best bet to start off with.

You can see other deployment options at the Jersey Documentation. For some of the options, you may need to add some Jersey compile-time dependencies. That's why I just mentioned the above. No other jars needed.

Another thing that would cause a 404, is if you specify the JAX-RS servlet path as /*. This will conflict with the default servlet that serves the static resources like your html pages. That's why I set it to /rest.


UPDATE

It is also stated in the JAX-RS spec that if there are empty sets returned in the getClasses() and getSingletons(), implicit classpath scanning should occur. (provider) Classes annotated withe @Provider will by default be added as singletons and resource classes annotated with @Path will be per-request objects (meaning a new object is created each request). So you could alternatively just have

@ApplicationPath("/rest")
public class RestApplication extends Application {
    // Left empty
}

and it should work just the same.

like image 189
Paul Samsotha Avatar answered Oct 21 '22 07:10

Paul Samsotha