7.12 Models -- Frequently Asked Questions

1、Should I use a query or a filter to seach records?我應該使用一個查詢或者過濾器來搜索記錄嗎?html

 這取決於你想要搜索多少reocrds而且它們是否被加載到store中了。html5

1. Queriesweb

(1) Queries對於搜索數百,數千,或者甚至百萬的記錄是有用的。你僅僅把搜索選項交給你的服務器,而且它負責把匹配的records列表交還給你。由於來自服務器的響應包含全部匹配的records的ID,這並不重要,若是store沒有提早加載它們;它認爲它們不在緩存中而且若是必要的話能夠經過ID請求record。api

(2) Queries的缺點是它們不是實時更新的,它們比較慢,而且它們要求你的服務器支持你但願執行的查詢類型。數組

(3) 由於是服務器決定哪些records匹配這個查詢,而不是store,Queries不實時更新。若是你但願更新它們,你必須手動調用reload()方法而且等待服務器響應。若是你在客戶端建立了一個新的record,它將不會顯示在結果中直到你存儲這條新的record到服務器而且從新加載查詢結果。緩存

(4) 由於store必須與你的服務器協商來決定一個查詢的結果,它須要一個網絡請求。這對用戶來講很慢,特別是若是他們是在一個很慢的鏈接上或者你的服務器響應很慢。當必須諮詢服務器時,JS Web應用程序的典型速度能夠提升遲鈍的感受。服務器

(5) 最後,執行查詢要求store和服務期間協做。默認的,Ember Data將會發送search options,你把它們做爲HTTP請求體傳遞到你的服務器。若是你的服務器不支持這種格式的請求,你要麼須要更改你的服務器,要麼經過建立自定義的適配器來自定義查詢如何被髮送。websocket

2. Filter網絡

(1) 過濾器,在另外一方面,是在store的緩存中執行一個關於全部records的實時搜索。一旦一條新的record被加載進store,這個filter將會檢查這條record是否匹配,若是匹配,就把它添加進搜索結果的數組中。若是這個數組被展示在一個模板中,模板會自動更新。app

(2) 過濾器還考慮到新建立的而且沒有被保存進store的records,而且records已經被修改可是沒有被保存。若是你但願records顯示在搜索結果中一旦它們在客戶端被建立或者被修改,你應該使用一個過濾器。

(3) 切記若是store不知道它們,records不會顯示在一個過濾器中。你能夠經過使用store的push()方法確保一條record在store中。

(4) 還有一個限制,在你遇到性能問題以前你能夠在內存中合理的保存和搜索多少records。

3.  最後,記得你能夠結合QueriesFilter去利用各自的長處。記得records經過一個query返回到服務器而且緩存進store。你可使用這個事實來執行一個filter,經過一個query,開始匹配record到store中,而且一個filter function匹配相同的records。

4. 這將卸載服務器搜索全部可能的records,同時仍然建立一個實時更新列表,它包含了在客戶端建立的和修改records。

app/routes/posts/favourited.js

export default Ember.Route.extend({
  model() {
    var store = this.store;

    // Create a filter for all favorited posts that will be displayed in
    // the template. Any favorited posts that are already in the store
    // will be displayed immediately;
    // Kick off a query to the server for all posts that
    // the user has favorited. As results from the query are
    // returned from the server, they will also begin to appear.
    return store.filter('post', { favorited: true }, function(post) {
      return post.get('isFavorited');
    });
  }
});

2、How do I inform Ember Data about new records created on the backend?我如何通知Ember Data在後臺建立的新記錄?

1. 當你經過使用Ember Data的store.findRecord方法請求一個record時,Ember將會自動把數據加載進store。對於已經請求過的數據,這容許Ember避免下一次到後臺的往返形成的延遲。另外,加載一條record進store將會更新任何RecordArray(例如store.filter或者store.findAll的結果),應該包含這條record。這意味着任何依據RecordArray的綁定的數據或者計算屬性將會自動被同步,去包含這條新的或者更新的record的值。

2. 一些應用程序可能但願不經過store.findeRecord請求record添加或者更新record到store。爲了完成這個要求,你可使用DS.Storepush或者pushPayload方法。對於有一個通道(例如 SSE或者 Web Sockets)去通知它後臺有新的或者更新的recordsweb的應用程序,這是有用的。

3. 在Ember Data的store中,push是最簡單的方法去加載或者更新records。當使用push的時候,在把record推送進store以前規範化(normalize)JSON對象很重要。

4. push一次只接收一條record。若是你想加載一個records數組到store你能夠調用pushMany

socket.on('message', function (message) {
  var modelName = message.model;
  store.push(modelName, store.normalize(modelName, message.data));
});

5. 做爲v1.0.0-beta.14的push方法,它接受部分屬性去更新存在的records。所以啓用更新方法。更新部分屬性是有用的,若是你的網絡應用程序只接收到一個模型的改變屬性的通知。

6. pushPayload對於store#push來講是一個方便的封裝,若是模型的序列化器實現一個pushPayload 方法嗎,它將反序列化payloads。

注意這個方法和JsonSerializer一塊兒工做不會有效,由於它沒有實現一個pushPayload方法,這個很是重要。

socket.on('message', function (message) {
  store.pushPayload(message.model, message.data);
});
相關文章
相關標籤/搜索