JQuery的XML解析:更换标签
我有下面的XML:JQuery的XML解析:更换标签
<?xml version="1.0" encoding="UTF-8" ?>
<text>
Lorem <foo>ipsum</foo> dolor sit amet.
</text>
,我试图解析这个XML与jQuery和替换<b></b>
标签的响应里面的<foo>
标签。结果字符串应该是"Lorem <b>ipsum</b> dolor sit amet."
我做对XML这样的GET请求:
$.ajax({
type: "GET",
url: "response.xml",
dataType: "xml",
success: function(xml){
}
});
我已经打过电话了replaceWith函数是这样的:
$(xml).find("foo").replaceWith(function(){
return "<b>" + $(this).text() + "</b>";
});
但这将完全从xml响应中删除文本。有什么我失踪?
编辑:萤火虫显示以下错误:
此[0] .innerHTML是不确定的
尝试使用
return "<b>" + $(this).html() + "</b>";
相反
这似乎用我的工作XML字符串直接在Firebug控制台中:
var xml = $('<?xml version="1.0" encoding="UTF-8" ?><text>Lorem <foo>ipsum</foo> dolor sit amet.</text>');
xml.find('foo').replaceWith(function(){
console.log(this);
return '<b>'+$(this).text()+'</b>';
});
console.log(xml);
您的成功功能还会发生什么?
我刚刚在萤火虫中检查过它,它显示我以下错误:这个[0] .innerHTML是未定义的。我只是在成功函数中执行replaceWith。 – arthurk 2010-10-27 19:59:44
'innerHTML'不适用于XML DOM,只适用于HTML DOM ...如果你试图用'innerHTML'做些什么,那就是你的问题。 – prodigitalson 2010-10-27 20:05:47
这可以作为字符串使用,但不能在加载xml时使用 – mcgrailm 2010-10-27 20:22:54
我建议您使用Web浏览器的XML DOM而不是滥用jQuery来处理HTML。这里是你如何解析XML到DOM:
var xmlDoc;
if (window.DOMParser)
{
var parser = new DOMParser();
xmlDoc = parser.parseFromString(xml, "text/xml");
}
else // Internet Explorer
{
xmlDoc = new ActiveXObject("Microsoft.XMLDOM");
xmlDoc.async = "false";
xmlDoc.loadXML(xml);
}
// Now do the tedious DOM manipulations on xmlDoc
var foos = xmlDoc.getElementsByTagName('foo');
for (var i = 0; i < foos.length; i++)
{
var oldElem = foos[i];
var replacement = xmlDoc.createElement("b");
replacement.appendChild(xmlDoc.createTextNode(oldElem.childNodes[0].nodeValue));
oldElem.parentNode.replaceChild(replacement, oldElem);
}
编辑
另一种可能是你使用客户端XSLT将XML转换成你想要的HTML。随着XSLT文档是这样的:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns="http://www.w3.org/1999/xhtml">
<xsl:template match="*">
<xsl:value-of select="."/>
</xsl:template>
<xsl:template match="text">
<span>
<xsl:apply-templates/>
</span>
</xsl:template>
<xsl:template match="foo">
<b>
<xsl:apply-templates/>
</b>
</xsl:template>
</xsl:stylesheet>
您可以将您的样品输入到span
与b
标签。如果你有很多转换规则,XSLT可能比一堆糟糕的DOM操作代码更易于维护。
jQuery是一个基于HTML的库,处理XML(或通常跨文档脚本)的能力有限。
一些方法将工作:find()
和text()
针对XML一般都可以。但是当你返回一个像<b>foo</b>
这样的标记字符串时,jQuery将使用它作为HTML内容,并尝试将其写入元素的innerHTML
。但是XML文档不是HTML,因此不支持innerHTML
,所以jQuery失败。
在任何情况下,您都不想采用元素的text()
并逐字将其用作标记。如果该文本包含<
或&
字符,该怎么办?这会破坏标记,并可能会导致跨站点脚本漏洞。不要使用天真的字符串吊索来准备HTML。
相反,使用DOM风格的方法。像replace()
这样的jQuery方法可以做到这一点,但是你不能使用简单的replace('<b>')
,因为jQuery会将'<b>'
转换成当前HTML文档拥有的HTML黑体元素,然后尝试将该HTML元素插入到XML文档,这将无法正常工作。相反,您需要使用XML DOM手动创建元素:
$(xml).find("foo").each(function() {
var b= xml.createElement('b');
this.parentNode.replaceChild(b, this);
while (this.firstChild)
b.appendChild(this.firstChild);
});
这改变了XML文档。但是,如果你想要做的是将XML文档转换为可用的HTML,这似乎并不能帮助你。使用序列化程序(依赖于浏览器)将其转换回XML标记可能会使标记不必与HTML兼容(例如,空标记可能会自行关闭)。
要将XML元素可靠地导入到HTML中,最好手动完成。 (有为importNode
,但IE不支持它。)例如:
function xmlToDocument(node, dest) {
if (node.nodeType===1) {
// Create HTML element from XML element. Change name if 'foo'.
//
var tag= node.tagName.toLowerCase()==='foo'? 'b' : node.tagName;
var el= document.createElement(tag);
dest.appendChild(el);
// Copy attributes
//
for (var attri= node.attributes.length; attri-->0;) {
var attr= node.attributes[attri];
el.setAttribute(attr.name, attr.value);
}
// Copy element contents
//
for (var child= node.firstChild; child!==null; child= child.nextSibling)
xmlToDocument(child, el);
}
else if (node.nodeType===3)
dest.appendChild(document.createTextNode(node.));
}
你知道...它可能更容易只是返回一些HTML标记的JSON对象。
永远不会使用innerHTML,它在每个浏览器中都有问题,并且运行不同,而且非常不标准! – 2010-10-27 20:55:19