创建没有名称空间声明的XML元素

BEN*_*der 8 c# xml

我尝试将新的"PropertyGroup"元素添加到以下XML文件中

<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003" ToolsVersion="4.0">
  <PropertyGroup>
    <ProjectGuid>{00AA7ECA-95A0-0000-0000-AD4D2E056BFE}</ProjectGuid>
    <OutputType>Library</OutputType>
    <AppDesignerFolder>Properties</AppDesignerFolder>
    <RootNamespace>testnS</RootNamespace>
    <AssemblyName>testname</AssemblyName>
    <PluginId>4B84E5C0-EC2B-4C0C-8B8E-3FAEB09F74C6</PluginId>
  </PropertyGroup>
</Project>
Run Code Online (Sandbox Code Playgroud)

我使用的代码如下(注意还有其他逻辑已被删除):

        XmlTextReader reader = new XmlTextReader(filename);
        XmlDocument doc = new XmlDocument();

        doc.Load(reader);
        reader.Close();

        XmlNamespaceManager ns = new XmlNamespaceManager(doc.NameTable);
        ns.AddNamespace("x", "http://schemas.microsoft.com/developer/msbuild/2003");

        XmlElement root = doc.DocumentElement;
        XmlNode refNode = root.SelectSingleNode("x:Project", ns);

        root.SelectSingleNode("Project", ns);

        XmlElement newElement = doc.CreateElement("PropertyGroup", "http://schemas.microsoft.com/developer/msbuild/2003");
        newElement.InnerXml = "<value>test</value>";
        root.InsertAfter(newElement, refNode);
        doc.Save(filename);
Run Code Online (Sandbox Code Playgroud)

这会在XML文档中生成以下新元素:

<PropertyGroup>
  <value xmlns="">test</value>
</PropertyGroup>
Run Code Online (Sandbox Code Playgroud)

如何摆脱元素上的命名空间声明?

Jon*_*Jon 10

您需要为添加到DOM的所有元素指定XML命名空间:

XmlNamespaceManager ns = new XmlNamespaceManager(doc.NameTable);
ns.AddNamespace("x", "http://schemas.microsoft.com/developer/msbuild/2003");

XmlElement root = doc.DocumentElement;
XmlNode refNode = root.SelectSingleNode("x:Project", ns);

XmlElement newElement = doc.CreateElement(
    "PropertyGroup",
    "http://schemas.microsoft.com/developer/msbuild/2003");
var value = newElement.AppendChild(doc.CreateElement(
    "value",
    "http://schemas.microsoft.com/developer/msbuild/2003"));
value.AppendChild(doc.CreateTextNode("test"));

root.InsertAfter(newElement, refNode);
Run Code Online (Sandbox Code Playgroud)

如果你不对任何元素这样做(或者如果你这样使用InnerXml),那么该元素将获得可怕的空命名空间.


Rob*_*ine 5

发生这种情况的原因是您通过在根节点上定义命名空间来将文档的默认命名空间定义为“ http://schemas.microsoft.com/developer/msbuild/2003 ”:

xmlns="http://schemas.microsoft.com/developer/msbuild/2003"
Run Code Online (Sandbox Code Playgroud)

然后,您继续将不属于任何命名空间(“null”命名空间)的元素添加到文档中。这必须符合

xmlns=""
Run Code Online (Sandbox Code Playgroud)

因为如果不是,则意味着新元素位于前面提到的 Microsoft 命名空间中 - 但它不是(或者更确切地说 - 您没有要求它位于)。

所以要么:

  • 您实际上希望新元素位于 Microsoft 命名空间中 - 在这种情况下您需要这么说。最简单的方法是使用 createElement 并提供名称空间,尽管您可能可以使用 InnerXml 上的 xmlns 属性显式声明它(这不是添加节点的特别好的方法)。

  • 您确实希望此元素位于 null 命名空间中,在这种情况下,您最好使用命名空间前缀来限定不在 null 命名空间中的所有其他节点。

我怀疑你想要前者。

可以在此处找到有关命名空间的快速概述。


Iva*_*tin 5

为了避免xmlns=""新创建的元素中出现额外的属性,您可以将根命名空间作为参数传递:

 $child = $doc.CreateElement("value", $doc.DocumentElement.NamespaceURI);
 $res = $doc.PropertyGroup.AppendChild($child); # res here to avoid extra output
Run Code Online (Sandbox Code Playgroud)

这将导致

<PropertyGroup>
    <value></value>
</PropertyGroup>
Run Code Online (Sandbox Code Playgroud)