2016-04-11 2 views
1

J'ai un projet qui utilise des fichiers XML JAXB marshalled afin de comparer les états de configuration de différents environnements. J'ai remarqué qu'il doit y avoir quelques différences dans l'implémentation du marshaller JAXB sous Windows par rapport à la version Unix. Lorsque je compare 2 fichiers créés sur les différentes plateformes, mon outil de comparaison signale toujours une différence à la fin du fichier. Le fichier créé sous Windows a une nouvelle ligne (CR et LF) à la fin du fichier alors que la version Unix ne l'a pas.Marshaller sur Windows ajoute une nouvelle ligne à la fin du fichier

S'il vous plaît noter que le problème est pas sur la différence de la nouvelle ligne de caractères entre les deux plates-formes! Le marshaller Windows ajoute effectivement une "nouvelle ligne" à la fin du fichier tandis que le marshaller Unix s'arrête après la fermeture ">" de la balise racine.

Windows marshaller adds a new line at the end

est-il un paramètre que je peux passer au placier afin d'éviter que cette ligne supplémentaire ou dois-je supprimer explicitement après marshalling sous Windows, de sorte que mon outil de comparaison ne signale pas la différence ?

Voici comment le code de triage ressemble: de deux systèmes différents

public void marshal(final Object rootObject, final OutputStream outputStream) throws JAXBException, TransformerException { 
    Preconditions.checkArgument(rootObject != null, "rootObject must not be null"); 
    Preconditions.checkArgument(outputStream != null, "outputStream must not be null"); 
    final JAXBContext ctx = JAXBContext.newInstance(rootObject.getClass()); 
    final Document document = getFactories().newDocument(); 
    document.setXmlStandalone(true); 
    final Marshaller marshaller = ctx.createMarshaller(); 
    marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); 
    marshaller.setSchema(schema); 
    marshaller.marshal(rootObject, document); 
    createTransformer().transform(new DOMSource(document), new StreamResult(outputStream)); 
    } 

    public static Transformer createTransformer() { 
    final Transformer transformer = getFactories().newTransformer(); 
    transformer.setOutputProperty(OutputKeys.INDENT, "yes"); 
    transformer.setOutputProperty(OutputKeys.STANDALONE, "yes"); 
    transformer.setOutputProperty(OutputKeys.ENCODING, JAXBDefaults.OUTPUT_CHARSET.name()); 
    transformer.setOutputProperty(OutputKeys.CDATA_SECTION_ELEMENTS, CDATA_XML_ELEMENTS); 
    transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", IDENT_LENGTH); 
    return transformer; 
    } 


    private static class JAXBFactories { 

    private DocumentBuilderFactory documentBuilderFactory; 

    public DocumentBuilderFactory getDocumentBuilderFactory() { 
     if (documentBuilderFactory == null) { 
     documentBuilderFactory = DocumentBuilderFactory.newInstance(); 
     } 
     return documentBuilderFactory; 
    } 

    private DocumentBuilder documentBuilder; 

    public DocumentBuilder getDocumentBuilder() { 
     if (documentBuilder == null) { 
     try { 
      documentBuilder = getDocumentBuilderFactory().newDocumentBuilder(); 
     } catch (final ParserConfigurationException ex) { 
      throw new RuntimeException("Failed to create DocumentBuilder", ex); 
     } 
     } 
     return documentBuilder; 
    } 

    public Document newDocument() { 
     return getDocumentBuilder().newDocument(); 
    } 

    private TransformerFactory transformerFactory; 

    public TransformerFactory getTransformerFactory() { 
     if (transformerFactory == null) { 
     transformerFactory = TransformerFactory.newInstance(); 
     } 
     return transformerFactory; 
    } 

    public Transformer newTransformer() { 
     try { 
     return getTransformerFactory().newTransformer(); 
     } catch (final TransformerConfigurationException ex) { 
     throw new RuntimeException("Failed to create Transformer", ex); 
     } 
    } 

    } 

    private static class FactoriesHolder { 

    static final JAXBFactories FACTORIES = new JAXBFactories(); 
    } 

    private static JAXBFactories getFactories() { 
    return FactoriesHolder.FACTORIES; 
    } 

Répondre

1

Il n'y a pas de raison (ou attente) que XML joli d'impression produira exactement les mêmes résultats. Il semble cependant probable que si vous éteignez la jolie impression (et que votre IDE/éditeur le fasse), vous découvrirez probablement que la sortie est la même.

Joli-impression XML est une transformation de l'original qui ajoute la mise en page. Ce n'est plus réel xml.

+0

Merci pour la réponse! Je comprends tout à fait votre point. Cependant, mon problème est que l'une des principales raisons pour lesquelles j'ai choisi XML était la lisibilité humaine qu'il offre et la possibilité de comparer facilement avec n'importe quel outil de comparaison. Maintenant, en raison de cette ligne supplémentaire, je reçois beaucoup de fausses différences lors de la comparaison de plusieurs fichiers à la fois. Vous ne connaissez pas un bon outil pour la comparaison XML, n'est-ce pas? :) La comparaison de texte en clair a fonctionné OK pour l'instant mais il y a beaucoup d'autres problèmes en dehors de ce nouveau problème de ligne. – Alex

+0

@Alex - [KDiff] (http://kdiff3.sourceforge.net/) peut être dit d'ignorer les espaces blancs lors de la comparaison. Cela ne résout pas tous les problèmes mais cela aide beaucoup. – OldCurmudgeon