Hi,

Someone pointed out to me today that the JAXB xjc/schemaGen transformations are lossy. Imagine a CXF JAXWS 
service written code-first, but using types generated from a schema that has an element M defined as a choice 
of two other elements A and B. That service will accept <M><A/><B/></M> and 
<M/> without error, even if it has validation enabled.

<!-- foo.xsd -->
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema";
          attributeFormDefault="unqualified"
          elementFormDefault="qualified"
          targetNamespace="http://foo.com";>
 <xs:element name="M">
   <xs:complexType>
     <xs:choice>
       <xs:element name="C" type="xs:string"/>
       <xs:element name="D" type="xs:string"/>
     </xs:choice>
   </xs:complexType>
 </xs:element>
</xs:schema>

<!-- HelloWorldImpl.java -->
package demo.hw.server;
import javax.jws.WebMethod;
import javax.jws.WebParam;
import javax.jws.WebService;
import javax.jws.soap.SOAPBinding;
import gen.M;
@WebService(targetNamespace = HelloWorldImpl.NS_URI)
@SOAPBinding(parameterStyle = SOAPBinding.ParameterStyle.BARE)
public class HelloWorldImpl {
   public static final String NS_URI = "http://foo.com";;
   @WebMethod(operationName = "M")
   public String processM(@WebParam(targetNamespace = NS_URI, name = "M") M m) {
       return "X";
   }
}

I guess this is because the runtime does not have access to the source XSD. It only has 
access to the JAXB annotations on the M class, which merely say that A and B may be 
omitted (i.e, you cannot say "either A or B but not both must be present" using 
JAXB annotations). Thus, the set of validation rules implemented by JAXB/CXF is only a 
subset of the validation rules specified in the source XSD.

But on closer inspection I discovered the 'location' attribute on the 
@XmlSchema annotation in package-info.java. This specifies the location of the 
original XSD. Unfortunately if I specify it in my package-info.java, the 
service generates WSDL that does not include any useful information about the 
schema:

<wsdl:types>
 <xsd:schema attributeFormDefault="unqualified"
             elementFormDefault="qualified"
             targetNamespace="http://foo.com";
             xmlns:tns="http://foo.com";
             xmlns:xsd="http://www.w3.org/2001/XMLSchema";>
   <xsd:element name="M" nillable="true" />
   <xsd:element name="MResponse" nillable="true" type="xsd:string" />
 </xsd:schema>
</wsdl:types>

So...is it possible to get CXF to honour the 'location' attribute on 
@XmlSchema? Ideally it should consider it when returning the service's WSDL, 
but also consider it when validating incoming messages.

- Chris

Reply via email to