Implementing the JAX-RS service of the adapter

To implement the JAX-RS service of the adapter, you must first implement the JAX-RS application class, then implement the JAX-RS resources classes.

Implementing the JAX-RS application class

About this task

The JAX-RS application class tells the JAX-RS framework which resources are included in the application. Any resource can have a separate set of URLs. Traditionally the application class should extend javax.ws.rs.core.Application and implement the method getClasses or getSingletons that will be called by the JAX-RS framework to get information about this application.

In the following example, a JAX-RS application defines three resources: Resource1, UsersResource, and MyResourceSingleton. The first two are provided by the getClasses method, while the last is provided by getSingletons.

import java.util.HashSet;
import java.util.Set;
import javax.ws.rs.core.Application;
  
public class MyApplication extends Application{
      
    @Override
    public Set<Class<?>> getClasses() {
        HashSet<Class<?>> classes = new HashSet<Class<?>>();
        classes.add(Resource1.class);
        classes.add(UsersResource.class);
        return classes;
    }
      
    @Override
    public Set<Object> getSingletons() {
        Set<Object> singletons = new HashSet<Object>();
        singletons.add(MyResourceSingleton.getInstance());
        return singletons;
    }
}
Note: The example demonstrates how to write a pure JAX-RS application using getClasses and getSingletons. A quicker alternative is to use extends MFPJAXRSApplication. The MFPJAXRSApplication class scans the package for JAX-RS 2.0 resources and automatically creates a list. Additionally, its init method is called by MobileFirst Server as soon as the adapter is deployed, before it starts serving, and when the MobileFirst runtime starts up.

Implementing a JAX-RS resource

About this task

A JAX-RS resource is a POJO (plain old Java object) which is mapped to a root URL and has Java methods for serving requests to this root URL and its sub-URLs. For example:
import java.util.ArrayList;
import javax.ws.rs.Consumes;
import javax.ws.rs.DELETE;
import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.PUT;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.Status;
 
@Path("/users")
//This is the root URL of the resource ("/users")
public class UsersResource {
    //Instead of this static field, it could be a users DAO that works with Database or cloud storage
    static ArrayList<User> users = new ArrayList<User>();
     
    @GET
    @Produces(MediaType.APPLICATION_JSON)
    //This will serve: GET /users
    public ArrayList<User> getUsers(){
        return users;
    }
     
    @Path("/{userId}")
    @Produces(MediaType.APPLICATION_JSON)
    //This will serve: GET /users/{userId}
    public User getUser(@PathParam("userId") String userId){
        return findUserById(userId);
    }
 
    @POST
    @Consumes(MediaType.APPLICATION_JSON)
    //This will serve: POST /users
    public void addUser(User u) {
        users.add(u);
    }
 
    @PUT
    @Consumes(MediaType.APPLICATION_JSON)
    //This will serve: PUT /users
    public Response updateUser(User u) {
        User user = findUserById(u.getId());
        if (user == null){
            return Response.status(Status.NOT_FOUND)
                           .entity("User with ID: "+u.getId()+" not found")
                           .build();
        }
        users.remove(user);
        users.add(u);
        return Response.ok().build();
    }
 
    @DELETE
    @Path("/{userId}")
    //This will serve: DELETE /users/{userId}
    public void deleteUser(@PathParam("userId") String userId){
        User user = findUserById(userId);
        users.remove(user);
    }
     
    private User findUserById(String userId) {
        //TODO implement...
        return null;
    }
}
The resource just shown is mapped to the URL /users and serves the following requests:
Table 1. Resource requests
Request Description
GET /users Gets all users list
POST /user Adds a new user
GET /users/{userId} Gets a specific user with id userId
PUT /users Updates an existing user
DELETE /users/{userId} Deletes a user with id userId

The JAX-RS framework does the mapping from the simple Java object User to a JSON object and conversely, thereby making it easier for the service developer to use without taking care of repeating conversion-related code. The implementation also helps in extracting parameter values from the URL and from the query string without having to parse it manually.

Configuring protection of JAX-RS resources

About this task

A JAX-RS adapter resource is protected by default by the MobileFirst security framework, meaning that access to the resource requires a valid access token. See OAuth resource protection. You can configure the resource protection by using the @OAuthSecurity annotation to assign a custom security scope, or to disable resource protection. For a complete reference, see Interface OAuthSecurity. For detailed configuration instructions, see Configure protection of Java API for RESTful Web Services (JAX-RS) resources.