使用Phonegap在iOS模拟器中不执行跨域ajax请求

时间:2014-05-15 23:06:51

标签: jquery ajax cordova cross-domain

我一开始就开始使用Phonegap和移动开发,而且当我从中运行时,我很难尝试拨打$ .ajax(...)来做任何事情 iOS模拟器或iOS设备 - 但是我的小应用程序在从浏览器或Ripple模拟器(http://ripple.incubator.apache.org/)运行时都能正常工作。

此外,我已经熟悉了CORS,我的测试似乎表明我的请求/响应标头已正确设置,可用于跨域客户端 - 服务器通信。使用Safari WebInspector的JS调试器逐步执行(并监视我的服务器的Apache日志),我已经能够确定对xhr.send()的调用从未实际执行过。

一旦我意识到这一点,我就从等式中删除了jQuery,以防我不正确地设置$ .ajax()请求,并且我使用下面的代码创建了CORS请求(从这里获得:{{3} })

在这两种情况下(使用和不使用jQuery),我在调试器中注意到在调用xhr.open(...)之后,xhr.status和xhr.statusText的值都设置为& #34; [异常:DOMException]",我假设是阻止xhr.send()执行的。

另外,我的config.xml包含以下行:

<access origin="*" />

这是创建和执行请求的代码:

// Create the XHR object.
function createCORSRequest(method, url) {
  var xhr = new XMLHttpRequest();
  if ("withCredentials" in xhr) {
    // XHR for Chrome/Firefox/Opera/Safari.
    xhr.open(method, url, true);
  } else if (typeof XDomainRequest != "undefined") {
    // XDomainRequest for IE.
    xhr = new XDomainRequest();
    xhr.open(method, url);
  } else {
    // CORS not supported.
    xhr = null;
  }
  return xhr;
}

// Helper method to parse the title tag from the response.
function getTitle(text) {
  return text.match('<title>(.*)?</title>')[1];
}

// Make the actual CORS request.
function makeCorsRequest() {
  // All HTML5 Rocks properties support CORS.
  var url = 'http://server.mylocalhost/api/action?arg1=foo';

  var xhr = createCORSRequest('GET', url);
  if (!xhr) {
    alert('CORS not supported');
    return;
  }

  // Response handlers.
  xhr.onload = function() {
    var text = xhr.responseText;
    var title = getTitle(text);
    alert('Response from CORS request to ' + url + ': ' + title);
  };

  xhr.onerror = function() {
    alert('Whoops, there was an error making the request.');
  };

  xhr.send();
}

注意:上面在makeCorsRequest()中指定的url反映了我在我的应用程序中定位的网址的实际结构。

我的设置:

我觉得我必须遗漏一些非常基本的东西...任何想法?

另外,我不想使用JSONP。

1 个答案:

答案 0 :(得分:1)

这结果是网络(DNS)层的问题。事实证明,Xcode iOS模拟器忽略了主机的/ etc / hosts文件,并且似乎不是在模拟器环境中控制DNS的等效方式。所以,据我所知,使用基于名称的虚拟主机在本地开发机器上开发是不可能的......这似乎是一个非常荒谬的限制。

由于iOS模拟器显然 知道如何找到&#34; localhost&#34;,我通过将以下行添加到我的目标虚拟主机的VirtualHost容器来修复我的问题API端点(在相应的Apache conf文件中):

ServerAlias localhost

然后我将makeCorsRequest()中的url更改为以下形式:

var url = 'http://localhost/api/action?arg1=foo';

在基于jQuery的代码版本中进行类似的更改也很有效。

可能有其他/更好的方法可以解决这个令人伤心的限制,但是现在这个修复程序让我可以回到实际关注我的应用程序。