2011-08-30 4 views
11

Sto utilizzando JAX-WS per i servizi Web.Java: Mapping JAX-WS

Ogni volta che utilizzo un parametro come parametro, lo ottengo come unsignedShort in xsd (Focus su weatherLetter).

Ecco la dichiarazione:

@WebMethod 
public boolean setWXtatus(
     @WebParam(name = "weatherLetter") char weatherLetter, 
     @WebParam(name = "weatherDigit") int weatherDigit, 
     @WebParam(name = "cloudCover") int cloudCover, 
     @WebParam(name = "cloudBaseInHundredsOfFeet") int cloudBaseInHundredsOfFeet, 
     @WebParam(name = "pressureInHg") int pressureInHg, 
     @WebParam(name = "visibilityInKm") int visibilityInKm, 
     @WebParam(name = "windSpeed") int windSpeed, 
     @WebParam(name = "windDirection") int windDirection, 
     @WebParam(name = "lastUpdateHour") int lastUpdateHour, 
     @WebParam(name = "lastUpdateMin") int lastUpdateMin 
) 

Ecco il mapping dei tipi che ricevo:

<xs:complexType name="setWXStatus"> 
<xs:sequence> 
<xs:element name="weatherLetter" type="xs:unsignedShort" minOccurs="0"/> 
<xs:element name="weatherDigit" type="xs:int"/> 
<xs:element name="cloudCover" type="xs:int"/> 
<xs:element name="cloudBaseInHundredsOfFeet" type="xs:int"/> 
<xs:element name="pressureInHg" type="xs:int"/> 
<xs:element name="visibilityInKm" type="xs:int"/> 
<xs:element name="windSpeed" type="xs:int"/> 
<xs:element name="windDirection" type="xs:int"/> 
<xs:element name="lastUpdateHour" type="xs:int"/> 
<xs:element name="lastUpdateMin" type="xs:int"/> 
</xs:sequence> 
</xs:complexType> 

Come posso ottenere weatherLetter per generare come Char o 1 Lettera String o qualcosa del genere?

+0

Avere giocattolo provato a cambiare da char a String nella dichiarazione? – 8vius

+0

Anche se è possibile inserire un codice lato server per vedere che cosa sta inviando sarebbe buono. – 8vius

+0

Non spingere, ma se trovi una risposta che è accettata, sentiti libero di contrassegnarla come una sola :) –

risposta

10

Aggiornamento:

Un modo per farlo è l'in XSD (se si fa contratto prima) esempio aggiungi direttamente un XSD Restriction, ad es.

<xs:element name="singleChar"> 
    <xs:simpleType> 
    <xs:restriction base="xs:string"> 
     <xs:length value="1"/> 
    </xs:restriction> 
    </xs:simpleType> 
</xs:element> 

Ma penso che la domanda è in contratto ultima (ad esempio, scrivere il codice che genera il XSD, non viceversa)

Questo non è ancora supportata in JAX-WS o JAXB, per quanto so che (ma un bel richiesta di miglioramento)

Fonti:

JAX-WS e JAXB non hanno il supporto per la generazione di codice per le restrizioni da XSD (ad es xsd: r estriction) http://old.nabble.com/Does-jaxb-2.1-enforce-xs:restriction-td21348458.html

Il motivo è che l'altra direzione (la generazione di restrizioni da parte delle annotazioni), non è supportato troppo

Soluzione:

Date un'occhiata a questo: http://download.oracle.com/docs/cd/E17802_01/webservices/webservices/docs/1.5/tutorial/doc/JAXBUsing4.html

E anche a questa domanda:

JAX-WS and Joda-Time?

Non fare esattamente quello che vuoi, ma è sempre un po 'più vicino


Non credo che si può avere limitato a 1 char qualsiasi altro modo, un char è davvero un unsigned short, e la cosa più vicina che puoi limitare a un carattere "String".

Se si utilizza una stringa, è possibile utilizzare caratteri illimitati. e @WebParam non ha un'API per limitare la lunghezza

In realtà non ho visto un modo per fare restrizioni XSD a tutti utilizzando JAX-WS, ma posso sbagliarmi

1

Si dovrebbe provare a cambiare da char a stringa nella dichiarazione, se siete a ricevere solo un singolo carattere, se si sta programmando il lato client non ci dovrebbero essere molti problemi così facendo

5

utilizzare un adattatore, qualcosa di simile:

import javax.xml.bind.annotation.adapters.XmlAdapter; 


public class CharAdapter extends XmlAdapter<String, Character> { 

    @Override 
    public String marshal(Character c) throws Exception 
    { 
     return String.valueOf(c); 
    } 

    @Override 
    public Character unmarshal(String s) throws Exception 
    { 
    if(s == null) { 
     return null; 
    } 
    if(s.length() != 1) { 
     throw new IllegalArgumentException("Provided string \"" + s + 
       "\" has invalid length of " + s.length() + " should be 1"); 
    } 
     return s.charAt(0); 
    } 

} 

E poi nel vostro WXStatus (definire una singola classe come argomento in ingresso invece del passaggio ing in un sacco di singoli parametri - JAX sta già trasformando questo in un complexType modo si può anche, in più è una migliore stile di OOP), aggiungere questa annotazione (per entrambi i campi o getter):

@XmlJavaTypeAdapter(CharAdapter.class) 
char weatherLetter; 

Ciò consentirà un/marshalling sul tuo server-side e il client lo vedrà come xs: string. Un effetto collaterale è dato dal fatto che stiamo usando il primitivo wrapper per char, dovrete gestire null.

UPDATE EDIT: Io non credo che ci sia alcun modo è possibile specificare la lunghezza della stringa con questo, però, senza creare manualmente/modificare il WSDL con qualcosa di simile:

<xs:simpleType name="weatherLetter"> 
    <xs:annotation> 
    <xs:documentation>weather character info blah blah</xs:documentation> 
    </xs:annotation> 
    <xs:restriction base="xs:string"> 
    <xs:length value="1"/> 
    </xs:restriction> 
</xs:simpleType> 
+2

+1 - Sono il lead di EclipseLink JAXB (MOXy), e questo è esattamente quello che avrei proposto. –

+1

@ Blaise - Diresti che un'annotazione '@ XsdRestriction' è una richiesta di miglioramento valida allora? è perso da XSD a Bean, mi sembra una lacuna, come si può sapere se è nella roadmap di JAXB? – ruchirhhi

+1

@ruchirhhi - Una richiesta comune è di sfruttare le annotazioni di convalida del bean (JSR-303) per le restrizioni. Il modo migliore per procedere è aggiungere una richiesta di funzionalità con un'implementazione individuale (Metro: http://java.net/jira/browse/JAXB/, MOXy: https://bugs.eclipse.org/bugs/enter_bug .cgi? product = EclipseLink). –