6

I'm trying to create an XmlDocument using C# and .NET (version 2.0.. yes, version 2.0). I have set the namespace attributes using:

document.DocumentElement.SetAttribute(
    "xmlns:soapenv", "http://schemas.xmlsoap.org/soap/envelope");

When I create a new XmlElement using:

document.createElement("soapenv:Header");

...it doesn't include the soapenv namespace in the final XML. Any ideas why this happens?

More info:

Okay, I'll try to clarify this problem a bit. My code is:

XmlDocument document = new XmlDocument();
XmlElement element = document.CreateElement("foo:bar");
document.AppendChild(element); Console.WriteLine(document.OuterXml);

That outputs:

<bar />

However, what I want is:

<foo:bar />
DavidRR
  • 18,291
  • 25
  • 109
  • 191
Frank X
  • 175
  • 1
  • 1
  • 8

3 Answers3

5

You can assign a namespace to your bar element by using XmlDocument.CreateElement Method (String, String, String)

Example:

using System;
using System.Xml;

XmlDocument document = new XmlDocument();

// "foo"                    => namespace prefix
// "bar"                    => element local name
// "http://tempuri.org/foo" => namespace URI

XmlElement element = document.CreateElement(
    "foo", "bar", "http://tempuri.org/foo");

document.AppendChild(element);
Console.WriteLine(document.OuterXml);

Expected Output #1:

<foo:bar xmlns:foo="http://tempuri.org/foo" />

For a more interesting example, insert these statements before document.AppendChild(element);:

XmlElement childElement1 = document.CreateElement("foo", "bizz",
    "http://tempuri.org/foo");

element.AppendChild(childElement1);
    
XmlElement childElement2 = document.CreateElement("foo", "buzz",
    "http://tempuri.org/foo");

element.AppendChild(childElement2);

Expected Output #2:

<foo:bar xmlns:foo="http://tempuri.org/foo"><foo:bizz /><foo:buzz /></foo:bar>

Note that the child elements bizz and buzz are prefixed with the namespace prefix foo, and that the namespace URI http://tempuri.org/foo isn't repeated on the child elements since it is defined within the parent element bar.

DavidRR
  • 18,291
  • 25
  • 109
  • 191
  • This is nice, but I am trying to reuse the namespace prefixes defined at the document root level. I have tried many things, but I can't make it work. It always redefines the namespaces on the child elements themselves and then adds the prefix too (as in your example). Any ideas how to only keep the prefix and not repeat the namespace (that is defined already)? – user2173353 Nov 14 '20 at 13:32
  • 1
    @user2173353 I have demonstrated how to append child elements to a parent element such that the namespace URI of the parent element is not repeated on the child elements. – DavidRR Nov 17 '20 at 01:49
  • Thanks! I was trying to achieve this on an XML document, but the namespaces where repeated. Not sure why, but I will compare my code to to yours to find out. ;) – user2173353 Nov 18 '20 at 08:49
  • in my case root had the namespace, but i had the child element parameters switched ("buzz", "foo", ns: in your example). Switching them back to "foo", "buzz" fixed the issue. Thanks! – Volodymyr Kotylo Dec 13 '21 at 12:55
0
using System;
using System.Xml;

namespace ConsoleApp3
{
    class Program
    {
        static void Main(string[] args)
        {
            var Ruta = @"C:\Users\isaac\Documents\XML\XMLTEST.xml";
            Agregar(Ruta, "32323");

        }

        public static void Agregar(string Ruta, string valor)
        {
            XmlDocument XML = new XmlDocument();

            XML.Load(Ruta);
            XmlNode root = XML.GetElementsByTagName("dte:DatosEmision")[0];

            string dte = "http://www.sat.gob.gt/dte/fel/0.2.0";
            XmlElement childElement = XML.CreateElement("dte", "Otros", dte);

            XmlElement childElement1 = XML.CreateElement("dte", "OtroTexto", dte);
            childElement1.SetAttribute("codigo", "OC");
            childElement1.InnerText = valor;
            ////
            childElement.AppendChild(childElement1);

            try
            {


                root.InsertAfter(childElement, root.LastChild);

            }
            catch (Exception x)
            {

                Console.WriteLine(x);
            }
            XML.Save("XMLFile2.xml");

        }
    }
}

as a result

    <dte:Otros>
      <dte:OtroTexto codigo="OC">32323</dte:OtroTexto>
    </dte:Otros>
toyota Supra
  • 3,181
  • 4
  • 15
  • 19
Isaac Rac
  • 1
  • 1
  • Thank you for contributing to the Stack Overflow community. This may be a correct answer, but it’d be really useful to provide additional explanation of your code so developers can understand your reasoning. This is especially useful for new developers who aren’t as familiar with the syntax or struggling to understand the concepts. **Would you kindly [edit] your answer to include additional details for the benefit of the community?** – Jeremy Caney Aug 23 '23 at 02:45
-1

Maybe you could share what you're expecting as final XML document.

However from what I understand you want to do that looks like:

    <?xml version="1.0"?>
    <soapMessage xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope">
        <Header xmlns="http://schemas.xmlsoap.org/soap/envelope" />
    </soapMessage>

so the code to do that would be:

    XmlDocument document = new XmlDocument();
    document.LoadXml("<?xml version='1.0' ?><soapMessage></soapMessage>");
    string soapNamespace = "http://schemas.xmlsoap.org/soap/envelope/";
    XmlAttribute nsAttribute = document.CreateAttribute("xmlns","soapenv","http://www.w3.org/2000/xmlns/");
    nsAttribute.Value = soapNamespace;
    document.DocumentElement.Attributes.Append(namespaceAttribute);
    document.DocumentElement.AppendChild(document.CreateElement("Header",soapNamespace));
BiwiGreg
  • 66
  • 6
  • 1
    -1 you do not have to explicitly create the `xmlns` "attribute". That's a namespace declaration, and simply creating an element that uses the namespace will cause the attribute to magically appear. – John Saunders Apr 09 '14 at 13:58
  • Okay, I try to clarify this problem a bit.. My code is XmlDocument document = new XmlDocument(); XmlElement element = document.CreateElement("foo:bar"); document.AppendChild(element); Console.WriteLine(document.OuterXml); ...and it will output ...and it SHOULD output – Frank X Apr 10 '14 at 08:47