Spring JAX-RS Servlet Deployment

0

In this article we will see how to deploy JAX-RS application in a servlet container.
You can declare the packages, classes or extend JAX-RS provided agnostic abstract Application which in turn defines the components of a JAX-RS application by providing the root resources, providers and feature classes.

Create a JAX-RS web application project using archetype jersey-quickstart-webapp. You can see more details here.

mvn archetype:generate -DarchetypeArtifactId=jersey-quickstart-webapp -DarchetypeGroupId=org.glassfish.jersey.archetypes -DinteractiveMode=false -DgroupId=com.javarticles.jax -DartifactId=jaxApplicationExampe -DarchetypeVersion=2.22.1

Define JAX-RS Resources

Let’s create few JAX-RS resources in different packages.

Package Structure

Package Structure

Resource1:

package com.javarticles.jax.packageA;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;

import com.javarticles.jax.packageB.Resource3;


@Path("resource1")
public class Resource1 extends Resource3 {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String getIt() {
        return "This is resource1";
    }
}

Resource2:

package com.javarticles.jax.packageA;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;

import com.javarticles.jax.packageA.subPackage.Resource4;


@Path("resource2")
public class Resource2 extends Resource4 {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String getIt() {
        return "This is resource2";
    }
}

Resource3:

package com.javarticles.jax.packageB;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;


@Path("resource3")
public class Resource3 {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String getIt() {
        return "This is resource3";
    }
}

Resource4:

package com.javarticles.jax.packageA.subPackage;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;


@Path("resource4")
public class Resource4 {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String getIt() {
        return "This is resource4";
    }
}

Resource5:

package com.javarticles.jax.packageC;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;


@Path("resource5")
public class Resource5 {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String getIt() {
        return "This is resource5";
    }
}

Resource6:

package com.javarticles.jax.packageC;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;


@Path("resource6")
public class Resource6 {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String getIt() {
        return "This is resource6";
    }
}

Configure JAX-RS Components in Deployment Descriptor

Specify Package Names in web.xml

We map REST resources to URL pattern /rest. The call is delegated to Jersey’s servlet ServletContainer which internally relies on its own implementation of Application called the ResourceConfig.
We specify one or more package names that contain application-specific resources and providers using the parameter jersey.config.server.provider.packages. Jersey’s Application will scan the packages for the root resources and provider classes. One can register JAX-RS component classes either manually or through the scanning.

Note that package scanning ignores the inheritance resources if the inherited classes are not in the same package or the nested packages. One can prevent from scanning the nested packages by setting parameter jersey.config.server.provider.scanning.recursive to false. By default it is considered as true and recursively scans any nested packages within the packages mentioned in web.xml.

web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<!-- This web.xml file is not required when using Servlet 3.0 container, 
	see implementation details http://jersey.java.net/nonav/documentation/latest/jax-rs.html -->
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
 	<servlet>
		<servlet-name>Jersey Web Application</servlet-name>
		<servlet-class>org.glassfish.jersey.servlet.ServletContainer</servlet-class>
		<init-param>
			<param-name>jersey.config.server.provider.packages</param-name>
			<param-value>com.javarticles.jax.packageA</param-value>
		</init-param>	
		<init-param>
		<load-on-startup>1</load-on-startup>
	</servlet>
	<servlet-mapping>
		<servlet-name>Jersey Web Application</servlet-name>
		<url-pattern>/rest/*</url-pattern>
	</servlet-mapping>
</web-app>

Specify Class Names in web.xml

You can also specify one or more class names implementing application-specific resources or the providers. JAX-RS resources are classes annotated with either javax.ws.rs.Path or javax.ws.rs.ext.Provider. The parameter against which you will specify the class names is jersey.config.server.provider.classnames.

web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<!-- This web.xml file is not required when using Servlet 3.0 container, 
	see implementation details http://jersey.java.net/nonav/documentation/latest/jax-rs.html -->
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
 	<servlet>
		<servlet-name>Jersey Web Application</servlet-name>
		<servlet-class>org.glassfish.jersey.servlet.ServletContainer</servlet-class>
		<init-param>
  	                <param-name>jersey.config.server.provider.classnames</param-name>
			<param-value>com.javarticles.jax.Resource1, com.javarticles.jax.Resource2</param-value>
		</init-param>
		<load-on-startup>1</load-on-startup>
	</servlet>
	<servlet-mapping>
		<servlet-name>Jersey Web Application</servlet-name>
		<url-pattern>/webapi/*</url-pattern>
	</servlet-mapping>
</web-app>

Specify Classpath in web.xml

You can specify one or more class-paths that contains application-specific resources and providers against parameter jersey.config.server.provider.classpath.

Specify Application in web.xml

Finally, you can provide the list of JAX-RS resources in an agnostic way by extending the Application class to provide the list of relevant root resource classes using getClasses() and singletons getSingletons(). Next you need to register it in your web application web.xml deployment descriptor using initialization parameter
with a name of javax.ws.rs.Application.

MyApplication:

package com.javarticles.jax;

import java.util.HashSet;
import java.util.Set;

import javax.ws.rs.ApplicationPath;
import javax.ws.rs.core.Application;

import com.javarticles.jax.packageC.Resource5;
import com.javarticles.jax.packageC.Resource6;

@ApplicationPath("/")
public class MyApplication extends Application {
    public Set<Class<?>> getClasses() {
        Set<Class<?>> classes = new HashSet<Class<?>>();
        classes.add(Resource5.class);
        classes.add(Resource6.class);
        return classes;
    }
}

web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<!-- This web.xml file is not required when using Servlet 3.0 container, 
	see implementation details http://jersey.java.net/nonav/documentation/latest/jax-rs.html -->
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
 	<servlet>
		<servlet-name>Jersey Web Application</servlet-name>
		<servlet-class>org.glassfish.jersey.servlet.ServletContainer</servlet-class>
		<init-param>
			<param-name>javax.ws.rs.Application</param-name>
			<param-value>com.javarticles.jax.MyApplication</param-value> -->
		</init-param>
		<load-on-startup>1</load-on-startup>
	</servlet>
	<servlet-mapping>
		<servlet-name>Jersey Web Application</servlet-name>
		<url-pattern>/webapi/*</url-pattern>
	</servlet-mapping>
</web-app>

In the below web.xml, we will use packages, classes and application way of finding the resources.

web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<!-- This web.xml file is not required when using Servlet 3.0 container, 
	see implementation details http://jersey.java.net/nonav/documentation/latest/jax-rs.html -->
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
 	<servlet>
		<servlet-name>Jersey Web Application</servlet-name>
		<servlet-class>org.glassfish.jersey.servlet.ServletContainer</servlet-class>
		<init-param>
			<param-name>jersey.config.server.provider.packages</param-name>
			<param-value>com.javarticles.jax.packageA</param-value>
		</init-param>	
		<init-param>
      	    <param-name>jersey.config.server.provider.classnames</param-name>
			<param-value>com.javarticles.jax.packageB.Resource3</param-value>
		</init-param>
		<init-param>
			<param-name>javax.ws.rs.Application</param-name>
			<param-value>com.javarticles.jax.MyApplication</param-value>
		</init-param>		
		<load-on-startup>1</load-on-startup>
	</servlet>
	<servlet-mapping>
		<servlet-name>Jersey Web Application</servlet-name>
		<url-pattern>/rest/*</url-pattern>
	</servlet-mapping>
</web-app>

index.html:

<html>
<body>
    <h2>JAX-RS Servlet Deployement Example</h2>
    <p><a href="rest/resource1">Resource1</a>
    <p><a href="rest/resource2">Resource2</a>
    <p><a href="rest/resource3">Resource3</a>
    <p><a href="rest/resource4">Resource4</a>
    <p><a href="rest/resource5">Resource5</a>
    <p><a href="rest/resource6">Resource6</a>
</body>
</html>

Click on on resource clinks to see the REST result or enter the URL directly in browser.
Welcome Page

If you enter http://localhost:8080/jaxApplicationExample/webapi/resource1, you should see the below output.

Output:

This is resource1

Enter http://localhost:8080/jaxApplicationExample/webapi/resource2

Download the source code

This was an example about JAX-RS Servlet Deployment.

You can download the source code here: jaxApplicationExamples.zip
Share.

Comments are closed.