提出AJAX请求和处理响应时,我一直遇到一些奇怪的问题。
我正在为XML文件进行ajax调用。但是,当我得到响应时,xhr.responseText属性在Firefox中可以正常工作,而在IE中则不能。另一件事是,我试图以XMLDocument的形式访问xhr.responseXML,但是在firefox中它告诉我xhr.responseXML是未定义的,即它甚至不会显示未定义的错误或显示输出。
这是我用来发出请求的代码:
var ajaxReq = function(url, callback) { //initialize the xhr object and settings var xhr = window.ActiveXObject ? new ActiveXObject("Microsoft.XMLHTTP") : new XMLHttpRequest(), //set the successful connection function httpSuccess = function(xhr) { try { // IE error sometimes returns 1223 when it should be 204 // so treat it as success, see XMLHTTPRequest #1450 // this code is taken from the jQuery library with some modification. return !xhr.status && xhr.status == 0 || (xhr.status >= 200 && xhr.status < 300) || xhr.status == 304 || xhr.status == 1223; } catch (e) { } return false; }; //making sure the request is created if (!xhr) { return 404; // Not Found } //setting the function that is going to be called after the request is made xhr.onreadystatechange = function() { if (!httpSuccess(xhr)) { return 503; //Service Unavailable } if (xhr.responseXML != null && xhr.responseText != null && xhr.responseXML != undefined && xhr.responseText != undefined) { callback(xhr); } }; //open request call xhr.open('GET', url, true); //setup the headers try { xhr.setRequestHeader("Content-Type", "application/x-www-form-urlencoded"); xhr.setRequestHeader("Accept", "text/xml, application/xml, text/plain"); } catch ( ex ) { window.alert('error' + ex.toString()); } //send the request try { xhr.send(''); } catch (e) { return 400; //bad request } return xhr; };
这就是我调用函数以测试结果的方式:
window.onload = function() { ajaxReq('ConferenceRoomSchedules.xml', function(xhr) { //in firefox this line works fine, //but in ie it doesnt not even showing an error window.document.getElementById('schedule').innerHTML = xhr.responseText; //firefox says ''xhr.responseXML is undefined'. //and ie doesn't even show error or even alerts it. window.alert(xhr.reponseXML.documentElement.nodeName); }); }
这也是我第一次尝试使用AJAX,因此可能有些我看错了。我一直在疯狂地寻找为什么或如何修复它的任何迹象,但是没有运气。任何想法都会很棒。
编辑:
我知道使用框架会更好,但是老板不想为ajax功能添加框架(“对于ajax:P而言,’只是’不公平”)。所以我用纯JavaScript来做。
XML文件格式正确,我在Web浏览器中看到的很好,但是为了完整起见,这是我正在使用的测试文件:
<?xml version="1.0" encoding="utf-8"?> <rooms> <room id="Blue_Room"> <administrator>somebody@department</administrator> <schedule> <event> <requester> <name>Johnny Bravo</name> <email>jbravo@department</email> </requester> <date>2009/09/03</date> <start_time>11:00:00 GMT-0600</start_time> <end_time>12:00:00 GMT-0600</end_time> </event> </schedule> </room> <room id="Red_Room"> <administrator>somebody@department</administrator> <schedule> </schedule> </room> <room id="Yellow_Room"> <administrator>somebody@department</administrator> <schedule> </schedule> </room> </rooms>
编辑2: 好消息是我说服老板使用jQuery,坏消息是AJAX仍然困扰我。我会出于好奇而阅读更多有关它的内容。感谢您的提示,我将答案归功于Heat Miser,因为他是最接近的工作提示。
几年前我遇到了同样的问题,然后我放弃了responseXML并开始始终使用responseText。这个解析函数一直对我有用:
function parseXml(xmlText){ try{ var text = xmlText; //text = replaceAll(text,"<","<"); //text = replaceAll(text,">",">"); //text = replaceAll(text,""","\""); //alert(text); //var myWin = window.open('','win','resize=yes,scrollbars=yes'); //myWin.document.getElementsByTagName('body')[0].innerHTML = text; if (typeof DOMParser != "undefined") { // Mozilla, Firefox, and related browsers var parser=new DOMParser(); var doc=parser.parseFromString(text,"text/xml"); //alert(text); return doc; }else if (typeof ActiveXObject != "undefined") { // Internet Explorer. var doc = new ActiveXObject("Microsoft.XMLDOM"); // Create an empty document doc.loadXML(text); // Parse text into it return doc; // Return it }else{ // As a last resort, try loading the document from a data: URL // This is supposed to work in Safari. Thanks to Manos Batsis and // his Sarissa library (sarissa.sourceforge.net) for this technique. var url = "data:text/xml;charset=utf-8," + encodeURIComponent(text); var request = new XMLHttpRequest(); request.open("GET", url, false); request.send(null); return request.responseXML; } }catch(err){ alert("There was a problem parsing the xml:\n" + err.message); } }
使用此XMLHttpRequest对象:
// The XMLHttpRequest class object debug = false; function Request (url,oFunction,type) { this.funct = ""; // this.req = ""; this.url = url; this.oFunction = oFunction; this.type = type; this.doXmlhttp = doXmlhttp; this.loadXMLDoc = loadXMLDoc; } function doXmlhttp() { //var funct = ""; if (this.type == 'text') { this.funct = this.oFunction + '(req.responseText)'; } else { this.funct = this.oFunction + '(req.responseXML)'; } this.loadXMLDoc(); return false; } function loadXMLDoc() { //alert(url); var functionA = this.funct; var req; req = false; function processReqChange() { // alert('reqChange is being called'); // only if req shows "loaded" if (req.readyState == 4) { // only if "OK" if (req.status == 200) { // ...processing statements go here... eval(functionA); if(debug){ var debugWin = window.open('','aWindow','width=600,height=600,scrollbars=yes'); debugWin.document.body.innerHTML = req.responseText; } } else { alert("There was a problem retrieving the data:\n" + req.statusText + '\nstatus: ' + req.status); if(debug){ var debugWin = window.open('','aWindow','width=600,height=600,scrollbars=yes'); debugWin.document.body.innerHTML = req.responseText; } } } } // branch for native XMLHttpRequest object if(window.XMLHttpRequest) { try { req = new XMLHttpRequest(); } catch(e) { req = false; } // branch for IE/Windows ActiveX version } else if(window.ActiveXObject) { try { req = new ActiveXObject("Msxml2.XMLHTTP"); } catch(e) { try { req = new ActiveXObject("Microsoft.XMLHTTP"); } catch(e) { req = false; } } } if(req) { req.onreadystatechange = processReqChange; if(this.url.length > 2000){ var urlSpl = this.url.split('?'); req.open("POST",urlSpl[0],true); req.setRequestHeader('Content-Type','application/x-www-form-urlencoded'); req.send(urlSpl[1]); } else { req.open("GET", this.url, true); req.send(""); } } } function browserSniffer(){ if(navigator.userAgent.toLowerCase().indexOf("msie") != -1){ if(navigator.userAgent.toLowerCase().indexOf("6")){ return 8; }else{ return 1; } } if(navigator.userAgent.toLowerCase().indexOf("firefox") != -1){ return 2; } if(navigator.userAgent.toLowerCase().indexOf("opera") != -1){ return 3; } if(navigator.userAgent.toLowerCase().indexOf("safari") != -1){ return 4; } return 5; }
当然,这是很旧的代码,但是它在我几年前建立的网站上仍然对我有用。尽管现在我通常使用框架,但我与其他所有人都同意,因此我不再需要使用此代码或类似的代码。
您可以使用Request onreadystate函数中的split等忽略某些细节。如果请求的长度大于某个长度,应该将其转换为帖子,但是我只是认为做一个帖子总是更好。