IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Services Web Java Discussion :

[Axis2] Web service qui retourne un ArrayList de String ?


Sujet :

Services Web Java

  1. #1
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Septembre 2008
    Messages
    2
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2008
    Messages : 2
    Points : 1
    Points
    1
    Par défaut [Axis2] Web service qui retourne un ArrayList de String ?
    Bonjour,

    Après plusieurs recherches je n'ai pas trouvé de solution précises à mon problème (a priori simple).

    J'ai fait un web service Axis 2 qui renvoi un ArrayList de String car je dois gérer dynamiquement des messages d'erreur. Je pensais récupérer tout ça côté client (Java pour le moment mais peut être n'importe quoi) sous forme de String[].

    J'ai codé quelque chose du genre pour le wsdl en typant ma variable de retour (qui est un POJO complexe mais contenant uniquement des booléen ou des chaînes, plus cette liste d'erreur)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    <complexType name="ArrayOfString">
      <complexContent>
        <restriction base="soapenc:Array">
        	<attribute ref="soapenc:arrayType"
        	wsdl:arrayType="string[]"/>
        </restriction>
     </complexContent>
    </complexType>
    En générant le wsdl par le plug in il type la liste par anyType et forcément ça plante aussi a l'éxecution, d'où cette modif...

    Le client est généré avec le plug in d'Axis et lorsque j'exécute un appel simple du web service j'ai l'erreur suivante :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    org.apache.axis2.AxisFault: org.apache.axis2.databinding.ADBException: Unexpected subelement listErreursValidation
    Remarque : lorsqu'il n'y a qu'un élément dans l'ArrayList côté serveur, le client ne plante pas. C'est lorsqu'il y a plusieurs éléments que ça plante.

    Si quelqu'un a une piste... merci !

  2. #2
    Futur Membre du Club
    Inscrit en
    Décembre 2007
    Messages
    9
    Détails du profil
    Informations forums :
    Inscription : Décembre 2007
    Messages : 9
    Points : 9
    Points
    9
    Par défaut
    Essaye ça. C'est pas exactement la même chose mais ça peut être une solution d'utiliser la multiplicité.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
    <xsd:complexType name="Erreur">
          	<xsd:sequence>	
          		<xsd:element name="messages" type="xsd:string" maxOccurs="unbounded" minOccurs="0"></xsd:element>
          	</xsd:sequence>
    </xsd:complexType>

  3. #3
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Septembre 2008
    Messages
    2
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2008
    Messages : 2
    Points : 1
    Points
    1
    Par défaut
    Exact. J'ai également testé de renvoyer un String[] niveau Java sur le serveur.

    Comme ça le wsdl marche, j'arrive à récupérer le tableau côté client. Par contre si je met des String[] dans un POJO que je renvoi ça ne marche pas. Je me prends des retour violents côté client du genre :

    AxisFault : unknown.

    Vraiment très étrange comme comportement

  4. #4
    Membre actif
    Inscrit en
    Juin 2008
    Messages
    207
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 207
    Points : 215
    Points
    215
    Par défaut
    Bonjour,

    Il me semble que le databinding XMLBeans supporte mieux les types complexes qu'ADB. Peut-être qu'il pourra te faciliter la tâche...

  5. #5
    Membre habitué
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    239
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 239
    Points : 173
    Points
    173
    Par défaut
    Pour les tableaux standards de java ils passent sans problème avec un client généré avec la méthode ADB, par contre pour les types complexes essayes de générer un client via XMLBeans, néaumoins, moi personnellement j'ai jamais réussi à faire passer un type complexe de type List par exemple.

    Je pense que CXF est beaucoup de ce coté là.

    Cdt,

  6. #6
    Membre confirmé
    Inscrit en
    Octobre 2007
    Messages
    210
    Détails du profil
    Informations forums :
    Inscription : Octobre 2007
    Messages : 210
    Points : 459
    Points
    459
    Par défaut
    Les webservices xml par définition ne savent pas ce qu'est une java.util.List ou un tableau de String[] de java.

    Les problèmes évoqués ici sont des problèmes de DataBinding (transformation xml<=>java).
    ADB (apache data binding) utilisé par défaut par Axis2 génère des attributs java.util.List pour mapper les cardinalités 0..n. J'ai pas mal travaillé avec et il ne propose aucune option pour générer à la place des arrays simples [].

    De plus il y a une norme a respecter lorsque tu construits ton modèle de données XML : "document/literal". Autrement dit il ne faut surtout pas utiliser les "soapenc".

    Lorsqu'on veut faire des "tableau" en XML, il y a deux choses importante : la cardinalité, et la nullité.

    J'ai pris un cas simple de bibliotheque contenant des livres. Il a plusieurs manière de faire mais celle qui suit est celle qui s'accorde le mieu avec le générateur d'Axis2.


    Tableau "null" :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    <bibliotheque xmlns="http://www.example.org/test/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.example.org/test/ test.xsd">
      <livres xsi:nil="true"/>
    </bibliotheque>
    Tableau vide
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    <bibliotheque xmlns="http://www.example.org/test/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.example.org/test/ test.xsd">
      <livres />
    </bibliotheque>
    Cas normal
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    <bibliotheque xmlns="http://www.example.org/test/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.example.org/test/ test.xsd">
      <livres>
        <livre titre="foo" />
        <livre titre="bar" />
      </livres>
    </bibliotheque>
    Il te faut l'XSD suivant :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
     
    <?xml version="1.0" encoding="UTF-8"?>
    <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:tns="http://www.example.org/test/" targetNamespace="http://www.example.org/test/" elementFormDefault="qualified">
     
      <xsd:element name="bibliotheque">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element name="livres" type="tns:ArrayOfLivre" nillable="true" />
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>
     
      <xsd:complexType name="ArrayOfLivre">
        <xsd:sequence>
          <xsd:element name="livre" type="tns:Livre" minOccurs="0" maxOccurs="unbounded" />
        </xsd:sequence>
      </xsd:complexType>
     
      <xsd:complexType name="Livre">
        <xsd:attribute name="titre" type="xsd:string" use="required"/>
      </xsd:complexType>
     
    </xsd:schema>
    Pour finir en java celà donnerait quelque chose comme ca :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
    Bibliotheque biblio = [payload du soapMessage];
    ArrayOfLivre array = biblio.getLivres();
    List livres = array.getLivre(); // ADB en a créé une java.util.List
    Livre livre = (Livre) livres.get(0);
    String titre = livre.getTitre();
    Celà peut parraitre un peu fastidieux mais pourtant c'est comme ça qu'il faut faire pour avoir une bonne compatibilité. Le problème vient d'ADB qui devrait générer le binding autrement et faire un racourcit sans passer par l'objet ArrayOfLivre.

    Par exemple avec JiBX il est possible de générer un binding différent qui aurait permis de faire directement Livre livre = (Livre) biblio.getLivres().get(0) ...

    Si tu veux faire des tableau de String, il te suffit de reprendre mon exemple mais cette fois avec un ArrayOfString de type xsd:string

  7. #7
    Membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    98
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 98
    Points : 54
    Points
    54
    Par défaut
    bonjour,
    je débute avec axis2 et les webservices, j'utilise le tuto suivants : http://wso2.org/library/1719, j'ai essayer de modifier mon web service, j'ai mis une seul methode qui me retourne un objet MnBean qui contient une liste, cependant, coté client, je ne sais pas comment récupérer le résultat, y'a t'il des tutorrials plus détaillés? avec quoi pourrai'je commencer?
    Merci
    MnBean:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
     
    package pack;
     
    import java.util.ArrayList;
     
    import javax.xml.bind.annotation.XmlAccessType;
    import javax.xml.bind.annotation.XmlAccessorType;
    import javax.xml.bind.annotation.XmlRootElement;
     
    @XmlAccessorType(XmlAccessType.FIELD) 
    @XmlRootElement(name="MnBean")
    public class MnBean {
     
     
    	private ArrayList<String> l=new ArrayList<String>();
     
    	public MnBean() {
    		super();
    		l.add(new String("nabil"));
    		l.add(new String("karim"));
     
    	}
     
    	public ArrayList<String> getL() {
    		return l;
    	}
     
    	public void setL(ArrayList<String> l) {
    		this.l = l;
    	}
     
     
     
    }
    Mon WS
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    package pack;
     
    import java.util.ArrayList;
    import java.util.Date;
     
    public class AfficherDate {
    	public MnBean donnerDate(){
     
    		MnBean m=new MnBean();
    		return m;
    	}
     
    }
    le client généré avec eclipse est le afficherDateStub, vous pourrez le consulter sur le tuto
    Merci

  8. #8
    Membre habitué
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    239
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 239
    Points : 173
    Points
    173
    Par défaut
    soit tu utilise le "launch the web services explorer" fournit par eclipse,, comme tu peux écrire une classe main qui invoque tes web services.

  9. #9
    Membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    98
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 98
    Points : 54
    Points
    54
    Par défaut
    merci pour ta réponse mais le pbm est quand je créer une classe avec la methode main, comment faire pour récupérer mon objet et afficher la liste?

  10. #10
    Membre habitué
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    239
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 239
    Points : 173
    Points
    173
    Par défaut
    Voici un exemple qui utilise un client généré avec la méthode ADB:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    package samples.quickstart.clients;
     
    import samples.quickstart.service.adb.StockQuoteServiceStub;
     
    public class ADBClient{
        public static void main(java.lang.String args[]){
            try{
                StockQuoteServiceStub stub =
                    new StockQuoteServiceStub
                    ("http://localhost:8080/axis2/services/StockQuoteService");
     
                getPrice(stub);
                update(stub);
                getPrice(stub);
     
            } catch(Exception e){
                e.printStackTrace();
                System.err.println("\n\n\n");
            }
        }
     
        /* fire and forget */
        public static void update(StockQuoteServiceStub stub){
            try{
                StockQuoteServiceStub.Update req = new StockQuoteServiceStub.Update();
                req.setSymbol ("ABC");
                req.setPrice (42.35);
     
                stub.update(req);
                System.err.println("price updated");
            } catch(Exception e){
                e.printStackTrace();
                System.err.println("\n\n\n");
            }
        }
     
        /* two way call/receive */
        public static void getPrice(StockQuoteServiceStub stub){
            try{
                StockQuoteServiceStub.GetPrice req = new StockQuoteServiceStub.GetPrice();
     
                req.setSymbol("ABC");
     
                StockQuoteServiceStub.GetPriceResponse res =
                    stub.getPrice(req);
     
                System.err.println(res.get_return());
            } catch(Exception e){
                e.printStackTrace();
                System.err.println("\n\n\n");
            }
        }
     
    }

  11. #11
    Membre du Club
    Profil pro
    Inscrit en
    Juin 2007
    Messages
    98
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2007
    Messages : 98
    Points : 54
    Points
    54
    Par défaut
    ah, merci, pourriez vous me passer l'adresse de ton tuto? ou un autre qui manipule les objets créer de la meme manière

  12. #12
    Membre habitué
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    239
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 239
    Points : 173
    Points
    173
    Par défaut
    essayes de voire la doc fournit par l'équipe axis d'apache.

Discussions similaires

  1. Web Service: service qui retourne une page web (JSP, JSF)
    Par spyder14 dans le forum Services Web
    Réponses: 2
    Dernier message: 03/02/2015, 11h21
  2. [Prototype] Appel d'un web service qui retourne un JSON en javascript
    Par cocobelle89 dans le forum Bibliothèques & Frameworks
    Réponses: 13
    Dernier message: 30/05/2013, 18h50
  3. Réponses: 1
    Dernier message: 03/03/2011, 09h36
  4. Web Service qui génère un Fichier XML
    Par Amir83 dans le forum Services Web
    Réponses: 8
    Dernier message: 29/05/2008, 13h32

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo