JavaScript高级程序设计 阅读笔记(二十一) JavaScript中的XML


Posted in Javascript onSeptember 14, 2012

一、IE中的XML DOM支持

IE对XML的支持是基于ActiveX的MSXML库。

1、DOM创建

对每个新版本的MSXML,都会创建出不同的XML DOM对象,所以尽量选择新的XML DOM版本。

2、载入XML

载入XML分两种,即:

载入XML字符串:loadXML(xml字符串)

载入xml文件:load(xml文件路径)。默认情况下文件载入是异步的,如果要改为同步把asynce特性改为true即可。异步载入文件时要用到readyState和onreadystatechange事件处理函数。readyState共有五种可能的值:

0——DOM尚未初始化任何信息;

1——DOM正在载入数据;

2——DOM完成了数据载入;

3——DOM已经可用,不过某些部分可能还不能用;

4——DOM已经完全被载入,可以使用了。

3、获取XML

微软为每个节点增加了xml特性,所以获取XML非常方便,见后面的示例。

4、解释错误

可以用parseError来处理XML载入过程中出现的错误。

parseError特性实际上是包含以下特性的对象:

errorCode:错误类型数字代码,没有错误为0

filePos:错误发生在文件中的位置

line:遇到错误的行号

linepos:在遇到错误的那一行上的字符的位置

reason:对错误的一个解释

srcText:造成错误的代码

url:造成错误的文件的URL

5、示例:

function createXMLDOM(){ 
var arrSignatures=["MSXML2.DOMDocument.5.0","MSXML2.DOMDocument.4.0","MSXML2.DOMDocument.3.0","MSXML2.DOMDocument","Microsoft.XmlDom"]; 
for(var i=0;i<arrSignatures.length;i++){ 
try{ 
var oXmlDom=new ActiveXObject(arrSignatures[i]); 
return oXmlDom; 
} catch(oError){ 
} 
} 
throw new Error("MSXML is not installed on your system"); 
} 
var oXmlDom=createXMLDOM(); 
//方式一:加载字符串 
oXmlDom.loadXML("<root><child/></rot>"); 
//处理错误 
if(oXmlDom.parseError != 0){ 
var oError=oXmlDom.parseError; 
alert("An Error occurred:\nError Code:" + oError.errorCode 
+ "\nLine:" + oError.line + "\nLine Pos:" + oError.linepos 
+ "\nReason:" + oError.reason); 
} else { 
var childNodes=oXmlDom.documentElement.childNodes; 
console.log(childNodes.length+" "+childNodes[0].xml);// 1 <child/> 
} 
//方式二:加载XML文件 
oXmlDom.onreadystatechange = function(){ 
//文档加载完毕 
if(oXmlDom.readyState == 4){ 
if(oXmlDom.parseError != 0){ 
var oError=oXmlDom.parseError; 
alert("An Error occurred:\nError Code:" + oError.errorCode 
+ "\nLine:" + oError.line + "\nLine Pos:" + oError.linepos 
+ "\nReason:" + oError.reason); 
} else { 
var childNodes=oXmlDom.documentElement.childNodes; 
console.log(childNodes.length+" "+childNodes[0].xml);// 1 <child/> 
} 
} 
} 
oXmlDom.load("test.xml");

二、Mozilla中的XML DOM支持

1、创建DOM

DOM标准指出,document.implementation有个 createDocument() 方法:
var oXmlDom=document.implementation.createDocument("","",null);

其中,第一个参数为文档的命名空间URL,文档元素的标签名,和文档类型对象(总是为null,因为在Mozilla中还没有支持)。

2、载入XML

Mozilla只支持一个载入XML的方法:load(文件名)。

同步或异步由async决定,默认为异步。

如果是XML字符串,要用DOMParser对象来转换成DOM,用法如下:

var oParser = new DOMParser(); 
var oXmlDom = oParser.parseFromString("<root/>","text/xml");

 parseFromString方法第一个参数为XML字符串,第二个参数为内容类型。可以是 "text/xml" 或 "application/xml"。

3、获取XML

微软提供的xml特性因为不是标准,所以Mozilla不支持,Mozilla提供了XMLSerializer对象:

var oSerializer = new XMLSerializer(); 
var sXml = oSerializer.serializeToString(oXmlDom,"text/xml");在后面的例子中我们可以看到如何用defineGetter()方法来定义一个xml特性。

4、解析错误

在XML文件的解析过程中发生错误时,XML DOM会创建文档来解释这个错误。常常用正则来输出错误信息:

var reError = />([\s\S]*?)Location:([\s\S]*?)Line Number (\d+),Column (\d+):<sourcetext>([\s\S]*?)(?:\-*\^)/; 
if(oXmlDom.documentElement.tagName == "parsererror"){ 
reError.test(oXmlDom.xml); 
alert("An error occurred:\nDescription: " + RegExp.$1 +"\n" 
+ "File: " + RegExp.$2 + "\n" 
+ "Line: " + RegExp.$3 + "\n" 
+ "Line Pos: " + RegExp.$4 + "\n" 
+ "Source: " + RegExp.$5); 
}

5、示例
var oXmlDom=document.implementation.createDocument("","<root>",null); 
oXmlDom.async = false; 
oXmlDom.onload = function(){ 
alert('Done'); 
} 
var reError = />([\s\S]*?)Location:([\s\S]*?)Line Number (\d+),Column (\d+):<sourcetext>([\s\S]*?)(?:\-*\^)/; 
if(oXmlDom.documentElement.tagName == "parsererror"){ 
reError.test(oXmlDom.xml); 
alert("An error occurred:\nDescription: " + RegExp.$1 +"\n" 
+ "File: " + RegExp.$2 + "\n" 
+ "Line: " + RegExp.$3 + "\n" 
+ "Line Pos: " + RegExp.$4 + "\n" 
+ "Source: " + RegExp.$5); 
} 
Node.prototype.__defineGetter__("xml", function () { 
var oSerializer = new XMLSerializer(); 
return oSerializer.serializeToString(this, "text/xml"); 
}); 
oXmlDom.load('test.xml'); 
alert(oXmldom.xml); 
var oNode = oXmlDom.documentElement.childNodes[1]; 
alert(oNode.xml);

三、通用接口

下面是兼容IE和FireFox的通用接口:

function XmlDom() { 
if (window.ActiveXObject) {//IE 
var arrSignatures = ["MSXML2.DOMDocument.5.0", "MSXML2.DOMDocument.4.0", 
"MSXML2.DOMDocument.3.0", "MSXML2.DOMDocument", "Microsoft.XmlDom"]; 
for (var i = 0; i < arrSignatures.length; i++) { 
try { 
var oXmlDom = new ActiveXObject(arrSignatures[i]); 
return oXmlDom; 
} 
catch (oError) { 
//ignore 
} 
} 
throw new Error("MSXML is not installed on your system."); 
} else if (document.implementation && document.implementation.createDocument) { 
var oXmlDom = document.implementation.createDocument("", "", null); 
oXmlDom.parseError = {valueOf:function () { 
return this.errorCode; 
}, toString:function () { 
return this.errorCode.toString(); 
}}; 
oXmlDom.__initError__(); 
oXmlDom.addEventListener("load", function () { 
this.__checkForErrors__(); 
this.__changeReadyState__(4); 
}, false); 
return oXmlDom; 
} else { 
throw new Error("Your browser doesn't support an XML DOM object."); 
} 
} 
if (isMoz) { 
Document.prototype._readyState_ = 0; 
Document.prototype.onreadystatechange = null; 
Document.prototype.__changeReadyState__ = function (iReadyState) { 
this._readyState_ = iReadyState; 
if (typeof this.onreadystatechange == "function") { 
this.onreadystatechange(); 
} 
}; 
Document.prototype.__initError__ = function () { 
this.parseError.errorCode = 0; 
this.parseError.filepos = -1; 
this.parseError.line = -1; 
this.parseError.linepos = -1; 
this.parseError.reason = null; 
this.parseError.srcText = null; 
this.parseError.url = null; 
}; 
Document.prototype.__checkForErrors__ = function () { 
if (this.documentElement.tagName == "parsererror") { 
var reError = />([\s\S]*?)Location:([\s\S]*?)Line Number (\d+),Column (\d+):<sourcetext>([\s\S]*?)(?:\-*\^)/; 
reError.test(this.xml); 
this.parseError.errorCode = -999999; 
this.parseError.reason = RegExp.$1; 
this.parseError.url = RegExp.$2; 
this.parseError.line = parseInt(RegExp.$3); 
this.parseError.linepos = parseInt(RegExp.$4); 
this.parseError.srcText = RegExp.$5; 
} 
}; 
Document.prototype.loadXML = function (sXml) { 
this.__initError__(); 
this.__changeReadyState__(1); 
var oParser = new DOMParser(); 
var oXmlDom = oParser.parseFromString(sXml, "text/xml"); 
while (this.firstChild) { 
this.removeChild(this.firstChild); 
} 
for (var i = 0; i < oXmlDom.childNodes.length; i++) { 
var oNewNode = this.importNode(oXmlDom.childNodes[i], true); 
this.appendChild(oNewNode); 
} 
this.__checkForErrors__(); 
this.__changeReadyState__(4); 
}; 
Document.prototype.__load__ = Document.prototype.load; 
Document.prototype.load = function (sURL) { 
this.__initError__(); 
this.__changeReadyState__(1); 
this.__load__(sURL); 
}; 
Document.prototype.getReadyState = function () { 
return this._readyState_; 
}; 
Node.prototype.__defineGetter__("xml", function () { 
var oSerializer = new XMLSerializer(); 
return oSerializer.serializeToString(this, "text/xml"); 
}); 
}

四、其他浏览器

本书中没有讲到其他浏览器,如现在很火的Chrome,最新版的主流浏览器现在都已支持上面讲到的Mozilla方式。如果不支持,可以用AJAX来读取处理XML。
作者:Artwl
出处:http://artwl.cnblogs.com

Javascript 相关文章推荐
学习YUI.Ext 第四天--对话框Dialog的使用
Mar 10 Javascript
JavaScript OOP类与继承
Nov 15 Javascript
jquery实现漂浮在网页右侧的qq在线客服插件示例
May 13 Javascript
基于jquery和svg实现超炫酷的动画特效
Dec 09 Javascript
微信中一些常用的js方法汇总
Mar 12 Javascript
jquery彩色投票进度条简单实例演示
Jul 23 Javascript
JavaScript数组合并的多种方法
May 22 Javascript
Vue.js组件tree实现无限级树形菜单
Dec 02 Javascript
js实现淡入淡出轮播切换功能
Jan 13 Javascript
浅谈angular2路由预加载策略
Oct 04 Javascript
使用vue的v-for生成table并给table加上序号的实例代码
Oct 27 Javascript
JS前端监控采集用户行为的N种姿势
Jul 23 Javascript
IE6-IE9不支持table.innerHTML的解决方法分享
Sep 14 #Javascript
javascript时区函数介绍
Sep 14 #Javascript
推荐40个简单的 jQuery 导航插件和教程(下篇)
Sep 14 #Javascript
推荐40款强大的 jQuery 导航插件和教程(上篇)
Sep 14 #Javascript
基于JQuery的一句话搞定手风琴菜单
Sep 14 #Javascript
JQuery select控件的相关操作实现代码
Sep 14 #Javascript
11个用于提高排版水平的基于jquery的文字效果插件
Sep 14 #Javascript
You might like
PHP+MYSQL的文章管理系统(一)
2006/10/09 PHP
PHP 开发工具
2006/12/06 PHP
phpmailer绑定邮箱的实现方法
2016/12/01 PHP
4种Windows系统下Laravel框架的开发环境安装及部署方法详解
2020/04/06 PHP
jquery.cookie.js 操作cookie实现记住密码功能的实现代码
2011/04/27 Javascript
js DOM的学习笔记
2011/12/22 Javascript
一个通过script自定义属性传递配置参数的方法
2014/09/15 Javascript
JS中FRAME的操作问题实例分析
2014/10/21 Javascript
jQuery实现企业网站横幅焦点图切换功能实例
2015/04/30 Javascript
jQuery中closest和parents的区别分析
2015/05/07 Javascript
jQuery实现径向动画菜单效果
2015/07/17 Javascript
jQuery中on绑定事件后引发的事件冒泡问题如何解决
2016/05/25 Javascript
JS遍历ul下的li点击弹出li的索引的实现方法
2016/09/19 Javascript
vue 组件高级用法实例详解
2018/04/11 Javascript
详解用场景去理解函数柯里化(入门篇)
2019/04/11 Javascript
jQuery创建折叠式菜单
2019/06/15 jQuery
深入理解Vue keep-alive及实践总结
2019/08/21 Javascript
详解JavaScript中的链式调用
2020/11/27 Javascript
一则python3的简单爬虫代码
2014/05/26 Python
Python 抓取动态网页内容方案详解
2014/12/25 Python
初学Python函数的笔记整理
2015/04/07 Python
Django框架中数据的连锁查询和限制返回数据的方法
2015/07/17 Python
python 队列详解及实例代码
2016/10/18 Python
python3解析库lxml的安装与基本使用
2018/06/27 Python
NumPy统计函数的实现方法
2020/01/21 Python
利用PyQt中的QThread类实现多线程
2020/02/18 Python
python中def是做什么的
2020/06/10 Python
利用CSS3的border-radius绘制太极及爱心图案示例
2016/05/17 HTML / CSS
澳大利亚正品化妆品之家:Cosmetic Capital
2017/07/03 全球购物
草莓网化妆品澳大利亚站:Strawberrynet AU
2017/12/18 全球购物
农业资源与环境专业自荐信范文
2013/12/30 职场文书
房地产项目策划书
2014/02/05 职场文书
运动会演讲稿200字
2014/08/25 职场文书
工会积极分子个人总结
2015/03/03 职场文书
和谐拯救危机观后感
2015/06/15 职场文书
如何利用opencv判断两张图片是否相同详解
2021/07/07 Python