.NET के XmlDocument से आउटपुट में रिक्त xmlns विशेषताओं को कैसे रोकें?


118

.NET में XmlDocument से XML जेनरेट xmlnsकरते समय , एक खाली विशेषता दिखाई देती है जब पहली बार संबंधित नाम स्थान के बिना एक तत्व डाला जाता है; इसे कैसे रोका जा सकता है?

उदाहरण:

XmlDocument xml = new XmlDocument();
xml.AppendChild(xml.CreateElement("root",
    "whatever:name-space-1.0"));
xml.DocumentElement.AppendChild(xml.CreateElement("loner"));
Console.WriteLine(xml.OuterXml);

आउटपुट:

<root xmlns="whatever:name-space-1.0"><loner xmlns="" /></root>

वांछित आउटपुट:

<root xmlns="whatever:name-space-1.0"><loner /></root>

क्या XmlDocumentकोड के लिए एक समाधान लागू होता है , न कि कुछ ऐसा जो दस्तावेज़ को स्ट्रिंग के साथ परिवर्तित करने के बाद होता है OuterXml?

ऐसा करने का मेरा तर्क यह देखना है कि क्या मैं XmlDocument- जनित XML का उपयोग करके किसी विशेष प्रोटोकॉल के मानक XML से मेल खा सकता हूं। रिक्त xmlnsविशेषता पार्सर को तोड़ या भ्रमित नहीं कर सकती है , लेकिन यह किसी भी उपयोग में मौजूद नहीं है जो मैंने इस प्रोटोकॉल के बारे में देखा है।

जवाबों:


111

जेरेमी ल्यू के उत्तर के लिए धन्यवाद और चारों ओर एक सा खेल, मैंने सोचा कि खाली xmlnsविशेषताओं को कैसे हटाया जाए : रूट नोड के नामस्थान में पास करें जब आप चाहते हैं कि कोई भी बच्चा नोड नहीं बनाये। रूट पर उपसर्ग के बिना किसी नामस्थान का उपयोग करने का अर्थ है कि आपको बाल तत्वों पर उसी नामस्थान का उपयोग करने की आवश्यकता है, क्योंकि उनके पास उपसर्ग भी नहीं हैं।

फिक्स्ड कोड:

XmlDocument xml = new XmlDocument();
xml.AppendChild(xml.CreateElement("root", "whatever:name-space-1.0"));
xml.DocumentElement.AppendChild(xml.CreateElement("loner", "whatever:name-space-1.0")); 
Console.WriteLine(xml.OuterXml);

आपके सभी जवाबों के लिए सभी को धन्यवाद जिसने मुझे सही दिशा में आगे बढ़ाया!


1
यकीनन। <Loner> तत्व को "जो भी: name-space-1.0" नामस्थान में रखने का अर्थ है कि खाली xmlns विशेषता (जो इसे किसी भी नामस्थान में नहीं डालती है) को जोड़ा जाएगा जब इसे क्रमबद्ध नहीं किया जाएगा। यदि आपको नामस्थान कैसे काम करते हैं, इस पर ताज़ा करने की आवश्यकता है, तो jclark.com/xml/xmlns.htm
JeniT

2
बाहर देखो: तत्वों को यह (या शायद बेहतर doc.DocumentElement.NamespaceURI) की आवश्यकता है, लेकिन आप के लिए एक नाम स्थान निर्दिष्ट नहीं करते CreateAttribute()हैं, xmlns:psomethingभले ही वह एक ही उरी हो।
जेसन क्लेबन

87

यह जेनीटी के जवाब का एक प्रकार है (बहुत बहुत धन्यवाद!)

XmlElement new_element = doc.CreateElement("Foo", doc.DocumentElement.NamespaceURI);

यह हर जगह नाम स्थान की नकल या दोहराने के लिए समाप्त करता है।


3
मेरे हिसाब से बेस्ट रिस्पॉन्स। हमें यह जानने की ज़रूरत नहीं है कि दस्तावेज़ डिफ़ॉल्ट नाम स्थान क्या है (जब हम स्क्रैच से xml फ़ाइल नहीं बनाते हैं तो उपयोगी है (परिदृश्यों को पढ़ें और संशोधित करें)।
MuiBienCarlota

11

यदि <loner>आपके नमूने में मौजूद तत्व XML में xmlnsडिफ़ॉल्ट नाम स्थान की घोषणा नहीं है, तो यह whatever:name-space-1.0बिना नाम के स्थान पर होने के बजाय नामस्थान में होगा। यदि आप यही चाहते हैं, तो आपको उस नामस्थान में तत्व बनाने की आवश्यकता है:

xml.CreateElement("loner", "whatever:name-space-1.0")

यदि आप चाहते हैं कि <loner>तत्व किसी नामस्थान में न हो, तो जो XML निर्मित किया गया है वह ठीक वही है जिसकी आपको आवश्यकता है, और आपको उस xmlnsविशेषता के बारे में चिंता नहीं करनी चाहिए जो आपके लिए स्वचालित रूप से जोड़ी गई है।


3
समस्या गैर-अनुरूप XML पार्सर (आमतौर पर Microsoft से) के साथ है जो xmnls = "") से सामना नहीं कर सकता है।
क्रेग ट्रेडर

2
/। बुलाया। वे अपनी बेतरतीब एमएस कोसने वाली टिप्पणी वापस चाहते हैं।

@W। क्रेग ट्रेडर - मैं यह नहीं कह सकता कि मैंने एक समस्या के रूप में सामना किया है। उदाहरण?
केव

1
सही है, मैं नहीं चाहता कि <loner /> नोड में नेमस्पेस हो, लेकिन मैं नहीं चाहता कि इसमें कोई खाली नामस्थान विशेषता (xmlns) हो। मेरा तर्क सिर्फ यह देखना है कि क्या मैं किसी विशेष प्रोटोकॉल के XML आउटपुट का मिलान कर सकता हूं जो इस तरह सेटअप है।
नील सी। ओम्बेम्स्की

5
यह यादृच्छिक कोस नहीं था। Microsoft अद्यतनकर्ता अनुप्रयोग ब्लॉक एक ग्राहक को देने के लिए निर्धारित करने के लिए एक XML घोषणापत्र का उपयोग करता है। दुर्भाग्य से, मैनिफ़ेस्ट पार्सर xmlns = "" के साथ सामना नहीं कर सकता; मुझे एक पोस्ट-प्रोसेसर लिखना था जो खाली xmlns विशेषताओं को बाहर निकाल देगा।
क्रेग ट्रेडर

7

चूंकि रूट एक अविभाजित नेमस्पेस में है, इसलिए रूट का कोई भी बच्चा जो अन-नेमस्पेस होना चाहता है, उसे आपके उदाहरण की तरह आउटपुट होना चाहिए। समाधान मूल तत्व को उपसर्ग करना होगा जैसे:

<w:root xmlns:w="whatever:name-space-1.0">
   <loner/>
</w:root>

कोड:

XmlDocument doc = new XmlDocument();
XmlElement root = doc.CreateElement( "w", "root", "whatever:name-space-1.0" );
doc.AppendChild( root );
root.AppendChild( doc.CreateElement( "loner" ) );
Console.WriteLine(doc.OuterXml);

धन्यवाद, लेकिन वास्तविक रूट में नाम स्थान जोड़ने से मेरे XML को उस विशेष प्रोटोकॉल के संबंध में तोड़ दिया जाएगा, जिसके साथ मैं काम कर रहा हूं।
नील सी। ओब्राम्स्की

आह! मुझे एहसास हुआ कि आप क्या कह रहे थे और अपना जवाब लिखते समय इसे ध्यान में रखा। धन्यवाद जेरेमी
नील सी। ओब्राम्स्की

0

यदि संभव हो, तो क्रमबद्धता वर्ग बनाएं, तब करें:

XmlSerializerNamespaces ns = new XmlSerializerNamespaces();
ns.Add("", "");
XmlSerializer serializer = new XmlSerializer(yourType);
serializer.Serialize(xmlTextWriter, someObject, ns);

यह सुरक्षित है, और यदि आप वास्तव में अधिक नियंत्रण की आवश्यकता है, तो आप विशेषताओं के साथ नाम स्थान को नियंत्रित कर सकते हैं।


0

मैंने फ़ैक्टरी पैटर्न का उपयोग करके समस्या को हल किया है। मैंने XElement वस्तुओं के लिए एक कारखाना बनाया। कारखाने की तात्कालिकता के लिए पैरामीटर के रूप में मैंने एक XNamespace ऑब्जेक्ट निर्दिष्ट किया है। इसलिए, कारखाने द्वारा प्रत्येक बार एक XElement बनाया जाता है, नाम स्थान स्वचालित रूप से जुड़ जाएगा। यहाँ कारखाने का कोड है:

internal class XElementFactory
{
    private readonly XNamespace currentNs;

    public XElementFactory(XNamespace ns)
    {
        this.currentNs = ns;
    }

    internal XElement CreateXElement(String name, params object[] content)
    {
        return new XElement(currentNs + name, content);
    }
}

1
ओपी के बारे में पूछ रहा था XmlDocument, नहीं XDocument
जॉन सॉन्डर्स

0

हाँ, आप XMLNS को XmlElement से रोक सकते हैं। पहले समय बनाना यह आ रहा है: जैसे

<trkpt lat="30.53597" lon="-97.753324" xmlns="">
    <ele>249.118774</ele>
    <time>2006-05-05T14:34:44Z</time>
</trkpt>

कोड बदलें: और इस तरह से xml नेमस्पेस पास करें

C # कोड:

XmlElement bookElement = xdoc.CreateElement("trkpt", "http://www.topografix.com/GPX/1/1");
bookElement.SetAttribute("lat", "30.53597");
bookElement.SetAttribute("lon", "97.753324");
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.