Select XML 的单个节点与 Powershell
Select Single Node of XML with Powershell
我正在努力阅读 XML:
<?xml version="1.0" encoding="utf-8"?>
<tmx version="1.4">
<header creationtool="B&R Automation Studio" creationtoolversion="4.2" datatype="unknown" segtype="sentence" adminlang="en" srclang="en" o-tmf="TMX">
<note>Change the namespace to define where this text module should be located within the logical structure of your texts</note>
<prop type="x-BR-TS:Namespace">ZagVision</prop>
</header>
<body>
<tu tuid="BcrWenglor.Init">
<tuv xml:lang="en">
<seg>Not initialized. </seg>
</tuv>
<tuv xml:lang="de">
<seg>Nicht initialisiert. </seg>
</tuv>
</tu>
<tu tuid="BcrUsbHid.WarnScanner">
<tuv xml:lang="fr">
<seg>BcrUsbHid : Avertissement général Scanner, scanner non reconnu ou interface défectueuse. </seg>
</tuv>
<tuv xml:lang="en">
<seg>BcrUsbHid: General warning Scanner, scanner not recognized or interface faulty. </seg>
</tuv>
<tuv xml:lang="de">
<seg>BcrUsbHid: Allgemeine Warnung Scanner, Scanner wurde nicht erkannt oder Schnittstelle fehlerhaft. </seg>
</tuv>
</tu>
</body>
</tmx>
我尝试通过“SelectSingleNode”通过 XPath 访问单个节点,如下所述:
XPath Syntax
$Path = "C:\Temp\ZagVision.tmx"
$result = Get-ChildItem -Path $Path -Filter '*.tmx' -Recurse |
ForEach-Object {
[xml]$xml = Get-Content -Path $_.FullName
foreach ($node in $xml.tmx.body.tu) {
[PSCustomObject]@{
'FileName' = $_.BaseName
'NameSpace' = $node.ParentNode.ParentNode.header.prop.'#text'
'LastChangeFile' = $_.LastWriteTime
'TextId' = $node.tuid
'fr' = $node.SelectSingleNode("//tuv[@lang='fr']")
'en' = $node.ChildNodes[1].seg # works fine , but only if we have 3 nodes
'de' = $node.ChildNodes[2].seg
}
}
}
$result
输出:
FileName : ZagVision
NameSpace : ZagVision
LastChangeFile : 16.07.2020 08:41:38
TextId : BcrUsbHid.WarnScanner
fr :
en : BcrUsbHid: General warning Scanner, scanner not recognized or
interface faulty.
de : BcrUsbHid: Allgemeine Warnung Scanner, Scanner wurde nicht
erkannt oder Schnittstelle fehlerhaft.
因为我刚开始使用 powershell,这可能是一些非常基本的东西,我在这里做错了......
提前致谢。
您需要注册 xml 命名空间才能将 xml:lang 属性与 selectSingleNode 一起使用:
$result = Get-ChildItem -Path $Path -Filter '*.tmx' -Recurse |
ForEach-Object {
[xml]$xml = Get-Content -Path $_.FullName
$ns = New-Object System.Xml.XmlNamespaceManager($xml.NameTable) # added this line
$ns.AddNamespace("xml", "http://www.w3.org/XML/1998/namespace") # added this line
foreach ($node in $xml.tmx.body.tu) {
[PSCustomObject]@{
'FileName' = $_.BaseName
'NameSpace' = $node.ParentNode.ParentNode.header.prop.'#text'
'LastChangeFile' = $_.LastWriteTime
'TextId' = $node.tuid
'fr' = $node.SelectSingleNode("//tuv[@xml:lang='fr']", $ns).seg # modified this line
'en' = $node.ChildNodes[1].seg # works if we have 3 nodes
'de' = $node.ChildNodes[2].seg
}
}
}
$result
我从尝试这样做时抛出的错误中发现了这一点:
"//tuv[@xml:lang='fr']"
@Uuuuuumm
是的,谢谢!注册命名空间并更改路径表达式
$node.SelectSingleNode("//tuv[@xml:lang='fr']", $ns).seg
到
$node.SelectSingleNode("tuv[@xml:lang='fr']", $ns).seg
做到了。
这是工作代码:
#$Path = "C:\Temp\ZagVision.tmx"
$result = Get-ChildItem -Path $Path -Filter '*.tmx' -Recurse |
ForEach-Object {
[xml]$xml = Get-Content -Path $_.FullName
$ns = New-Object System.Xml.XmlNamespaceManager($xml.NameTable)
$ns.AddNamespace("xml", "http://www.w3.org/XML/1998/namespace")
foreach ($node in $xml.tmx.body.tu) {
[PSCustomObject]@{
'FileName' = $_.BaseName
'NameSpace' = $node.ParentNode.ParentNode.header.prop.'#text'
'LastChangeFile' = $_.LastWriteTime
'TextId' = $node.tuid
'fr' = $node.SelectSingleNode("tuv[@xml:lang='fr']", $ns).seg
'en' = $node.SelectSingleNode("tuv[@xml:lang='en']", $ns).seg
'de' = $node.SelectSingleNode("tuv[@xml:lang='de']", $ns).seg
}
}
}
#$result
$result | Export-Csv -NoTypeInformation "C:\Temp\Messages.csv" -Encoding Default -Delimiter ';' #-Append
Invoke-Item "C:\Temp\Messages.csv"
我正在努力阅读 XML:
<?xml version="1.0" encoding="utf-8"?>
<tmx version="1.4">
<header creationtool="B&R Automation Studio" creationtoolversion="4.2" datatype="unknown" segtype="sentence" adminlang="en" srclang="en" o-tmf="TMX">
<note>Change the namespace to define where this text module should be located within the logical structure of your texts</note>
<prop type="x-BR-TS:Namespace">ZagVision</prop>
</header>
<body>
<tu tuid="BcrWenglor.Init">
<tuv xml:lang="en">
<seg>Not initialized. </seg>
</tuv>
<tuv xml:lang="de">
<seg>Nicht initialisiert. </seg>
</tuv>
</tu>
<tu tuid="BcrUsbHid.WarnScanner">
<tuv xml:lang="fr">
<seg>BcrUsbHid : Avertissement général Scanner, scanner non reconnu ou interface défectueuse. </seg>
</tuv>
<tuv xml:lang="en">
<seg>BcrUsbHid: General warning Scanner, scanner not recognized or interface faulty. </seg>
</tuv>
<tuv xml:lang="de">
<seg>BcrUsbHid: Allgemeine Warnung Scanner, Scanner wurde nicht erkannt oder Schnittstelle fehlerhaft. </seg>
</tuv>
</tu>
</body>
</tmx>
我尝试通过“SelectSingleNode”通过 XPath 访问单个节点,如下所述: XPath Syntax
$Path = "C:\Temp\ZagVision.tmx"
$result = Get-ChildItem -Path $Path -Filter '*.tmx' -Recurse |
ForEach-Object {
[xml]$xml = Get-Content -Path $_.FullName
foreach ($node in $xml.tmx.body.tu) {
[PSCustomObject]@{
'FileName' = $_.BaseName
'NameSpace' = $node.ParentNode.ParentNode.header.prop.'#text'
'LastChangeFile' = $_.LastWriteTime
'TextId' = $node.tuid
'fr' = $node.SelectSingleNode("//tuv[@lang='fr']")
'en' = $node.ChildNodes[1].seg # works fine , but only if we have 3 nodes
'de' = $node.ChildNodes[2].seg
}
}
}
$result
输出:
FileName : ZagVision
NameSpace : ZagVision
LastChangeFile : 16.07.2020 08:41:38
TextId : BcrUsbHid.WarnScanner
fr :
en : BcrUsbHid: General warning Scanner, scanner not recognized or
interface faulty.
de : BcrUsbHid: Allgemeine Warnung Scanner, Scanner wurde nicht
erkannt oder Schnittstelle fehlerhaft.
因为我刚开始使用 powershell,这可能是一些非常基本的东西,我在这里做错了...... 提前致谢。
您需要注册 xml 命名空间才能将 xml:lang 属性与 selectSingleNode 一起使用:
$result = Get-ChildItem -Path $Path -Filter '*.tmx' -Recurse |
ForEach-Object {
[xml]$xml = Get-Content -Path $_.FullName
$ns = New-Object System.Xml.XmlNamespaceManager($xml.NameTable) # added this line
$ns.AddNamespace("xml", "http://www.w3.org/XML/1998/namespace") # added this line
foreach ($node in $xml.tmx.body.tu) {
[PSCustomObject]@{
'FileName' = $_.BaseName
'NameSpace' = $node.ParentNode.ParentNode.header.prop.'#text'
'LastChangeFile' = $_.LastWriteTime
'TextId' = $node.tuid
'fr' = $node.SelectSingleNode("//tuv[@xml:lang='fr']", $ns).seg # modified this line
'en' = $node.ChildNodes[1].seg # works if we have 3 nodes
'de' = $node.ChildNodes[2].seg
}
}
}
$result
我从尝试这样做时抛出的错误中发现了这一点:
"//tuv[@xml:lang='fr']"
@Uuuuuumm 是的,谢谢!注册命名空间并更改路径表达式
$node.SelectSingleNode("//tuv[@xml:lang='fr']", $ns).seg
到
$node.SelectSingleNode("tuv[@xml:lang='fr']", $ns).seg
做到了。
这是工作代码:
#$Path = "C:\Temp\ZagVision.tmx"
$result = Get-ChildItem -Path $Path -Filter '*.tmx' -Recurse |
ForEach-Object {
[xml]$xml = Get-Content -Path $_.FullName
$ns = New-Object System.Xml.XmlNamespaceManager($xml.NameTable)
$ns.AddNamespace("xml", "http://www.w3.org/XML/1998/namespace")
foreach ($node in $xml.tmx.body.tu) {
[PSCustomObject]@{
'FileName' = $_.BaseName
'NameSpace' = $node.ParentNode.ParentNode.header.prop.'#text'
'LastChangeFile' = $_.LastWriteTime
'TextId' = $node.tuid
'fr' = $node.SelectSingleNode("tuv[@xml:lang='fr']", $ns).seg
'en' = $node.SelectSingleNode("tuv[@xml:lang='en']", $ns).seg
'de' = $node.SelectSingleNode("tuv[@xml:lang='de']", $ns).seg
}
}
}
#$result
$result | Export-Csv -NoTypeInformation "C:\Temp\Messages.csv" -Encoding Default -Delimiter ';' #-Append
Invoke-Item "C:\Temp\Messages.csv"