兼容IE、FireFox、Chrome等浏览器的xml处理函数js代码


Posted in Javascript onNovember 30, 2011

在编写处理xml的网页时,经常为浏览器兼容性头疼。于是我将常用的xml操作封装为函数。经过一段时间的改进,现在已经很稳定了,用起来很舒服。

函数有——
xml_loadFile:xml同步/异步加载。
xml_transformNode:xsl转换。
xml_text:节点的文本。
selectSingleNode:根据XPath选择单个节点。
selectNodes:根据XPath选择多个节点。

全部代码(zyllibjs_xml.js)——

/* 
zyllibjs_xml 
XML处理 
@author zyl910 
注意—— 
1. Chrome 由于其安全机制限制, 不能读取本地文件。 
Reference 
~~~~~~~~~ 
http://www.jinlie.net/?p=302 
Chrome浏览器加载XML文档 
Update 
~~~~~~ 
[2011-11-02] 
定义。 
[2011-11-09] 
xml_loadFile: 为回调函数加上isError参数。 
[2011-11-21] 
selectSingleNode 
selectNodes 
*/ 
// 加载XML文件并返回XML文档节点 
// return: 成功时返回一个对象(同步模式下返回xml文档对象,异步模式下返回操作对象),失败时返回空。 
// xmlUrl: xml文件的url。 
// funcAsync: 回调函数. function onload(xmlDoc, isError){ ... } 
function xml_loadFile(xmlUrl, funcAsync) 
{ 
var xmlDoc = null; 
var isChrome = false; 
var asyncIs = (null!=funcAsync); // 是否是异步加载。当funcAsync不为空时,使用异步加载,否则是同步加载。 
// 检查参数 
if (""==xmlUrl) return null; 
if (asyncIs) 
{ 
if ("function"!=typeof(funcAsync)) return null; 
} 
// 创建XML对象 
try 
{ 
xmlDoc = new ActiveXObject("Microsoft.XMLDOM"); // Support IE 
} 
catch(ex) 
{ 
} 
if (null==xmlDoc) 
{ 
try 
{ 
// Support Firefox, Mozilla, Opera, etc 
xmlDoc = document.implementation.createDocument("", "", null); // 创建一个空的 XML 文档对象。 
} 
catch(ex) 
{ 
} 
} 
if (null==xmlDoc) return null; 
// 加载XML文档 
xmlDoc.async = asyncIs; 
if (asyncIs) 
{ 
if(window.ActiveXObject) 
{ 
xmlDoc.onreadystatechange = function(){ 
if(xmlDoc.readyState == 4) 
{ 
var isError = false; 
if (null!=xmlDoc.parseError) 
{ 
isError = (0!=xmlDoc.parseError.errorCode); // 0成功, 非0失败。 
} 
funcAsync(xmlDoc, isError); 
} 
} 
} 
else 
{ 
xmlDoc.onload = function(){ 
funcAsync(xmlDoc, false); 
} 
} 
} 
try 
{ 
xmlDoc.load(xmlUrl); 
} 
catch(ex) 
{ 
// alert(ex.message) // 如果浏览器是Chrome,则会catch这个异常:Object # (a Document) has no method "load" 
isChrome = true; 
xmlDoc = null; 
} 
if (isChrome) 
{ 
var xhr = new XMLHttpRequest(); 
if (asyncIs) // 异步 
{ 
xhr.onreadystatechange = function(){ 
if(xhr.readyState == 4) 
{ 
funcAsync(xhr.responseXML, xhr.status != 200); 
} 
} 
xhr.open("GET", xmlUrl, true); 
try // 异步模式下,由回调函数处理错误。 
{ 
xhr.send(null); 
} 
catch(ex) 
{ 
funcAsync(null, true); 
return null; 
} 
return xhr; // 注意:返回的是XMLHttpRequest。建议异步模式下仅用null测试返回值。 
} 
else // 同步 
{ 
xhr.open("GET", xmlUrl, false); 
xhr.send(null); // 同步模式下,由调用者处理异常 
xmlDoc = xhr.responseXML; 
} 
} 
return xmlDoc; 
} 
// 使用XSLT把XML文档转换为一个字符串。 
function xml_transformNode(xmlDoc, xslDoc) 
{ 
if (null==xmlDoc) return ""; 
if (null==xslDoc) return ""; 
if (window.ActiveXObject) // IE 
{ 
return xmlDoc.transformNode(xslDoc); 
} 
else // FireFox, Chrome 
{ 
//定义XSLTProcesor对象 
var xsltProcessor=new XSLTProcessor(); 
xsltProcessor.importStylesheet(xslDoc); 
// transformToDocument方式 
var result=xsltProcessor.transformToDocument(xmlDoc); 
var xmls=new XMLSerializer(); 
var rt = xmls.serializeToString(result); 
return rt; 
} 
} 
// 得到节点的文本 
function xml_text(xmlNode) 
{ 
if (null==xmlNode) return ""; 
var rt; 
if (window.ActiveXObject) // IE 
{ 
rt = xmlNode.text; 
} 
else 
{ 
// FireFox, Chrome, ... 
rt = xmlNode.textContent; 
} 
if (null==rt) rt=xmlNode.nodeValue; // XML DOM 
return rt; 
} 
// 添加方法。为了兼容FireFox、Chrome。 
if (!window.ActiveXObject) 
{ 
XMLDocument.prototype.selectSingleNode = Element.prototype.selectSingleNode = function (xpath) 
{ 
var x = this.selectNodes(xpath) 
if ( ! x || x.length < 1 ) return null ; 
return x[ 0 ]; 
} 
XMLDocument.prototype.selectNodes = Element.prototype.selectNodes = function (xpath) 
{ 
var xpe = new XPathEvaluator(); 
var nsResolver = xpe.createNSResolver( this.ownerDocument == null?this.documentElement : this.ownerDocument.documentElement); 
var result = xpe.evaluate(xpath, this , nsResolver, 0 , null ); 
var found = []; 
var res; 
while (res = result.iterateNext()) 
found.push(res); 
return found; 
} 
}

Chrome浏览器加载XML文档
Chrome浏览器不支持load方法加载XML文档。网上找了下,需要如下解决:
function loadXMLDoc(xml_name) 
{ 
var xmlDoc; 
try 
{ 
xmlDoc = new ActiveXObject("Microsoft.XMLDOM"); // Support IE 
} 
catch(e) 
{ 
try 
{ 
// Support Firefox, Mozilla, Opera, etc 
xmlDoc = document.implementation.createDocument("", "", null) ;// 创建一个空的 XML 文档对象。 
} 
catch(e) 
{ 
alert(e.message); 
} 
} 
// 加载XML文档 
try 
{ 
xmlDoc.async = false; // 关闭异步加载 
xmlDoc.load(xml_name); 
} 
catch(e) 
{ 
// alert(e.message) 如果浏览器是Chrome,则会catch这个异常:Object # (a Document) has no method "load",所以,以下实现支持chrome加载XML文档(只是粗略的写下) 
var xhr = new XMLHttpRequest(); 
xhr.open("GET", xml_name, false); 
xhr.send(null); 
xmlDoc = xhr.responseXML.documentElement; 
} 
return xmlDoc; 
}

BTW,各浏览器加载XML字符串也不同。
IE使用 loadXML() 方法来解析 XML 字符串:
xmlDoc.loadXML(xml_str);

FireFox等使用DOMParser 对象解析XML字符串:
var parseXml = new DOMParser(); 
var doc = parseXml.parseFromString(xml_str,"text/xml");
Javascript 相关文章推荐
用js实现下载远程文件并保存在本地的脚本
May 06 Javascript
javascript 兼容各个浏览器的事件
Feb 04 Javascript
基于javascript的异步编程实例详解
Apr 10 Javascript
AngularJS读取JSON及XML文件的方法示例
May 25 Javascript
Angularjs 双向绑定时字符串的转换成数字类型的问题
Jun 12 Javascript
JS声明对象时属性名加引号与不加引号的问题及解决方法
Feb 16 Javascript
总结js函数相关知识点
Feb 27 Javascript
Vue2.0系列之过滤器的使用
Mar 01 Javascript
Vue使用json-server进行后端数据模拟功能
Apr 17 Javascript
微信小程序之事件交互操作实例分析
Dec 03 Javascript
微信小程序实现获取小程序码和二维码java接口开发
Mar 29 Javascript
Taro UI框架开发小程序实现左滑喜欢右滑不喜欢效果的示例代码
May 18 Javascript
Javascript的getYear、getFullYear、getUTCFullYear异同分享
Nov 30 #Javascript
chrome原生方法之数组
Nov 30 #Javascript
使用Javascript接收get传递的值的代码
Nov 30 #Javascript
关于递归运算的顺序测试代码
Nov 30 #Javascript
对javascript的一点点认识总结《javascript高级程序设计》读书笔记
Nov 30 #Javascript
Jquery插件之打造自定义的select标签
Nov 30 #Javascript
jquery中dom操作和事件的实例学习 仿yahoo邮箱登录框的提示效果
Nov 30 #Javascript
You might like
php实现猴子选大王问题算法实例
2015/04/20 PHP
php基础设计模式大全(注册树模式、工厂模式、单列模式)
2015/08/31 PHP
thinkphp跨库操作的简单代码实例
2016/09/22 PHP
php+redis在实际项目中HTTP 500: Internal Server Error故障排除
2017/02/05 PHP
javascript 客户端验证上传图片的大小(兼容IE和火狐)
2009/08/15 Javascript
JS获取节点的兄弟,父级,子级元素的方法
2014/01/09 Javascript
node.js中watch机制详解
2014/11/17 Javascript
jQuery实现伪分页的方法分享
2016/02/17 Javascript
JavaScript如何实现组合列表框中元素移动效果
2016/03/01 Javascript
js canvas实现5张图片合成一张图片
2019/07/15 Javascript
微信小程序事件 bindtap bindinput代码实例
2019/08/26 Javascript
ES6如何用一句代码实现函数的柯里化
2020/01/18 Javascript
[01:49]一目了然!DOTA2DotA快捷操作对比第二弹
2014/05/16 DOTA
在Python的gevent框架下执行异步的Solr查询的教程
2015/04/16 Python
python创建列表并给列表赋初始值的方法
2015/07/28 Python
Python3利用SMTP协议发送E-mail电子邮件的方法
2017/09/30 Python
python实现按长宽比缩放图片
2018/06/07 Python
python 拼接文件路径的方法
2018/10/23 Python
Python3爬取英雄联盟英雄皮肤大图实例代码
2018/11/14 Python
Python常用的json标准库
2019/02/19 Python
Python实现一个数组除以一个数的例子
2019/07/20 Python
Python模块future用法原理详解
2020/01/20 Python
日本最新流行服饰网购:Nissen
2016/07/24 全球购物
如何在发生故障的节点上重新安装 SQL Server
2013/03/14 面试题
《金孔雀轻轻跳》教学反思
2014/04/20 职场文书
《明天,我们毕业》教学反思
2014/04/24 职场文书
另类冲刺标语
2014/06/24 职场文书
租房安全协议书
2014/08/20 职场文书
交警正风肃纪剖析材料
2014/10/29 职场文书
离婚协议书样本
2015/01/26 职场文书
前台接待岗位职责
2015/02/03 职场文书
春秋淹城导游词
2015/02/11 职场文书
摩登时代观后感
2015/06/03 职场文书
《称赞》教学反思
2016/02/17 职场文书
Golang 正则匹配效率详解
2021/04/25 Golang
MySQL 原理与优化之原数据锁的应用
2022/08/14 MySQL