API REST avec Jersey et Spring

Haut REST

Je viens d'annoncer le nouveau cours Learn Spring , axé sur les principes de base de Spring 5 et Spring Boot 2:

>> VOIR LE COURS

1. Vue d'ensemble

Jersey est un framework open source pour le développement de services Web RESTful. Il sert d'implémentation de référence de JAX-RS.

Dans cet article, nous allons explorer la création d'un service Web RESTful à l'aide de Jersey 2 . De plus, nous utiliserons l'injection de dépendances (DI) de Spring avec la configuration Java.

2. Dépendances de Maven

Commençons par ajouter des dépendances au pom.xml :

 org.glassfish.jersey.containers jersey-container-servlet 2.26   org.glassfish.jersey.media jersey-media-json-jackson 2.26 

De plus, pour l'intégration Spring, nous devons ajouter la dépendance jersey-spring4 :

 org.glassfish.jersey.ext jersey-spring4 2.26 

La dernière version de ces dépendances est disponible sur jersey-container-servlet, jersey-media-json-jackson et jersey-spring4.

3. Configuration Web

Ensuite, nous devons configurer un projet Web pour effectuer la configuration du servlet. Pour cela, nous utiliserons WebApplicationInitializer de Spring :

@Order(Ordered.HIGHEST_PRECEDENCE) public class ApplicationInitializer implements WebApplicationInitializer { @Override public void onStartup(ServletContext servletContext) throws ServletException { AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext(); servletContext.addListener(new ContextLoaderListener(context)); servletContext.setInitParameter( "contextConfigLocation", "com.baeldung.server"); } }

Ici, nous ajoutons l' annotation @Order (Ordered.HIGHEST_PRECEDENCE) pour nous assurer que notre initialiseur est exécuté avant l'initialiseur par défaut de Jersey-Spring.

4. Un service utilisant Jersey JAX-RS

4.1. Classe de représentation des ressources

Utilisons un exemple de classe de représentation de ressources:

@XmlRootElement public class Employee { private int id; private String firstName; // standard getters and setters }

Notez que les annotations JAXB telles que @XmlRootElement ne sont requises que si la prise en charge XML est nécessaire (en plus de JSON).

4.2. Mise en œuvre du service

Voyons maintenant comment nous pouvons utiliser les annotations JAX-RS pour créer des services Web RESTful:

@Path("/employees") public class EmployeeResource { @Autowired private EmployeeRepository employeeRepository; @GET @Path("/{id}") @Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML }) public Employee getEmployee(@PathParam("id") int id) { return employeeRepository.getEmployee(id); } @POST @Consumes({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML }) public Response addEmployee( Employee employee, @Context UriInfo uriInfo) { employeeRepository.addEmployee(new Employee(employee.getId(), employee.getFirstName(), employee.getLastName(), employee.getAge())); return Response.status(Response.Status.CREATED.getStatusCode()) .header( "Location", String.format("%s/%s",uriInfo.getAbsolutePath().toString(), employee.getId())).build(); } }

L' annotation @Path fournit le chemin d'accès URI relatif au service. Nous pouvons également incorporer des variables dans la syntaxe URI, comme le montre la variable {id} . Ensuite, les variables seront remplacées lors de l'exécution. Pour obtenir la valeur de la variable, nous pouvons utiliser l' annotation @PathParam .

@GET , @PUT , @POST, @DELETE et @HEAD définissent la méthode HTTP de la requête , qui sera traitée par des méthodes annotées.

L' annotation @Produces définit le type de réponse du point de terminaison (type de média MIME). Dans notre exemple, nous l'avons configuré pour renvoyer JSON ou XML en fonction de la valeur de l'en-tête HTTP Accept ( application / json ou application / xml ).

D'autre part, l' annotation @Consumes définit les types de média MIME que le service peut consommer. Dans notre exemple, le service peut consommer JSON ou XML en fonction de l'en-tête HTTP Content-Type ( application / json ou application / xml ).

L' annotation @Context est utilisée pour injecter des informations dans un champ de classe, une propriété de bean ou un paramètre de méthode. Dans notre exemple, nous l'utilisons pour injecter UriInfo . Nous pouvons également l'utiliser pour injecter ServletConfig , ServletContext , HttpServletRequest et HttpServletResponse.

5. Utilisation d' ExceptionMapper

ExceptionMapper nous permet d'intercepter les exceptions et de renvoyer le code de réponse HTTP approprié au client. Dans l'exemple suivant, le code de réponse HTTP 404 est renvoyé si l' exception EmployeeNotFound est levée:

@Provider public class NotFoundExceptionHandler implements ExceptionMapper { public Response toResponse(EmployeeNotFound ex) { return Response.status(Response.Status.NOT_FOUND).build(); } }

6. Gestion des classes de ressources

Enfin, connectons toutes les classes d'implémentation de service et les mappeurs d'exceptions à un chemin d'application:

@ApplicationPath("/resources") public class RestConfig extends Application { public Set
    
      getClasses() { return new HashSet
     
      ( Arrays.asList( EmployeeResource.class, NotFoundExceptionHandler.class, AlreadyExistsExceptionHandler.class)); } }
     
    

7. Test API

Testons maintenant les API avec des tests en direct:

public class JerseyApiLiveTest { private static final String SERVICE_URL = "//localhost:8082/spring-jersey/resources/employees"; @Test public void givenGetAllEmployees_whenCorrectRequest_thenResponseCodeSuccess() throws ClientProtocolException, IOException { HttpUriRequest request = new HttpGet(SERVICE_URL); HttpResponse httpResponse = HttpClientBuilder .create() .build() .execute(request); assertEquals(httpResponse .getStatusLine() .getStatusCode(), HttpStatus.SC_OK); } }

8. Conclusion

Dans cet article, nous avons présenté le framework Jersey et développé une API simple. Nous avons utilisé Spring pour les fonctionnalités d'injection de dépendances. Nous avons également vu l'utilisation d' ExceptionMapper .

Comme toujours, le code source complet est disponible dans ce projet Github.

REST bas

Je viens d'annoncer le nouveau cours Learn Spring , axé sur les principes de base de Spring 5 et Spring Boot 2:

>> VOIR LE COURS