0

I have a XSD file, from which I want to generate C# and Java classes as well.

I first set the namespace in the XSD according to my C# namespace where my classes resides. The generation (with the Microsoft tools) works fine and also the serialisation works great and I can validat them against the XSD - perfect.

Now I want to create java classes with JAXB. The problem is that the classes which are going to be created have a different package structure then the one in C#. So when I set the XSD namespace to the package structure of java, it works fine. I can serialize and validate the XML.

Now my question(s): Is there a way to solve this? (Have one XSD for both generation tools) Do I lack a understanding of what the namespace actually is needed for?

Thank you

Edit: Since it seems to be that there is a missunderstanding, I added an example

XSD: targetNamespace = "http://foo.bar/mySubNs/model"

  • C# Modelnamespace: com.foo.mySubNs.model (which fits the XSD namespace) all generated classes will have the same namespace provided though the MS codegen
  • Java Modelnamespace : com.foo.myOtherSubNs.model (which differs from the XSD namespace) the generated classes will have the "C# namespace". As a result the classes will not compile.

If I would change the namespace during the code generation for java, I can compile the classes. So far so good. But I won't be able to validate the generated XML by that java classes against the XSD, since the namespace differs.

To marshall my objects in Java, I use JAXB like this:

  ValidationEventCollector validationCollector = new ValidationEventCollector();
  SchemaFactory schemaFactory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI);
  Schema schema = schemaFactory.newSchema(new File ("my/schema/location"));

  // JAXB_CONTEXT is just an instance of "JAXBContext"
  Marshaller marshaller = JAXB_CONTEXT.createMarshaller();    

  marshaller.setSchema(schema);

  marshaller.setEventHandler(validationCollector);

  marshaller.setProperty(Marshaller.JAXB_ENCODING, "UTF-8");
  marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);

  JAXBElement<MyClass> root = new JAXBElement<MyClass> (  new QName(MyClass.class.getPackage().getName(),"MyClass"),MyClass.class, node);

  marshaller.marshal(root, new File("output/Path/obj.xml"));

To build my java classes from the schema I use a xjc-task in an ant build script:

<xjc destdir="${dir.src.gen}" removeOldOutput="no" extension="true">
    <schema dir="${dir.schema}" includes="${file.schema}"/>
    <binding dir="${dir.schema}" includes="*.xjb"/>
    <produces dir="${dir.src.gen}" includes="**/*.java"/>
</xjc>
DerApe
  • 3,097
  • 2
  • 35
  • 55

2 Answers2

1

The XSD namespace doesn't have to match the package structure, at least not in Java. When generating the classes using JAXB just provide the package you want to put the classes into.

Thomas
  • 87,414
  • 12
  • 119
  • 157
  • Okay, but that works only one way right? So I will be able to generate the java classes in a different package structure than the namespaces stating. But the generated XML from that classes won't be validateable against the schema due to the namespace right? – DerApe Jul 16 '12 at 11:43
  • @derape No, if you use the same XSD when generating the XML from the classes it should be validatable. XSD namespaces and Java packages should be completely independent and any match would just be a coincidence. – Thomas Jul 16 '12 at 12:08
  • Okay, then it seems that I miss a understanding of the XSD namespace in general. So the XML file namepspace can be completely different from the XSD namespace in order to be valid? – DerApe Jul 16 '12 at 12:18
  • @derape The namespaces in the XSD as well as the XML need to match in order to match the types defined in the XSD to the namespace prefixes used in the XML. If you don't use them, then AFAIK the namespace might differ. However, what I talked about is not the relation between XSD and XML namespaces but the relation between XSD namespaces and Java packages, which doesn't matter. So the Java package can be `foo.bar` while the XSD/XML namespace is `http://baz.com` or whatever. They don't have to match. – Thomas Jul 16 '12 at 12:58
  • Alright, then my problem can't be solved by telling JAXB to create the classes in a different package, correct? Because as I said serializing that java classes wont validate against the schema. Or is there a way to change the namespace back to the XSD namespace during serialisation (dont know if thats a good approach)? – DerApe Jul 16 '12 at 13:10
  • @Derape please share some more details, i.e. the relevant XSD part as well as the code where you marshal the objects to the XML. – Thomas Jul 16 '12 at 13:15
  • I think the models in the XSD are not important. My schmema definition looks like this: `` Not entirely sure if I need both namespace declarations. For marshaling the object I just use JAXB – DerApe Jul 16 '12 at 14:44
  • @derape No, it still matters how you use JAXB to create the classes or marshal the objects. When creating the classes, provide the package name to JAXB. There are multiple methods to do this, one being a `` inside the XSD, another being to pass the package to XJC. – Thomas Jul 16 '12 at 15:21
  • I updated my post once again. The namespace could be changed by using the binding file as you said, so on Java side im okay. The problem now is when marashalling the classes, because the java namespace is set in the xml, which obviously isn't consistent with the one in the xsd... – DerApe Jul 17 '12 at 07:16
  • +1 - @derape, Thomas is correct that the namespace does not need to match the package structure. When a JAXB impl generates a model from an XML schema by default it uses that to default a package name. The namespaces that JAXB marshals to XML however will match the XML schema used to generate the model. The following may help: http://blog.bdoughan.com/2010/08/jaxb-namespaces.html – bdoughan Jul 17 '12 at 18:28
  • I know this took a while, but I realized that by now too. Thanks for the help everyone – DerApe Jul 18 '12 at 05:59
0

You must take your pick as to what model is the main one: XSD, C#, or Java code. Once you make that choice, you must let the other two vary as they may. The best choice would be to make your XSD the reference model, generate the code in both languages with their respective tools, and just accept the results.

You can also try to pick the XML namespace such that the code at both ends will be satisfactory, but don't try to force anything to the last letter. That's not how it's meant to work.

Marko Topolnik
  • 195,646
  • 29
  • 319
  • 436
  • I can't really follow your suggenstion. Are you saying I would have to pick one namespace structure wich fits either the namespace in java/c# and adapt the generation of the other one? But once again the validation against the schema will not work since the namespace will be different in one or the other case – DerApe Jul 16 '12 at 11:46
  • Are you saying that you use a tool to generate program code from an XSD, and the result is that the code fails to create a document with the XSD's `targetNamespace`? – Marko Topolnik Jul 16 '12 at 11:48
  • no, not really. As in my question stated the code generated with a "suitable" namespace to either C# or Java will create the classes correctly. The serialized data from that classes also corresponds to the XSD and can be validated. It's about the other code which fits not to the namespace of the XSD... – DerApe Jul 16 '12 at 11:54
  • We still have a misunderstanding. The way I read it, you have just stated that the code does not fit to the namespace of the XSD, and that's what I have stated as well. – Marko Topolnik Jul 16 '12 at 11:58
  • I added an example in the question, hope this clarifys my question :) – DerApe Jul 16 '12 at 12:16
  • As to your edit: 1. You didn't demonstrate the reason WHY that Java code wouldn't compile. 2. (a side note) Java uses the term "package", not "namespace" and the package where the classe reside is irrelevant to the generated XML. Most tools allow you to choose it at will. – Marko Topolnik Jul 16 '12 at 12:18
  • let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/13931/discussion-between-derape-and-marko-topolnik) – DerApe Jul 16 '12 at 12:19