Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why Error "System.String does not contain a method named 'AppendChild'"

Tags:

powershell

Why does this PowerShell Script not work:

[xml]$xml = '<products></products>'

$newproduct = $xml.CreateElement('product')
$attr = $xml.CreateAttribute('code')
$attr.Value = 'id1'
$newproduct.Attributes.Append($attr)

$products = $xml.products
$products.AppendChild($newproduct)

Error is

Method invocation failed because [System.String] does not contain a method named 'AppendChild'.
At line:1 char:1
+ $products.AppendChild($newproduct)
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidOperation: (:) [], RuntimeException
    + FullyQualifiedErrorId : MethodNotFound

If I replace

$products = $xml.products

by

$products = $xml.SelectSingleNode('//products')

it will work, but I'd like to know why first syntax does not work because it is illogical for me. $xml.products should be a valid XML object and thus provide the method AppendChild().

like image 943
user310291 Avatar asked Jan 07 '23 22:01

user310291


2 Answers

$xml.products does not reference the products node itself, but the contents of the products node. Since products is empty, it evaluates to an empty string.

To get to the products node you could also use:

$Products = $xml.FirstChild 
$Products.AppendChild($newproduct)

or, more specifically:

$Products = $xml.ChildNodes.Where({$_.Name -eq "products"}) |Select-Object -First 1
$Products.AppendChild($newproduct) 

But SelectSingleNode() will probably serve you just fine

like image 158
Mathias R. Jessen Avatar answered Jan 10 '23 12:01

Mathias R. Jessen


$xml.configuration.SelectSingleNode("connectionStrings").AppendChild($newnode)

would work fine, but an interesting & dirty hack: given this empty node:

  <connectionStrings>    
  </connectionStrings>

the script

$xml.configuration.connectionStrings.AppendChild($newnode)

gives a "Method invocation failed because [System.String] does not contain a method named 'AppendChild'" error

but this:

  <connectionStrings>
        <!-- random comment -->
  </connectionStrings>

works perfectly fine

like image 43
Vland Avatar answered Jan 10 '23 10:01

Vland