Skip to content

Jersey: example using POST method

Mihai Negrean edited this page Dec 3, 2018 · 1 revision

Jersey – example using POST method

As we have noticed in the first article about Jersey in this library we find the Java implementation for the JAX-RS specifications. We showcased a simple example of an API that works using the GET http method - which is also the default method used by browsers when accessing a web resource.

In this article we will exemplify a web service that can be accessed using the POST method. In order to test the new web resource it is necessary to use a rest client.

1. Rest client

A rest client is a program that can communicate with a rest web service. For Google Chrome I recommend installing a plugin from the Chrome web store, like Advanced REST Client or Postman:

Rest clients chrome

For Firefox I recommend installing an add-on like RESTClient:

Rest clients firefox

2. Implementing the web service

The complete code of the example can be found here. We will consider a web service that is capable of receiving some sort of data and also returning data. Using the POST method we will send a pet name to the web service. Using the GET method we will obtain all the names that were sent. For simplicity the names will be temporarily saved in a list (normally we should use a database or some other sort of persistence engine).

As well as in the former Jersey example, we will use the same infrastructure for the project: Grizzly as a http server and Maven for building the project. The code looks like this:

public class Main {
    public static final String BASE_URI = "http://localhost:8081/tribulit/";

    public static HttpServer startServer() {
        final ResourceConfig resourceConfig = new ResourceConfig().packages("ro.tribulit.rest");
        return GrizzlyHttpServerFactory.createHttpServer(URI.create(BASE_URI), resourceConfig);
    }

    public static void main(String[] args) throws IOException {
        final HttpServer server = startServer();
        System.out.println(String.format("Jersey app started at %s", BASE_URI));
        System.out.println("Press Enter to stop the server.");
        System.in.read();
        server.shutdownNow();
    }
}

This class remains unchanged; it contains all the Jersey configuration and starts the http server.

@Path("animals")
public class AnimalNamesRestService {
    private static List<String> animalNames = new ArrayList<>();
    
    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String getAnimalNames() {
        return ((ArrayList) animalNames).toString();
    }
    
    @POST
    @Consumes(MediaType.TEXT_PLAIN)
    public Response addAnimalName(String name) {
        animalNames.add(name);
        return Response.status(Response.Status.CREATED).build();
    }
}

In this class we have the logic behind the web service. We have 2 methods that were exposed as web resources: getAnimalNames() and addAnimalName(). As the name suggests, the method getAnimalNames() will be used in order to obtain the names of all the animals that were sent towards the rest service. The method addAnimalName() will be used in order to add, one by one, pet names in the list that we will used for 'persistence': animalNames.

Let us therefore observe a few peculiarities:

  • at class level we use the @Path("animals") annotation - this means that if we want to access the exposed methods from this class we need to form the url as: base_url + "animals"
  • at method level we use the annotations @GET and @POST: this is how we specify the http method that we want to use in order to access the resources from the web service
  • @Consumes and @Produces: those annotations serve to specify the content type that will be accepted or returned by the accessed resource. In our example, the content "consumed" by the service as well as the content "produced" by the service will be of type text/plain
  • in case of success, the method addAnimalName() returns a http response with the status CREATED - this status corresponds to the http code 201

Let's start the server and see how can we interact with the web service using a rest client. For this, we need to navigate to the jersey-post-example folder (after downloading or cloning the complete code from here). Then we will open a terminal and input the commands:

mvn clean test
mvn exec:java

3. Querying the web service using a rest client

In order to illustrate this example I chose to use Advanced REST Client from Chrome.

Chrome client initial

In the rest client we can introduce the url where we want to perform a request - in our case http://localhost:8081/tribulit - we can also select the http method that we want to use (I've selected GET) and we can edit the http headers. In this first request we received an error message from the server: 404 - NOT FOUND. This means that the url that we tried to access was not found on this server, and this was expected. The methods that we've exposed can be accessed using the urls:

So let's insert a few pet names in the list using the POST method:

Chrome client post

Using the correct url, the POST method and content type text/plain (the content type defined by the @Consumes annotation) we were able to add the name "Bobi" in the list of pet names. The response status from the server is 201: CREATED - exactly what we defined. The name that we want to insert needs to be specified in the body of the request (often also called payload). This text is mapped automatically to the type String from Java and sent as a parameter to the method addAnimalName(). We've inserted some more names, like "Blacky", "Firicel" and "Papi". Now we will call the web resource using the GET method and we should receive as a result these names:

Chrome client get

We observe that the response from server is 200: OK. We did not configure this status but it is implicitly sent in case there were no errors. In the body of the response we received exactly the list of pet names that we expected: [Bobi, Blacky, Firicel, Papi].