DOM 的 JavaScript 解析器
Posted
技术标签:
【中文标题】DOM 的 JavaScript 解析器【英文标题】:A JavaScript parser for DOM 【发布时间】:2012-03-21 08:45:20 【问题描述】:我们在一个项目中有一个特殊要求,我们必须在客户端仅通过 JavaScript 解析一串 html(来自 AJAX 响应)。没错没有在 PHP 或 Java 中进行解析!我整个星期都在使用 ***,但还没有一个可以接受的解决方案。
有关要求的更多详细信息:
我们可以使用任何库(最好是 dojo 和/或 jQuery)或使用原生库!
我们需要解析一个作为字符串接收的整个 HTML 文档,包括<head>
和<body>
。
我们有时还需要将已解析的 DOM 结构序列化为字符串。
最后,我们不希望将解析后的 DOM 附加到当前 Document。 相反,我们会将其发送回服务器进行永久存储。
例如:我们需要类似的东西
var dom = HTMLtoDOM('<html><head><title> This is the old title. </title></head></html>');
dom.getElementsByTagName('title')[0].innerHTML = "This is a new Title";
根据我的研究,以下是我们的选择:
TinyMCE Parser。问题?我认为我们必须包括一名编辑。在我们不需要编辑器的情况下解析 HTML 怎么样?
John Resig's Parser。应该是我们最好的选择。不幸的是,当将页面的全部内容提供给解析器时,解析器就会崩溃!
jQuery $(htmlString) 或 dojo.toDom(htmlString)。两者都依赖 DocumentFragment,因此吞噬了 <head>
和 <body>
!
编辑:我们想要序列化 HTML,以便我们可以通过 RegExp 捕获某些自定义 HTML Commnet。我们需要让用户有机会编辑元标记、标题标记等,因此需要 HTML 解析器。
哦,我觉得我会在 Stack Overflow 中被谋杀,即使我只是提示通过 RegExp 解析 HTML !!!
【问题讨论】:
创建一个 IFRAME 节点并将其塞入其中? 但是.. 我不明白你为什么要在将已经序列化的 HTML 字符串发送到服务器之前“解析”它。无论如何,您都必须将其重新序列化回字符串以将其传递回服务器,对吗? @JensRoland 我们想从 RegExp 中捕获某些自定义 HTML cmets,从而进行序列化。我们希望让用户能够编辑标题标签、元标签等,从而进行 DOM 解析! @DreamFactory:给他们<input>
的!不要给用户做 XSS 或其他危险事情的机会。他们不需要编辑文档!并且您应该永远显示并非来自可信来源的 HTML。永远不要相信客户!很危险!
可以管理所有提到的问题,而无需一次解析整个 DOM
【参考方案1】:
您可以利用当前文档而不向其附加任何节点。
试试这样的:
function toNode(html)
var doc = document.createElement('html');
doc.innerHTML = html;
return doc;
var node = toNode('<html><head><title> This is the old title. </title></head></html>');
console.log(node);
http://jsfiddle.net/6SvqA/3/
【讨论】:
现在 this 很优雅。 +1!但是我们仍然有一个问题,即解析 DOM 是解决初始问题的错误方法。不过,这不是这个答案的错。 @elusive 它可能适用于受信任的用户,例如现场代理或其他你永远不知道的东西。 @elusive 用户非常信任! 也试试outerHTML,不要告诉任何人我让你这样做:p @GGG 也想试试 DOCTYPE,因为它在 之前。我已经尝试过$(string)
(第 2 点)。与outerHTML 一样吗? 无法设置 outerHTML 属性。此操作的目标元素无效。【参考方案2】:
我会建议一个两部分的解决方案,您可以读取 jQuery 不会为您解析的标签,然后将其余部分传递给 jQuery。如果您正在寻找一种纯 javascript 解决方案来解析 HTML 数据结构,那么 jQuery 可能是您最好的选择,因为它具有许多用于操作数据的内置函数。您实际上可以将您的插件构建为 jQuery 插件,可以通过以下方式调用:$.parser 或类似的东西。如果您使用自己的函数扩展 jQuery 来解析数据,您还可以返回一个扩展的 jQuery 对象,该对象包含甚至从标头读取特定数据元素的函数,因为您可以手动解析 ... 信息并将其存储在同一个对象中.
【讨论】:
【参考方案3】:我不知道为什么有人需要这个,但我建议您将源代码直接转储到 iframe 中。浏览器可以为您进行解析。您甚至可以对结果运行 DOM 查询。
【讨论】:
是的,我试过了!但是请参考我们可能需要将 DOM 序列化回字符串的地方。我们如何为 iframe 做到这一点?我们正在为自定义 CMS 制作此功能,其中将通过自定义 HTML cmets 标记可编辑区域。【参考方案4】:由于 HTML 本质上是 XML,您可以使用 jquery parseXML
var dom = $.parseXML(html);
$('title', dom).text("This is a new Title");
编辑:
如果你想把它变成一个字符串,你需要使用 xml 插件,但我找不到它的原始来源,所以在这里:
/**
* jQuery xml plugin
* Converts XML node(s) to string
*
* Copyright (c) 2009 Radim Svoboda
* Dual licensed under the MIT (MIT-LICENSE.txt)
* and GPL (GPL-LICENSE.txt) licenses.
*
* @author Radim Svoboda, user Zzzzzz
* @version 1.0.0
*/
/**
* Converts XML node(s) to string using web-browser features.
* Similar to .html() with HTML nodes
* This method is READ-ONLY.
*
* @param all set to TRUE (1,"all",etc.) process all elements,
* otherwise process content of the first matched element
*
* @return string obtained from XML node(s)
*/
jQuery.fn.xml = function(all)
//result to return
var s = "";
//Anything to process ?
if( this.length )
//"object" with nodes to convert to string
(
( ( typeof all != 'undefined' ) && all ) ?
//all the nodes
this
:
//content of the first matched element
jQuery(this[0]).contents()
)
//convert node(s) to string
.each(function()
s += window.ActiveXObject ?//== IE browser ?
//for IE
this.xml
:
//for other browsers
(new XMLSerializer()).serializeToString(this)
;
);
return s;
;
【讨论】:
这会保留 HTML 文档结构吗?例如 和 标签?jQuery.parseXML()
不是要与 XML 一起使用吗?我们在这里讨论 HTML。它们不兼容。
据我所知是的,但测试取决于您。我已经将它用于类似的场景,到目前为止没有问题:)【参考方案5】:
如果您想要一个不依赖浏览器中现有内容的完整解析器来引导您的解释器,则 dom.js 中的 HTML 解析器是一流的。它的全部目的是解析 html 以在 javascript 托管的 DOM 中使用,因此它必须同时满足 DOM 规范以及在 js 中解析和使用结果的需要,同时不假设除基本 JS 之外的任何现有工具。它甚至可以在 node.js 或 spidermonkey 的 jsshell 或 webworkers 中运行。 https://github.com/andreasgal/dom.js
它也有序列化部分,但要做到这一点,您需要承诺使用的不仅仅是解析器部分。您可以找到独立的序列化程序,尽管它适用于任何类似 DOM 的结构。
【讨论】:
不错,但它是客户端吗?以上是关于DOM 的 JavaScript 解析器的主要内容,如果未能解决你的问题,请参考以下文章