Xml XSL:如何防止xsltproc篡改属性值中转义的HTML字符串?

Xml XSL:如何防止xsltproc篡改属性值中转义的HTML字符串?,xml,csv,xslt,Xml,Csv,Xslt,我正在阅读一个平面实体的XML文件,其中的值都在属性中,并试图生成一个分隔文本文件(CSV,但不是comma1)。问题是其中一个属性的值是一个任意的HTML blob,它(在XML文件中)已被正确转义。但是,当我使用样式表运行xsltproc时,我会输出HTML,并使用换行符,这意味着我的输出不再是每个元素一行 示例XML输入——这都在源代码中的一行上,但为了清晰起见,我在这里插入了人工换行符: <row Id="-1" Reputation="1" CreationDate="2010-

我正在阅读一个平面实体的XML文件,其中的值都在属性中,并试图生成一个分隔文本文件(CSV,但不是comma1)。问题是其中一个属性的值是一个任意的HTML blob,它(在XML文件中)已被正确转义。但是,当我使用样式表运行xsltproc时,我会输出HTML,并使用换行符,这意味着我的输出不再是每个元素一行

示例XML输入——这都在源代码中的一行上,但为了清晰起见,我在这里插入了人工换行符:

<row Id="-1" Reputation="1" CreationDate="2010-11-18T19:05:26.543" DisplayName="Community" 
  LastAccessDate="2010-11-18T19:05:26.543" Location="on the server farm" 
  AboutMe="&lt;p&gt;Hi, I'm not really a person.&lt;/p&gt;&#xA;&#xA;&lt;p&gt;I'm a background process that helps keep this site clean!&lt;/p&gt;&#xA;&#xA;&lt;p&gt;I do things like&lt;/p&gt;&#xA;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Randomly poke old unanswered questions every hour so they get some attention&lt;/li&gt;&#xA;&lt;li&gt;Own community questions and answers so nobody gets unnecessary reputation from them&lt;/li&gt;&#xA;&lt;li&gt;Own downvotes on spam/evil posts that get permanently deleted&lt;/li&gt;&#xA;&lt;li&gt;Own suggested edits from anonymous users&lt;/li&gt;&#xA;&lt;li&gt;&lt;a href=&quot;http://meta.stackexchange.com/a/92006&quot;&gt;Remove abandoned questions&lt;/a&gt;&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;" 
  Views="0" UpVotes="760" DownVotes="315" AccountId="-1" />

我当前获得的输出如下所示(这些换行符位于输出中):

-1 | 1 | 2010-11-18T19:05:26.543 |社区| 2010-11-18T19:05:26.543 |在服务器场|嗨,我不是一个人

我是一个后台进程,有助于保持这个网站的清洁

我做的事情像

  • 每小时随机提出一些未回答的老问题,以便引起注意
  • 拥有自己的社区问题和答案,因此没有人从他们那里获得不必要的声誉
  • 拥有永久删除的垃圾邮件/恶意帖子的否决票
  • 拥有来自匿名用户的建议编辑
| 0 | 760 | 315 | -1 |
我的样式表是:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output method="text" encoding="UTF-8"/>

<xsl:template match="row">
  <xsl:for-each select="@*">
    <xsl:value-of select="."/>
    <xsl:text> | </xsl:text>
    </xsl:for-each>
  <xsl:text>&#xA;</xsl:text>
</xsl:template>

</xsl:stylesheet>

| 

;
如果我必须为HTML-y属性(在本例中为AboutMe)编写特殊的处理,那没关系,但是最好使用“在输入文件中保留文本”的通用解决方案,因为我希望对几个不同的XML输入文件使用相同的样式表。我需要a的转换在输出文件中的一行上显示出来


1我知道这里还有另一个问题——如果管道出现在其中一个文本字段中,在某个时候它肯定会出现,该怎么办?我可以自由地使用任何单个字符作为分隔符;我现在正在使用管道,直到我解决了这个问题。

您可以使用
translate()
来转换属性1:1,它将替换字符,在本例中,返回字符和换行字符由空格字符替换:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output method="text" encoding="UTF-8"/>

<xsl:template match="row">
  <xsl:for-each select="@*">
    <xsl:value-of select="translate(., '&#xA;&#xD;', '  ')"/>
    <xsl:text> | </xsl:text>
    </xsl:for-each>
  <xsl:text>&#xA;</xsl:text>
</xsl:template>

</xsl:stylesheet>

| 

;
还有一句话:您可能想添加一个带有任何条件的
,作为
的第一个子元素,以便为所有行获得相同的列顺序

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output method="text" encoding="UTF-8"/>

<xsl:template match="row">
  <xsl:for-each select="@*">
    <xsl:value-of select="translate(., '&#xA;&#xD;', '  ')"/>
    <xsl:text> | </xsl:text>
    </xsl:for-each>
  <xsl:text>&#xA;</xsl:text>
</xsl:template>

</xsl:stylesheet>