Question

J'ai deux applications écrites en Java qui communiquent entre elles à l'aide de messages XML sur le réseau.J'utilise un analyseur SAX à la réception pour récupérer les données des messages.L'une des exigences est d'incorporer des données binaires dans un message XML, mais SAX n'aime pas cela.Est-ce que quelqu'un sait comment faire ça?

MISE À JOUR:J'ai fait fonctionner ça avec le Base64 classe de la bibliothèque de codecs Apache Commons, au cas où quelqu'un d'autre essaierait quelque chose de similaire.

Était-ce utile?

La solution

Vous pouvez encoder les données binaires en base64 et les placer dans un élément Base64 ;l'article ci-dessous est assez bon sur le sujet.

Gestion des données binaires dans les documents XML

Autres conseils

XML est si polyvalent...

<DATA>
  <BINARY>
    <BIT index="0">0</BIT>
    <BIT index="1">0</BIT>
    <BIT index="2">1</BIT>
    ...
    <BIT index="n">1</BIT>
  </BINARY>
</DATA>

XML est comme la violence : s'il ne résout pas votre problème, c'est que vous n'en utilisez pas suffisamment.

MODIFIER:

D'AILLEURS:Base64 + CDATA est probablement la meilleure solution

(EDIT2 :
Quiconque me met à jour, veuillez également mettre à jour la vraie réponse.Nous ne voulons pas qu'une pauvre âme vienne ici et mette en œuvre ma méthode parce qu'elle était la mieux classée sur SO, n'est-ce pas ?)

Base64 est en effet la bonne réponse mais CDATA ne l'est pas, cela revient à dire :"cela pourrait être n'importe quoi", mais cela doit pas être n'importe quoi, il doit s'agir de données binaires codées en Base64.Le schéma XML définit Binaire base 64 comme type de données primitif que vous pouvez utiliser dans votre xsd.

J'ai eu ce problème la semaine dernière.J'ai dû sérialiser un fichier PDF et l'envoyer, dans un fichier XML, à un serveur.

Si vous utilisez .NET, vous pouvez convertir un fichier binaire directement en chaîne base64 et le coller dans un élément XML.

string base64 = Convert.ToBase64String(File.ReadAllBytes(fileName));

Ou bien, il existe une méthode intégrée directement à l’objet XmlWriter.Dans mon cas particulier, j'ai dû inclure l'espace de noms du type de données Microsoft :

StringBuilder sb = new StringBuilder();
System.Xml.XmlWriter xw = XmlWriter.Create(sb);
xw.WriteStartElement("doc");
xw.WriteStartElement("serialized_binary");
xw.WriteAttributeString("types", "dt", "urn:schemas-microsoft-com:datatypes", "bin.base64");
byte[] b = File.ReadAllBytes(fileName);
xw.WriteBase64(b, 0, b.Length);
xw.WriteEndElement();
xw.WriteEndElement();
string abc = sb.ToString();

La chaîne abc ressemble à ceci :

<?xml version="1.0" encoding="utf-16"?>
<doc>
    <serialized_binary types:dt="bin.base64" xmlns:types="urn:schemas-microsoft-com:datatypes">
        JVBERi0xLjMKJaqrrK0KNCAwIG9iago8PCAvVHlwZSAvSW5mbw...(plus lots more)
    </serialized_binary>
</doc>

J'encode habituellement les données binaires avec MIMEBase64 ou Encodage d'URL.

Essayez d'encoder/décoder vos données binaires en Base64.Consultez également les sections CDATA

Peut-être les coder dans un ensemble connu - quelque chose comme la base 64 est un choix populaire.

N'importe lequel codage binaire en texte fera l'affaire.J'utilise quelque chose comme ça

<data encoding="yEnc>
<![CDATA[ encoded binary data ]]>
</data>

Bien que les autres réponses soient généralement bonnes, vous pouvez essayer une autre méthode de codage, plus économe en espace, comme yEnc.(Lien Wikipédia yEnc) Avec yEnc, obtenez également une capacité de somme de contrôle dès la sortie de la boîte.Lire et liens ci-dessous.Bien entendu, étant donné que XML n'a pas de type yEnc natif, votre schéma XML doit être mis à jour pour décrire correctement le nœud codé.

Pourquoi:En raison des stratégies d'encodage base64/63, uuencode et al.Les encodages augmentent la quantité de données (surcharge) que vous devez stocker et transférer d'environ 40 % (contreyEnc est de 1 à 2 %).En fonction de ce que vous encodez, une surcharge de 40 % pourrait être/devenir un problème.


yEnc - Résumé Wikipédia : https://en.wikipedia.org/wiki/YEncyEnc est un système de codage binaire en texte permettant de transférer des fichiers binaires dans des messages sur Usenet ou via e-mail....Un avantage supplémentaire de yEnc par rapport aux méthodes de codage précédentes, telles que uuencode et Base64, est l'inclusion d'une somme de contrôle CRC pour vérifier que le fichier décodé a été livré intact.‎

Les frais généraux Base64 sont de 33 %.

BaseXML pour XML1.0 les frais généraux ne sont que de 20 %.Mais ce n'est pas un standard et n'a encore qu'une implémentation en C.Vérifiez-le si vous êtes préoccupé par la taille des données.Notez que cependant les navigateurs ont tendance à implémenter la compression afin qu'elle soit moins nécessaire.

Je l'ai développé après la discussion dans ce fil : Encodage de données binaires au sein de XML :alternatives à base64.

Vous pouvez aussi Uuencode vos données binaires originales.Ce format est un peu plus ancien mais il fait la même chose que l'encodage base63.

Si vous contrôlez le format XML, vous devez renverser le problème.Plutôt que de joindre le XML binaire, vous devriez réfléchir à la manière de joindre un document comportant plusieurs parties, dont l'une contient du XML.

La solution traditionnelle à ce problème est une archive (par ex.le goudron).Mais si vous souhaitez conserver votre document joint dans un format texte ou si vous n'avez pas accès à une bibliothèque d'archivage de fichiers, il existe également un schéma standardisé largement utilisé dans le courrier électronique et HTTP qui est multipart/* MIME avec Encodage de transfert de contenu :binaire.

Par exemple, si vos serveurs communiquent via HTTP et que vous souhaitez envoyer un document en plusieurs parties, le principal étant un document XML faisant référence à une donnée binaire, la communication HTTP pourrait ressembler à ceci :

POST / HTTP/1.1
Content-Type: multipart/related; boundary="qd43hdi34udh34id344"
... other headers elided ...

--qd43hdi34udh34id344
Content-Type: application/xml

<myxml>
    <data href="cid:data.bin"/>
</myxml>
--qd43hdi34udh34id344
Content-Id: <data.bin>
Content-type: application/octet-stream
Content-Transfer-Encoding: binary

... binary data ...
--qd43hdi34udh34id344--

Comme dans l'exemple ci-dessus, le XML fait référence aux données binaires dans le multipart englobant en utilisant un cid Schéma d'URI qui est un identifiant de l'en-tête Content-Id.La surcharge de ce schéma serait simplement l'en-tête MIME.Un schéma similaire peut également être utilisé pour la réponse HTTP.Bien entendu, dans le protocole HTTP, vous avez également la possibilité d'envoyer un document en plusieurs parties dans une requête/réponse distincte.

Si vous souhaitez éviter d'encapsuler vos données dans un multipart, utilisez l'URI des données :

<myxml>
    <data href="data:application/something;charset=utf-8;base64,dGVzdGRhdGE="/>
</myxml>

Mais cela a la surcharge base64.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top