2016-10-14 6 views
0

Verwenden von PowerShell-Skripts zum dynamischen Anhängen von XML-Tags. In diesem Fall wird versucht, ein benutzerdefiniertes ElasticSearch-Ziel für NLog hinzuzufügen (von here).Laden von XML mit benutzerdefiniertem Namespace

$source = '<target name="elastic" xsi:type="BufferingWrapper"> </target>' 

Wenn $source zu XML-Konvertierung mit

[xml]$source 

oder

$xml = New-Object -TypeName System.Xml.XmlDocument 
$xml.LoadXml($source) 

bekomme ich folgende Fehler

Cannot convert value "<targetname="elastic" xsi:type="BufferingWrapper"> </target>" to type "System.Xml.XmlDocument". Error: "'xsi' is an undeclared prefix."

Irgendwelche Vorschläge?

Fast, aber nicht ganz da:

ich ConvertTo-Xml $source -as Document verwenden können, aber das Ergebnis verwendet nicht die <target>-Tag, verwendet es <Object>, was in diesem Fall nicht funktioniert.

<?xml version="1.0" encoding="utf-8"?> 
<Objects> 
    <Object Type="System.String">&lt;target name="elastic" xsi:type="BufferingWrapper" 
<Objects> 

Antwort

1

Sie könnten das XML-Fragment laden, wie in this answer beschrieben:

$source = '<target name="elastic" xsi:type="BufferingWrapper"></target>' 
$sreader = New-Object IO.StringReader $source 
$xreader = New-Object Xml.XmlTextReader $sreader 
$xreader.Namespaces = $false 
$fragment = New-Object Xml.XmlDocument 
$fragment.Load($xreader) 

jedoch davon aus, dass Sie das Fragment in einer anderen XML-Datenstruktur zu einem bestimmten Zeitpunkt zu importieren, so wohl tun führen zu andere Probleme (siehe zum Beispiel this question).

um dieses Problem zu arbeiten, um einen Dummy-Root-Knoten mit dem richtigen Namespace-Definition der XML-Fragment hinzu:

$source = '<target name="elastic" xsi:type="BufferingWrapper"> </target>' 
[xml]$fragment = "<dummy xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance'>$source</dummy>" 

diese Weise können Sie den Knoten in einem anderen XML-Dokument wie folgt aus (die andere XML zur Verfügung gestellte Datei importieren enthält auch die richtige Namensraumdefinition):

[xml]$xml = Get-Content 'C:\path\to\master.xml' 

$nsm = New-Object Xml.XmlNamespaceManager $xml.NameTable 
$nsm.AddNamespace('xsi', $xml.NamespaceURI) 

$node = $xml.ImportNode($fragment.DocumentElement.target, $true) 

$targets = $xml.SelectSingleNode('//targets', $nsm) 
$targets.AppendChild($node) | Out-Null