使用 Powershell .Net 方法将 XML 转换为 HTML

Posted

技术标签:

【中文标题】使用 Powershell .Net 方法将 XML 转换为 HTML【英文标题】:Transforming XML to HTML using Powershell .Net method 【发布时间】:2021-03-29 09:06:17 【问题描述】:

我正在尝试使用 Powershell .Net 方法转换 XML file with an XSL file。这是我的代码,

#-- Create transformation --#
$xslt = New-Object System.Xml.Xsl.XslCompiledTransform

#-- Create a reader with DTDparsing set to parse --#
$xrs = New-Object System.Xml.XmlReaderSettings
$xrs.DtdProcessing = 'Parse'

#-- Load the XSL transform with the reader setting --#
$xr = [System.Xml.XmlReader]::Create("C:\Users\admin\Downloads\recoveryHistory_en.xsl", $xrs)
$xslt.Load($xr)

#-- Create a writer --#
$xws = New-Object System.Xml.XmlWriterSettings
$xw = [System.Xml.XmlWriter]::Create("C:\Users\admin\Downloads\Test RP_failover.html", $xslt.OutputSettings)

#-- Execute the transform and output the results to a file --#
$xslt.Transform("C:\Users\admin\Downloads\Test RP_failover.xml", $xw)
$xw.Close()

虽然$xslt.Transform() 确实按预期创建了 HTML 文件,但它似乎完全是空的。这是 xsl 文件中的 xsl:outputxsl:choose 元素。我的 XML 和 XSL 文件存储在上面的链接中。我想知道 XSL 文件中的 xsl:choose 元素是否导致输出 HTML 文件为空,因为 XSL 也有 <xsl:when test="@outputType = 'csv'">

<xsl:output omit-xml-declaration="yes" indent="yes" encoding="utf-8" doctype-public="-//W3C//DTD HTML 4.01 Transitional//EN"/>

<xsl:template match="RecoveryPlanStepReport">
<xsl:choose>
   <xsl:when test="@outputType = 'html'">
      <xsl:call-template name="PrintRecoveryPlanStepReportForHtml"/>
   </xsl:when>
   <xsl:when test="@outputType = 'csv'">
      <xsl:call-template name="PrintRecoveryPlanStepReportForCsv"/>
   </xsl:when>
</xsl:choose>
</xsl:template>

System.Xml.Xsl.XslCompiledTransformTransform 属性中是否有值可以设置为显式调用&lt;xsl:when test="@outputType = 'html'"&gt;?我正在尝试找到一种强制 XSL 仅使用 HTML 的方法。

$xslt = New-Object System.Xml.Xsl.XslCompiledTransform
$xslt.Transform.Value
OverloadDefinitions
-------------------
void Transform(System.Xml.XPath.IXPathNavigable input, System.Xml.XmlWriter results)
void Transform(System.Xml.XPath.IXPathNavigable input, System.Xml.Xsl.XsltArgumentList arguments, System.Xml.XmlWriter results)
void Transform(System.Xml.XPath.IXPathNavigable input, System.Xml.Xsl.XsltArgumentList arguments, System.IO.TextWriter results)
void Transform(System.Xml.XPath.IXPathNavigable input, System.Xml.Xsl.XsltArgumentList arguments, System.IO.Stream results)
void Transform(System.Xml.XmlReader input, System.Xml.XmlWriter results)
void Transform(System.Xml.XmlReader input, System.Xml.Xsl.XsltArgumentList arguments, System.Xml.XmlWriter results)
void Transform(System.Xml.XmlReader input, System.Xml.Xsl.XsltArgumentList arguments, System.IO.TextWriter results)
void Transform(System.Xml.XmlReader input, System.Xml.Xsl.XsltArgumentList arguments, System.IO.Stream results)
void Transform(string inputUri, System.Xml.XmlWriter results)
void Transform(string inputUri, System.Xml.Xsl.XsltArgumentList arguments, System.Xml.XmlWriter results)
void Transform(string inputUri, System.Xml.Xsl.XsltArgumentList arguments, System.IO.TextWriter results)
void Transform(string inputUri, System.Xml.Xsl.XsltArgumentList arguments, System.IO.Stream results)
void Transform(string inputUri, string resultsFile)
void Transform(System.Xml.XmlReader input, System.Xml.Xsl.XsltArgumentList arguments, System.Xml.XmlWriter results, System.Xml.XmlResolver documentResolver)
void Transform(System.Xml.XPath.IXPathNavigable input, System.Xml.Xsl.XsltArgumentList arguments, System.Xml.XmlWriter results, System.Xml.XmlResolver documentResolver)

【问题讨论】:

XSLT 是否在另一个上下文(如 IDE 或 XML 编辑器)中针对该 XML 工作,或者在使用 XSLT 处理器的命令行 API 运行时?否则,超过 90% 的 XSLT 不输出任何数据的问题只是 XSLT 没有考虑的 XML 输入中的默认名称空间。所以你需要展示 XML 和 XSLT 的相关部分,如果没有看到相关的 XML 输入,我们就无法判断模板失败的原因。 我和 Martin Honnen 在一起。只需运行像 &lt;xsl:template match="/"&gt;&lt;xsl:copy-of select="."/&gt;&lt;/xsl:template&gt; 这样的身份转换,就可以测试常见的命名空间问题。 对不起,如果我的信息不够清楚。我已将我的 XML 和 XSL 文件上传到 ufile.io/f/0bohi 并将其链接到上面的原始问题中。我认为将它们存储在那里而不是粘贴整个内容是明智的,我认为这很难阅读。让我用几个在线 XSLT/XML 验证器进行测试,看看会发生什么。 @Alejandro,是你的提示修复了它。 &lt;xsl:when test=EXPRESSION&gt; 存在问题,其中表达式在 XML 中不存在,因此未调用 &lt;xsl:call-template name="PrintHistoryReportForHtml"/&gt;。此外,我必须删除所有与 CSV 相关的模板。现在我可以使用修改后的 XSLT 成功生成 HTML 文件。非常感谢。如果您可以发表您的评论作为答案,我可以将其标记为“答案”。 尽量减少样本以证明问题并内联插入相关部分。如果您也想将示例放到网上,那么至少使用我们可以浏览的一侧来查看源代码,而不是提供下载。 【参考方案1】:

这是我修复它的方法,

我在XSL中修改了下面的sn-p

   <xsl:template match="RecoveryPlanResult">
     <xsl:choose>
       <xsl:when test="Results">  <!-- SRM 4.x identifying tag -->
         <xsl:choose>
           <xsl:when test="@outputType = 'html'">
             <xsl:call-template name="LegacyPrintHistoryReportForHtml"/>
           </xsl:when>
           <xsl:when test="@outputType = 'csv'">
             <xsl:call-template name="LegacyPrintHistoryReportForCsv"/>
           </xsl:when>
         </xsl:choose>
       </xsl:when>
       <xsl:otherwise>  <!-- SRM 5.x -->
         <xsl:choose>
           <xsl:when test="@outputType = 'html'">
             <xsl:call-template name="PrintHistoryReportForHtml"/>
           </xsl:when>
           <xsl:when test="@outputType = 'csv'">
             <xsl:call-template name="PrintHistoryReportForCsv"/>
           </xsl:when>
         </xsl:choose>
       </xsl:otherwise>
     </xsl:choose>
   </xsl:template>

到这里

<xsl:template match="RecoveryPlanResult">
    <xsl:call-template name="PrintHistoryReportForHtml"/>
</xsl:template>

问题:虽然match元素在xsl:template元素中有正确的模式,但xsl:when元素中的表达式不正确

<xsl:when test="@outputType = 'html'">

XML

<?xml version="1.0" encoding="UTF-8"?>
<RecoveryPlanResult>
  <RecoveryPlan>
    <Name>Test RP</Name>
    <Description />
    <LocalVcAddress>LocalVC</LocalVcAddress>
    <LocalSiteName>LocalSite</LocalSiteName>
    <RemoteVcAddress>remote</RemoteVcAddress>
    <RemoteSiteName>remote</RemoteSiteName>
    <TimeZoneOffset>0</TimeZoneOffset>
  </RecoveryPlan>
</RecoveryPlanResult>

【讨论】:

以上是关于使用 Powershell .Net 方法将 XML 转换为 HTML的主要内容,如果未能解决你的问题,请参考以下文章

Powershell 调用使用 App.config 的 .NET 程序集

Powershell / .Net:获取对方法返回的对象的引用

从 Powershell 调用的 DLL 使用相对于 Powershell 安装目录的路径。如何将其设置为其他内容?

powershell 使用System.Net命名空间中的WebClient类的DownloadFileAsync方法下载文件

powershell 使用System.Net命名空间中的WebClient类的DownloadFile方法下载文件

Powershell调用静态方法