2010-12-14 63 views
8

Je dois sérialiser un objet java XML dans un fichier XML à l'aide du JAXB Marshaller (version 2.2 de JAXB). Maintenant, dans l'objet xml, j'ai une étiquette qui contient Valeur de chaîne telle que:Gestion des caractères d'échappement XML (par exemple des guillemets) à l'aide de JAXB Marshaller

"<"tagA> 
**"<"YYYYY>done"<"/YYYYY>** 
"<"/tagA> 

Maintenant que vous pouvez voir que cette valeur de chaîne contient à nouveau les tags. Je veux que cela soit écrit de la même manière dans le fichier xml.

Mais JAXB Marshaller convertit ces valeurs telles que:

"&"lt;YYYYY"&"gt;"&"#xD;done ... & ainsi de suite

Je ne suis pas en mesure de traiter ces caractères d'échappement séparément en utilisant JAXB 2.2 Est-il possible de toute façon?

Toute aide à cet égard sera grand ..

Merci à l'avance, Abhinav Mishra

Répondre

7

Terminé en définissant la propriété suivante pour la JAXB Marshaller:

marshaller.setProperty("jaxb.encoding", "Unicode"); 
+0

pouvez-vous s'il vous plaît élaborer sur votre utilisation pour échapper au charatcer. Je ne suis pas capable de faire cela avec le jus mis à la propriété unicode. –

+0

Pour élaborer le même, je venais de définir la propriété suivante pour le marshaller: marshaller.setProperty ("jaxb.encoding", "Unicode"); marshaller.setProperty (Marshaller.JAXB_FORMATTED_OUTPUT, true); marshaller.setProperty (CharacterEscapeHandler.class.getName(), nouveau CustomCharacterEscapeHandler()); – javdev

+0

Ici, dans la troisième instruction, comme vous pouvez le voir, j'ai créé une classe CustomCharacterEscapeHandler qui s'occupe de la gestion des caractères d'échappement. Vous pouvez trouver son code facilement sur le net en cherchant 'comment surcharger la méthode d'échappement de CharacterEscapeHandler'. Dans le cas où vous avez besoin du code puis demandez-moi .. – javdev

2

Vous pouvez tirer parti de la structure CDATA. La norme JAXB ne couvre pas cette structure. Il y a une extension dans EclipseLink JAXB (MOXy) pour cela (je suis le chef technique). Consultez ma réponse à une question connexe:

Il décrit l'annotation @XmlCDATA dans Moxy:

import javax.xml.bind.annotation.XmlRootElement; 
import org.eclipse.persistence.oxm.annotations.XmlCDATA; 

@XmlRootElement(name="c") 
public class Customer { 

    private String bio; 

    @XmlCDATA 
    public void setBio(String bio) { 
     this.bio = bio; 
    } 

    public String getBio() { 
     return bio; 
    } 

} 

Pour plus d'informations, voir:

+0

Merci pour votre réponse Blaise. Je vais explorer celui-ci à coup sûr car il semble intéressant. Cependant, j'ai trouvé une solution pour mon problème que je poste ci-dessous .. – javdev

1

Selon ce que vous cherchez exactement, vous pouvez:

  • caractère désactiver échapper
  • ou utiliser CDATA chaîne qui support peut être ajouté dans JAXB avec juste un peu de configuration
6

Il y a un moyen plus simple.Première utilisation séquence d'échappement personnalisée:

m.setProperty(CharacterEscapeHandler.class.getName(), new CharacterEscapeHandler() { 
    @Override 
    public void escape(char[] ch, int start, int length, boolean isAttVal, Writer out) throws IOException { 
     out.write(ch, start, length); 
    } 
}); 

maréchal Puis à une chaîne comme mentionné ci-dessous

StringWriter writer = new StringWriter(); 
m.marshal(marshalObject, writer); 

puis créer un objet de documents de l'auteur mentionné ci-dessous

DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); 
DocumentBuilder builder = factory.newDocumentBuilder(); 
InputSource is = new InputSource(new StringReader(writer.toString())); 
Document doc = builder.parse(is); 

caractères d'échappement question sera résolu

+3

le problème de cette approche est que vous ne pouvez pas construire l'application avec OpenJDK. com.sun.xml.internal.bind.marshaller.CharacterEscapeHandler appartient à Sun JDK. – walv

+0

Vous pouvez utiliser com.sun.xml.bind.marshaller.CharacterEscapeHandler – user2814648

0

Avec JAXB marshaller si vous voulez un contrôle complet o voir quels personnages s'échapper (par ex. "\ '"), Vous devrez ajouter la propriété:

Marshaller marshaller = jc.createMarshaller(); 
marshaller.setProperty(CharacterEscapeHandler.class.getName(), new CustomCharacterEscapeHandler()); 

et de créer une nouvelle classe CustomCharacterEscapeHandler

import com.sun.xml.bind.marshaller.CharacterEscapeHandler; 

import java.io.IOException; 
import java.io.Writer; 

public class CustomCharacterEscapeHandler implements CharacterEscapeHandler { 

    public CustomCharacterEscapeHandler() { 
     super(); 
    } 

    public void escape(char[] ch, int start, int length, boolean isAttVal, Writer out) throws IOException { 
     // avoid calling the Writerwrite method too much by assuming 
     // that the escaping occurs rarely. 
     // profiling revealed that this is faster than the naive code. 
     int limit = start+length; 
     for (int i = start; i < limit; i++) { 
      char c = ch[i]; 
      if(c == '&' || c == '<' || c == '>' || c == '\'' || (c == '\"' && isAttVal)) { 
       if(i!=start) 
        out.write(ch,start,i-start); 
       start = i+1; 
       switch (ch[i]) { 
        case '&': 
         out.write("&amp;"); 
         break; 
        case '<': 
         out.write("&lt;"); 
         break; 
        case '>': 
         out.write("&gt;"); 
         break; 
        case '\"': 
         out.write("&quot;"); 
         break; 
        case '\'': 
         out.write("&apos;"); 
         break; 
       } 
      } 
     } 

     if(start!=limit) 
      out.write(ch,start,limit-start); 
    } 
} 

espoir qui aide.