2009-04-08 6 views
66

जावा में आप एक स्ट्रिंग को कैसे परिवर्तित कर सकते हैं जो एक्सएमएल दस्तावेज़ में सम्मिलन के लिए एक्सएमएल के टुकड़े का प्रतिनिधित्व करता है?जावा में दस्तावेज़ नोड में स्ट्रिंग एक्सएमएल खंड को कनवर्ट करें

उदा।

String newNode = "<node>value</node>"; // Convert this to XML 

तो किसी दिए गए नोड के बच्चे के रूप में एक org.w3c.dom.Document में इस नोड डालने?

+0

भी देखें: http://stackoverflow.com/a/7607435/363573 – Stephan

उत्तर

52
Element node = DocumentBuilderFactory 
    .newInstance() 
    .newDocumentBuilder() 
    .parse(new ByteArrayInputStream("<node>value</node>".getBytes())) 
    .getDocumentElement(); 
+3

.parse (नई StringInputStream (.... .parse (नई ByteArrayInputStream (नई स्ट्रिंग ("xml") .getBytes())) पढ़ना चाहिए; – Steen

+5

मैं बस (उस बात के लिए, या markdown) इन commentboxes और मार्कअप की कमी से नफरत – Steen

+4

लेकिन यह नकल नहीं करता है बच्चे... उदाहरण के लिए आप यह केवल हो जाता है अपने बच्चों – grobartn

30

आप एक्सएमएल टुकड़े जोड़ने के लिए दस्तावेज़ के import (या adopt) पद्धति का उपयोग कर सकते हैं:

/** 
    * @param docBuilder 
    *   the parser 
    * @param parent 
    *   node to add fragment to 
    * @param fragment 
    *   a well formed XML fragment 
    */ 
    public static void appendXmlFragment(
     DocumentBuilder docBuilder, Node parent, 
     String fragment) throws IOException, SAXException { 
    Document doc = parent.getOwnerDocument(); 
    Node fragmentNode = docBuilder.parse(
     new InputSource(new StringReader(fragment))) 
     .getDocumentElement(); 
    fragmentNode = doc.importNode(fragmentNode, true); 
    parent.appendChild(fragmentNode); 
    } 
+5

हम्म का प्रयास कर सकते हैं। यदि यह सबसे आसान समाधान है, तो मुझे कहना होगा कि यह ऐसी छोटी समस्या के लिए जटिल है। – Jonik

+0

I ' इसे न्यूनतम तक सीमित कर दिया है - यह अभी भी जेआरई एपीआई में जो भी मिलता है उसका उपयोग करता है, हालांकि, वर्बोजिटी का थोड़ा सा अपरिहार्य है। – McDowell

+3

यह वहीं है जिसे मैं ढूंढ रहा था। मुझे एहसास नहीं हुआ कि मुझे पैरेंट नोड में जोड़ने से पहले डोम में टुकड़ा आयात करना था! –

14

क्या इसके लायक है के लिए, यहाँ एक समाधान मैं dom4j लाइब्रेरी का उपयोग कर के साथ आया है । (। मैं जाँच की थी कि यह काम करता है)

पढ़ें एक org.dom4j.Document में एक्सएमएल टुकड़ा (ध्यान दें: सभी XML नीचे इस्तेमाल किया कक्षाओं org.dom4j से कर रहे हैं; परिशिष्ट देखें):

String newNode = "<node>value</node>"; // Convert this to XML 
    SAXReader reader = new SAXReader(); 
    Document newNodeDocument = reader.read(new StringReader(newNode)); 

तब दस्तावेज़ मिल जिसमें नया नोड डाला जाता है, और इसके द्वारा अभिभावक तत्व (होना) होता है। (। आपका org.w3c.dom.Document यहाँ org.dom4j.Document करने के लिए परिवर्तित करने की आवश्यकता होगी) प्रयोजनों के परीक्षण के लिए, मैं इस तरह एक बनाया:

Document originalDoc = 
     new SAXReader().read(new StringReader("<root><given></given></root>")); 
    Element givenNode = originalDoc.getRootElement().element("given"); 

नए बच्चे तत्व जोड़ना बहुत आसान है:

givenNode.add(newNodeDocument.getRootElement()); 

हो गया। Outputting originalDoc अब पैदावार:

<?xml version="1.0" encoding="utf-8"?> 

<root> 
    <given> 
     <node>value</node> 
    </given> 
</root> 

परिशिष्ट: आपके प्रश्न के बारे में बात करती है org.w3c.dom.Document वजह से, यहाँ है कि और org.dom4j.Document के बीच परिवर्तित करने के लिए कैसे।

// dom4j -> w3c 
DOMWriter writer = new DOMWriter(); 
org.w3c.dom.Document w3cDoc = writer.write(dom4jDoc); 

// w3c -> dom4j 
DOMReader reader = new DOMReader(); 
Document dom4jDoc = reader.read(w3cDoc); 

(आप Document रों नियमित रूप से दोनों तरह की जरूरत चाहते हैं, तो यह शायद एक वर्ग XMLUtils या ऐसा ही कुछ कहा जाता है में साफ उपयोगिता तरीकों में इन डाल करने के लिए, मतलब हो सकता है।)

हो सकता है कि वहाँ

ऐसा करने के बेहतर तरीके हैं, यहां तक ​​कि किसी तीसरे पक्ष के पुस्तकालयों के बिना भी। लेकिन अब तक प्रस्तुत समाधानों में से, मेरे विचार में यह सबसे आसान तरीका है, भले ही आपको dom4j < -> w3c रूपांतरण करने की आवश्यकता हो।

अद्यतन (2011): अपने कोड पर dom4j निर्भरता जोड़ने से पहले, ध्यान दें कि it is not an actively maintained project, and has some other problems too। बेहतर संस्करण 2.0 उम्र के लिए काम में रहा है, लेकिन केवल एक अल्फा संस्करण उपलब्ध है। आप एक्सओएम की तरह वैकल्पिक विकल्प पर विचार करना चाहेंगे; ऊपर जुड़े प्रश्न में और पढ़ें।

+0

यदि dom4j कोई नो-गो है, तो इस समाधान को आजमाएं: http://stackoverflow.com/a/7607435/363573 – Stephan

6

XOM library का उपयोग करके, अभी तक एक और समाधान है, जो my dom4j answer के साथ प्रतिस्पर्धा करता है। (यह मेरे quest to find a good dom4j replacement का हिस्सा है जहां एक्सओएम को एक विकल्प के रूप में सुझाव दिया गया था।)

पहले एक nu.xom.Document में एक्सएमएल टुकड़ा पढ़ें:

String newNode = "<node>value</node>"; // Convert this to XML 
Document newNodeDocument = new Builder().build(newNode, ""); 

फिर, दस्तावेज़ और नोड जिसके तहत टुकड़ा जोड़ दिया जाता है मिलता है। अब

Document originalDoc = new Builder().build("<root><given></given></root>", ""); 
Element givenNode = originalDoc.getRootElement().getFirstChildElement("given"); 

बताया चाइल्ड नोड सरल है, और dom4j साथ के रूप में समान (सिवाय इसके कि XOM आप मूल जड़ तत्व जोड़ नहीं करता है: एक बार फिर, परीक्षण प्रयोजनों के लिए मैं दस्तावेज़ एक स्ट्रिंग से पैदा हो जाएगी जो पहले से ही newNodeDocument के अंतर्गत आता है):

givenNode.appendChild(newNodeDocument.getRootElement().copy()); 

दस्तावेज़ Outputting पैदावार सही परिणाम एक्सएमएल (और XOM उल्लेखनीय आसान है:

<?xml version="1.0"?> 
<root><given><node>value</node></given></root> 
: सिर्फ स्ट्रिंग originalDoc.toXML() द्वारा दिया) प्रिंट

(यदि आप एक्सएमएल को अच्छी तरह से प्रारूपित करना चाहते हैं (इंडेंटेशन और लाइनफीड्स के साथ), Serializer का उपयोग करें; इस बिंदु को इंगित करने के लिए पीटर Štibraný के लिए धन्यवाद।)

तो, स्वीकार्य रूप से यह dom4j समाधान से बहुत अलग नहीं है। :) हालांकि, एक्सओएम काम करने के लिए थोड़ा अच्छा हो सकता है, क्योंकि एपीआई बेहतर दस्तावेज है, और इसके डिजाइन दर्शन के कारण कि प्रत्येक चीज करने के लिए एक कैननिक तरीका है।

परिशिष्ट: फिर, यहां org.w3c.dom.Document और nu.xom.Document के बीच कनवर्ट करने का तरीका बताया गया है। XOM के DOMConverter कक्षा में सहायक विधियों का उपयोग करें:

// w3c -> xom 
Document xomDoc = DOMConverter.convert(w3cDoc); 

// xom -> w3c 
org.w3c.dom.Document w3cDoc = DOMConverter.convert(xomDoc, domImplementation); 
// You can get a DOMImplementation instance e.g. from DOMImplementationRegistry 
+0

ध्यान दें कि इसके बजाय नए बिल्डर()। बिल्ड (नया स्ट्रिंग रीडर ("")); आप नए बिल्डर() का निर्माण भी कर सकते हैं। ("", "test.xml"); (जहां "test.xml" कुछ यादृच्छिक आधार यूआरआई है) –

+1

"अगर आप एक्सएमएल को अच्छी तरह से प्रारूपित करना चाहते हैं (इंडेंटेशन और लाइनफीड्स के साथ), मुझे यकीन नहीं है कि एक्सओएम के साथ ऐसा कैसे करें।" - Serializer वर्ग का उपयोग कर। SetIndent और setMaxLength का उपयोग करके इसे कॉन्फ़िगर करें, और लिखें लिखें (दस्तावेज़)। –

+0

सीरिएलाइज़र उप-वर्गीकरण द्वारा अनुकूलित करना भी आसान है। –

4

आप dom4j उपयोग कर रहे हैं, तो आप सिर्फ कर सकते हैं:

दस्तावेज़ दस्तावेज़ = DocumentHelper.parseText (पाठ);

(dom4j अब यहां: https://github.com/dom4j/dom4j)

+0

बस अपनी वेबसाइट पर गया। वे Google विज्ञापन को सामान्य मैवेन-जेनरेट नेविगेशन बार में सीधे रखते हैं! अतुल्य! – Thilo

+2

जाहिर है, साइट अब dom4j लोगों द्वारा संचालित नहीं है, लेकिन कुछ डोमेन हथियार ले गए ... – Thilo

+0

एक dom4j-less समाधान: http://stackoverflow.com/a/7607435/363573 – Stephan

1

... और अगर आप विशुद्ध रूप से XOM, कुछ इस तरह का प्रयोग कर रहे:

String xml = "<fakeRoot>" + xml + "</fakeRoot>"; 
    Document doc = new Builder(false).build(xml, null); 
    Nodes children = doc.getRootElement().removeChildren(); 
    for(int ix = 0; ix < children.size(); ix++) { 
     otherDocumentElement.appendChild(children.get(ix)); 
    } 

XOM fakeRoot आंतरिक रूप से काफी भी ऐसा ही करने का उपयोग करता है, इसलिए यह सुरक्षित होना चाहिए, अगर बिल्कुल सुरुचिपूर्ण नहीं है।

4
/** 
* 
* Convert a string to a Document Object 
* 
* @param xml The xml to convert 
* @return A document Object 
* @throws IOException 
* @throws SAXException 
* @throws ParserConfigurationException 
*/ 
public static Document string2Document(String xml) throws IOException, SAXException, ParserConfigurationException { 

    if (xml == null) 
    return null; 

    return inputStream2Document(new ByteArrayInputStream(xml.getBytes())); 

} 


/** 
* Convert an inputStream to a Document Object 
* @param inputStream The inputstream to convert 
* @return a Document Object 
* @throws IOException 
* @throws SAXException 
* @throws ParserConfigurationException 
*/ 
public static Document inputStream2Document(InputStream inputStream) throws IOException, SAXException, ParserConfigurationException { 
    DocumentBuilderFactory newInstance = DocumentBuilderFactory.newInstance(); 
    newInstance.setNamespaceAware(true); 
    Document parse = newInstance.newDocumentBuilder().parse(inputStream); 
    return parse; 
} 
1

एक एक लाइनर के साथ jcabi-xml प्रयास करें,:

Node node = new XMLDocument("<node>value</node>").node(); 
संबंधित मुद्दे

 संबंधित मुद्दे