14

I have an object, generated by XJC, called Product. I want to set product.currentPrice (a String) to be £210 where £ is the currency symbol (passed in from elsewhere in the system).

Trouble is, JAXB is escaping my ampersand, so it produces £210 instead. How do I make it not do this?

skaffman
  • 398,947
  • 96
  • 818
  • 769
rjsang
  • 1,757
  • 3
  • 16
  • 26
  • Possible duplicate? http://stackoverflow.com/questions/1506663/can-i-force-jaxb-not-to-convert-into-quot-for-example-when-marshalling-to-x – Abhinav Sarkar Jul 20 '10 at 11:02

6 Answers6

14

By default, the marshaller implementation of the JAXB usually escapes characters. To change this default behavior you will have to Write a class that implements the com.sun.xml.bind.marshaller.CharacterEscapeHandler interface.

set that handler in the Marshaller

CharacterEscapeHandler escapeHandler = NoEscapeHandler.theInstance;
marshaller.setProperty("com.sun.xml.bind.characterEscapeHandler", escapeHandler); 

You can have a look at samples provided with JAXB, character escaping sample

Manish Singh
  • 3,463
  • 22
  • 21
  • 1
    Okay, that's great, but if I do that I am forced to write an implementation that covers how to escape every single character. How do I delegate to the default behaviour if the character is not the one I'm interested in? – rjsang Jul 20 '10 at 11:31
  • 2
    I'm accepting this as the correct answer, because it SHOULD be the correct answer. For anyone else reading this hoping it will help you, this doesn't actually work in JAXB 2.2.1 because of a bug ( https://jaxb.dev.java.net/issues/show_bug.cgi?id=777 ) – rjsang Jul 20 '10 at 16:27
  • Since it seems the source is already escaped, shouldn't it simply be unescaped before passing to JAXB? – herman May 12 '15 at 10:48
  • 1
    Of the multiple solutions I found online, this was the one that finally fixed the escaping. Thank you! – Zeleres Jul 26 '16 at 19:32
  • 2
    How to set the above properties with xml configuration in spring? – newday Nov 09 '16 at 05:26
  • @Manish Singh, what if I just want it not to escape in the first place? Why do I have to implement a code that could compromise the rest just to disable escaping? – Artanis Zeratul Dec 02 '18 at 06:06
7

Like rjsang said, there is a bug when using "UTF-8" encoding, which is the default. If you don't care about the case sensitive issues, try using "utf-8" and get your custom escaper to work as it is supposed to do. Also UTF-16 works, anything but "UTF-8": "uTf-8" and so on.

Awful bug in the standard.

Here is the code to do so:

marshaller.setProperty(javax.xml.bind.Marshaller.JAXB_ENCODING, "utf-8");
Flexo
  • 87,323
  • 22
  • 191
  • 272
jfuentes
  • 71
  • 1
  • 1
2

Solution for XmlStreamWriter

final XMLOutputFactory streamWriterFactory = XMLOutputFactory.newFactory();
streamWriterFactory.setProperty("escapeCharacters", false);

From here

Community
  • 1
  • 1
ZiglioUK
  • 2,573
  • 4
  • 27
  • 32
  • Also had a comment on the [linked answer](https://stackoverflow.com/a/13508779/809536): `"Not documented, so you can't trust this to work in the future"`. – Mohammad Faisal Jul 06 '18 at 12:31
1

If you implement this interface: com.sun.xml.bind.marshaller.CharacterEscapeHandler, with your own character escaping, but you want to delegate some behaviour to the traditional escaping, you can use any of these clases (or write your own code based on them):

  • com.sun.xml.bind.marshaller.MinimumEscapeHandler
  • com.sun.xml.bind.marshaller.NioEscapeHandler
  • com.sun.xml.bind.marshaller.DumbEscapeHandler

They come with the JAXB RI Implementation AKA jaxb-impl-2.2.1.jar.

Hope this help to anyone, like it helped me.

Carlitos Way
  • 3,279
  • 20
  • 30
0

How about using a CDATA section to wrap the value, and then use a JAXB implementation such as EclipseLink MOXy that can handle CDATA?

To handle CDATA using MOXy see:

bdoughan
  • 147,609
  • 23
  • 300
  • 400
-2

Depending on what you are exactly looking for you can either :

  • disable character escaping
  • or use CDATA string which support can be added into JAXB with just a bit of configuration
fred
  • 9
  • 1
fred
  • 75
  • 1
  • 1