Services Web avec JavaEE

Les exemples présentés ici illustrent les deux grandes familles de services web. Les web utilisant SOAP avec JAX-WS) et ceux s’appuyant sur le modèle REST (REpresentational State Transfer avec JAX-RS.

Avec JEE un service web est une classe POJO annotée par @WebService, les méthodes qui doivent être présentées sont annotées par @WebMethod.

Dans le projet exemple, c’est directement la classe PersonneManager du module EJB qui a été annotée.

Après l’avoir déployé, vous pouvez le tester directement avec un navigateur web : http://localhost:8080/PersonneManagerService/PersonneManager?Tester

La description standard du service est accessible ici : http://localhost:8080/PersonneManagerService/PersonneManager?wsdl

Maven peut générer automatique les fichiers et classes nécessaire :

             <plugin>
                <groupId>org.jvnet.jax-ws-commons</groupId>
                <artifactId>jaxws-maven-plugin</artifactId>
                <version>${jaxws-maven-plugin.version}</version>
                <executions>
                    <execution>
                        <id>generate-wsdl</id>
                        <goals>
                            <goal>wsgen</goal>
                        </goals>
                    </execution>
                </executions>
 
                <configuration>
                    <sei>fr.univ_tln.bruno.test.jee.ejb.PersonneManager</sei>
                    <genWsdl>true</genWsdl>
                </configuration>
            </plugin>

Le client peut être écrit dans n’importe quel langage. Un exemple en Java se trouve dans le module JEE/WSClient. Cet exemple est écrit en utilisant l’injection et peut être exécuté avec la commande :

appclient -client target/WSClient-1.0-SNAPSHOT.jar

Le module RS présente un exemple très simple de service web rest. Il est composé de deux classes : PersonneManagerApplication active le service web avec la spécialisation de la classe javax.ws.rs.core.Application en évitant les déclarations XML. La seconde classe définit le service en lui même en déléguant la partie métier à l’interface locale de PersonnalManager.

PersonneManagerRS.java
@Path("personneManagerRS")
@RequestScoped
public class PersonneManagerRS {
    @Inject
    PersonneManagerLocal personneManager;
 
    @GET
    @Produces({MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML})
    public Collection<Personne> findAll() {
        return personneManager.findAll();
    }
 
    @GET
    @Path("/{index}")
    @Produces({MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML})
    public Personne getPerson(@PathParam("index") int index)
    {
        return personneManager.find(index);
    }
}
PersonneManagerApplication.java
@ApplicationPath("/")
public class PersonneManagerApplication extends Application{
}

Deux méthodes répondent au http GET. La première sans paramètre et la seconde extrait l’identificateur de la personne de l’url. Dans les deux cas, le résultat est sérialisé de façon transparent en JSON et en XML (Pour XML, la classe Personne a été modifiée en ajoutant simplement l’annotation JAXB @XMLRootElement). Le type attendu conformément aux principes rest est transmis dans la requête HTTP. Les deux commandes suivantes et leur résultats montre un exemple d’appel en ligne de commande.

  • La seconde personne en JSON

curl -H “Accept: application/json” http://localhost:8080/WS/personneManagerRS/2

{"id":2,"nom":"martin","prenom":"marie"}
  • La seconde personne en XML

curl -H “Accept: application/xml” http://localhost:8080/WS/personneManagerRS/2

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<personne><id>2</id><nom>martin</nom><prenom>marie</prenom></personne>
  • Toutes les personnes en JSON

curl -H “Accept: application/json” http://localhost:8080/WS/personneManagerRS

[{"id":1,"nom":"martin","prenom":"pierre"},
 {"id":2,"nom":"martin","prenom":"marie"},
 {"id":3,"nom":"durand","prenom":"marie"},
 {"id":4,"nom":"durand","prenom":"jacques"}]
import com.sun.jersey.api.client.Client;
import com.sun.jersey.api.client.WebResource;
import com.sun.jersey.api.client.config.ClientConfig;
import com.sun.jersey.api.client.config.DefaultClientConfig;
import fr.univ_tln.bruno.test.jpa.Personne;
import javax.ws.rs.core.MediaType;
 
public class RSClient {
    public static void main(String[] args) {
        ClientConfig config = new DefaultClientConfig();
        Client client = Client.create(config);
        WebResource service = client.resource("http://localhost:8080/");
 
        //Récupération de toutes les personnes via XML
        Personne[] personnes = new Personne[1];
        personnes = service.path("WS").path("personneManagerRS")
                .accept(MediaType.APPLICATION_XML).get(personnes.getClass());
        for (Personne p : personnes)
            System.out.println("(" + p.getId() + "," + p.getNom() + " "
                    + p.getPrenom() + ")");
 
        //Récupération d'une personne spécifique via JSON
        Personne p2 = service.path("WS").path("personneManagerRS").path("2")
                .accept(MediaType.APPLICATION_JSON).get(Personne.class);
        System.out.println(p2.getId() + " -> " + p2.getNom() + ", "
                + p2.getPrenom());
    }
}

avec les dépendances maven suivante

<dependency>
 <groupId>com.sun.jersey</groupId>
 <artifactId>jersey-client</artifactId>
 <version>1.18</version>
</dependency>
 
<dependency>
 <groupId>com.sun.jersey</groupId>
 <artifactId>jersey-json</artifactId>
 <version>1.18</version>
</dependency>

—- dataentry page —- type : Howto technologie_tags : SOAP, REST, Maven, Java, JEE theme_tags : POO,Services Web