3

I have a situation where I need to setup my namespaces dynamically for my jaxb classes. my namespace in jaxb classes have a version that needs to be dynamically changed.

 @XmlRootElement(name = "myobject",namespace="http://myhost.com/version-2")
 @XmlAccessorType(XmlAccessType.FIELD)
 @XmlType
 public class myObject{

 }

my marshalling works perfect when I use this static namespacing mechanism, but in my real situation, I need this version to be changed dynamically..

I tried this approach to solve this issue when marshalling

 XMLStreamWriter xmlStreamWriter =     
 XMLOutputFactory.newInstance().createXMLStreamWriter(stringWriter);
 String uri = "http://myhost.com/ver-"+version;

//xmlStreamWriter.setDefaultNamespace(uri);
xmlStreamWriter.writeStartDocument("1.0");

xmlStreamWriter.writeNamespace("ns1", uri);

my attempt to use setDefaultNamespace was not successful and writeNamespace throw me an error Invalid state: start tag is not opened at writeNamespace

any input on how this can be resolved is highly appreciated.

1

2 Answers 2

2

You may implement a XMLStreamWriter that delegates all calls to the original writer, but overrides the writeNamespace(...) method:

public void writeNamespace(String prefix, String uri) {
  if ("http://myhost.com/version-2".equals(uri) {
    uri = "http://myhost.com/version-" + version;
  }
  delegate.writeNamespace(prefix, uri);
}
Sign up to request clarification or add additional context in comments.

4 Comments

when I try to override this.. xmlStreamWriter.writeNamespace("ns2", myhost.com /version-2); I get this error .. Invalid state: start tag is not opened at writeNamespace(ns2, myhost.com/version-2)
Please try to override the startElement(String uri,...) and setPrefix(...) metods in the same manner. Basically, every method getting a namespaceURI parameter needs to do the namespace transformation.
since I only wanted to add the name space version only in the root element of the xml, I did this trick.. I had the xml annotated model class like this @XmlRootElement(name = "myobject",namespace="myhost.com /version-") @XmlAccessorType(XmlAccessType.FIELD) @XmlType public class myObject{ }
where version was supplied like version- and just before passing the xml to be marshalled, I added the version number to the xml string programatically. if(version == 1){ String ns = "myhost.com/version-"+version; } the issue is how to address this problem when unmarshalling?
1

Did you consider using an XSL-T transformation ? Depending on your schema, it could be relatively straight-forward to replace the namespace after marshalling.

2 Comments

how about the performance of this ..I feel that the performance of reading the dom tree again after marshalling will impact on performance. why can't I use default namespacing or something like that when creating the xml stream writer?
I guess I remember that there exist streaming XSL processors. They have limited functionality, but for such simple tasks it should be ok.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.