Ember.js ember-data restadapter无法加载json

xam*_*rax 11 javascript json ember.js ember-data

干杯! 我有ember-data商店:

TravelClient.Store = DS.Store.extend({
  revision: 11,
  adapter: DS.RESTAdapter.create({ bulkCommit: false, url: "http://someIP:somePORT"})
});
Run Code Online (Sandbox Code Playgroud)

和路由器:

TravelClient.ToursRoute = Ember.Route.extend({
  model: function() {
    return TravelClient.Tour.find();
  }
});
Run Code Online (Sandbox Code Playgroud)

我从远程服务器接收这个JSON:

{
  "tours": [
    {
      "id": "5110e8b5a8fefe71e0000197",
      "title": "qui deserunt dolores",
      "description": "Id velit nihil.",
      "seats": 12,
      "options": [

      ],
      "images": [
        {
          "id": "5110e8b5a8fefe71e0000196",
          "url": "url"
        }
}
Run Code Online (Sandbox Code Playgroud)

但是当我尝试return TravelClient.Tour.find()失败的时候:

http://someIP:somePORT/tours 404 (Not Found)

XMLHttpRequest cannot load http://someIP:somePORT/tours. Origin http://localhost:3000 is not allowed by Access-Control-Allow-Origin.
Run Code Online (Sandbox Code Playgroud)

看起来RESTAdapter似乎不知道它必须接收JSON还是什么?

更新:

在rails服务器端的应用程序控制器中:

def set_access_control_headers
  headers['Access-Control-Allow-Origin'] = '*'
  headers['Access-Control-Request-Method'] = '*'
end
Run Code Online (Sandbox Code Playgroud)

但它仍然是:

OPTIONS http://someIP:somePORT/tours 404 (Not Found)
Run Code Online (Sandbox Code Playgroud)

看起来RESTAdapter试图加载tour资源,而不是tours.json:

Request URL:http://someIP:somePORT/tours
Run Code Online (Sandbox Code Playgroud)

工作解决方案

扩展RESTAdapter:

TravelClient.CUSTOMAdapter = DS.RESTAdapter.extend({
  bulkCommit: false, 
  url: "http://remote_server_address",    
  buildURL: function(record, suffix) {
    var s = this._super(record, suffix);
    return s + ".json";
  }
})
Run Code Online (Sandbox Code Playgroud)

并使用正确的标头响应OPTIONS请求

alb*_*jan 10

RESTAdapter预计JSON认为是没有问题的,但页面和JSON不在同一个域中,这是一个安全问题.您可以使用以下两种解决方案之一解决此问题.

您正在使用您应该使用的原始政策JSONPCORS.最快的修复方法可能是告诉你要使用的ember-data JSONP.

对于CORS您的服务器需要OPTIONS使用标头响应请求:

  • Access-Control-Allow-Origin
  • Access-Control-Request-Method

我不是专家,但你可能需要在这里这里rack-cors一下宝石.

你可以通过覆盖类似的ajax钩子来做到这RESTAdapter一点:

App.store = DS.Store.create({
    revision: 11,
    adapter: DS.RESTAdapter.create({
        namespace: "data",
        url: "",
        ajax: function (url, type, hash) {
            hash.url = url;
            hash.type = type;
            hash.dataType = 'jsonp';
            hash.contentType = 'application/json; charset=utf-8';
            hash.context = this;

            if (hash.data && type !== 'GET') {
                hash.data = JSON.stringify(hash.data);
            }

            jQuery.ajax(hash);
        },
    })
});
Run Code Online (Sandbox Code Playgroud)