EmberJs之Ember-Data

写在前面

最近比较忙,换了新工作还要学习很多全新的技术栈,并给自己找了很多借口来不去坚持写博客。常常具有讽刺意味的是,更多剩下的时间并没有利用而更多的是白白浪费,也许这就是青春吧,挥霍吧,这不是我想要的,既然这样,我还要继续写下去,坚持把博客做好,争取进前100博客,在此谨记。

2015年5月7日深夜,于电脑旁。

文章索引

JS前端框架之Ember.js系列

什么是Ember-Data?

  对于简单的应用来说,可以通过jQuery来从服务器加载JSON数据,并将这些JSON数据对象作为模型。

  但是,使用一个模型库来管理查询、更改和将更改保存回服务器,将会大大的简化代码,同时也能提升应用的健壮性和性能,这便产生了Ember-Data数据模型。

  Ember-Data不需要进行任何配置,就可以实现通过服务端提供的RESTful JSON API加载和保存记录以及它们的管理关系,这些操作都遵从于特定的惯例。

如果需要将Ember.js应用与现有的、未遵从惯例的JSON APIs进行集成,Ember-Data也进行了充分的设计,通过简单的配置就可以使用服务端返回的数据。

Ember-Data同样适用于使用流式的API,例如socket.io、Firebase或WebSockets。通过建立一个与服务器端的Socket连接,在记录发生变化的时候,将这些变更推送到本地仓库中(Store)。

核心概念

仓库

  仓库是应用存放记录的中心仓库。你可以认为仓库是应用的所有数据的缓存。应用的控制器和路由都可以访问这个共享的仓库;当它们需要显示或者修改一个记录时,首先就需要访问仓库。

  DS.Store的实例会被自动创建,并且该实例被应用中所有的对象所共享。

  可以使用该实例来获取记录,创建新的记录等。例如,需要在路由的model钩子中查找一个类型为App.Person,ID为1的记录:

App.IndexRoute = Ember.Route.extend({
  model: function() {
    return this.store.find(‘person‘, 1);
  }
});

模型

  模型是一个类,它定义了需要呈现给用户的数据的属性和行为。任何用户期望在其离开应用然后再回到应用时能够看见的数据,都应该通过模型来表示。

  例如,如果正在编写一个可以给饭店下单的Web应用,那么这个应用中应该包含Order、LineItem和MenuItem这样的模型。

  获取订单就变得非常的容易:


1


this.store.find(‘order‘);

  模型定义了服务器提供的数据的类型。例如Person模型可能包含一个名为firstName的字符串类型的属性,还有一个名为birthday的日期类型的属性。


1

2

3

4


App.Person = DS.Model.extend({

firstName: DS.attr(‘string‘),

birthday:  DS.attr(‘date‘)

});

  模型也声明了它与其他对象的关系。例如,一个Order可以有许多LineItems,一个LineItem可以属于一个特定的Order。


1

2

3

4

5

6

7


App.Order = DS.Model.extend({

lineItems: DS.hasMany(‘lineItem‘)

});

App.LineItem = DS.Model.extend({

order: DS.belongsTo(‘order‘)

});

  模型本身没有任何数据;模型只定义了其实例所具有的属性和行为,而这些实例被称为记录

记录

  记录是模型的实例,包含了从服务器端加载而来的数据。应用本身也可以创建新的记录,以及将新记录保存到服务器端。

  记录由以下两个属性来唯一标识:

  1. 模型类型
  2. 一个全局唯一的ID

  例如,如果正在编写一个联系人管理的应用,有一个模型名为Person。那么在应用中,可能存在一个类型为Person,ID为1或者steve-buscemi的记录。


1


this.store.find(‘person‘, 1); // => { id: 1, name: ‘steve-buscemi‘ }

  ID通常是在服务器端第一次创建记录的时候设定的,当然也可以在客户端生成ID。

适配器

  适配器是一个了解特定的服务器后端的对象,主要负责将对记录的请求和变更转换为正确的向服务器端的请求调用。

  例如,如果应用需要一个ID为1的person记录,那么Ember Data是如何加载这个对象的呢?是通过HTTP,还是Websocket?如果是通过HTTP,那么URL会是/person/1,还是/resources/people/1呢?

适配器负责处理所有类似的问题。无论何时,当应用需要从仓库中获取一个没有被缓存的记录时,应用就会访问适配器来获取这个记录。如果改变了一个记录并准备保存改变时,仓库会将记录传递给适配器,然后由适配器负责将数据发送给服务器端,并确认保存是否成功。

序列化

  序列化主要负责将服务器端返回的原生JSON数据转化为记录对象。

  JSON API可能将属性、关联关系用不同的方式表示。例如,一些属性名可能采用了驼峰式命名规则,而另一些又使用了下划线隔离的命名规则。关联关系的表示方法更是五花八门:它们有可能会是一个ID数组,一个内嵌的对象集合,也可能是作为外键。

  当适配器从服务器端获取到一个特定记录的数据时,它将数据交给序列化对象,进而将数据转换为Ember Data期望的格式。

大部分人都需要使用序列化来完成JSON数据的转换,因为Ember Data将这些数据作为非透明的对象来处理,它们可能是以二进制数据被存储的,也可能是ArrayBuffer

自动化缓存

  仓库会自动缓存记录。如果一个记录已经被加载了,那么再次访问它的时候,会返回同一个对象实例。这样大大减少了与服务器端的往返通信,使得应用可以更快的为用户渲染所需的UI。

  例如,应用第一次从仓库中获取一个ID为1的person记录时,将会从服务器端获取对象的数据。

  但是,当应用再次需要ID为1的person记录时,仓库会发现这个记录已经获取到了,并且缓存了该记录。那么仓库就不会再向服务器端发送请求去获取记录的数据,而是直接返回第一次时候获取到并构造出来的记录。这个特性使得不论请求这个记录多少次,都会返回同一个记录对象,这也被称为Identity Map(标识符映射)。

  使用标识符映射非常重要,因为这样确保了在一个UI上对一个记录的修改会自动传播到UI其他使用到该记录的UI。同时这意味着你无须手动去保持对象的同步,只需要使用ID来获取应用已经获取到的记录就可以了。

架构简介

  应用第一次从仓库获取一个记录时,仓库会发现本地缓存并不存在一份被请求的记录的副本,这时会向适配器发请求。适配器将从持久层去获取记录;通常情况下,持久层都是一个HTTP服务,通过该服务可以获取到记录的一个JSON表示。

  如上图所示,适配器有时不能立即返回请求的记录。这时适配器必须向服务器发起一个异步的请求,当请求完成加载后,才能通过返回的数据创建的记录。

由于存在这样的异步性,仓库会从find()方法立即返回一个承诺(promise)。另外,所有请求需要仓库与适配器发生交互的话,都会返回承诺。

一旦发给服务器端的请求返回被请求记录的JSON数据时,适配器会履行承诺,并将JSON传递给仓库。

仓库这时就获取到了JSON,并使用JSON数据完成记录的初始化,并使用新加载的记录来履行已经返回到应用的承诺。

下面将介绍一下当仓库已经缓存了请求的记录时会发生什么。

  在这种情形下,仓库已经缓存了请求的记录,不过它也将返回一个承诺,不同的是,这个承诺将会立即使用缓存的记录来履行。此时,由于仓库已经有了一份拷贝,所以不需要向适配器去请求(没有与服务器发生交互)。

时间: 2024-08-25 00:34:34

EmberJs之Ember-Data的相关文章

Ember.js 入门指南——model简介2

本文接上一篇<Ember.js 入门指南--model简介1>. 2,核心概念 声明:下面简介内摘抄至http://www.emberjs.cn/guides/models/#toc_. 1,store store是应用存放记录的中心仓库.你可以认为store是应用的所有数据的缓存.应用的控制器和路由都可以访问这个共享的store:当它们需要显示或者修改一个记录时,首先就需要访问store. DS.Store的实例会被自动创建,并且该实例被应用中所有的对象所共享. store可以看做是一个缓存

【JavsScript】Ember.js

现在,我们经常都可以看到复杂的JavaScript应用程序,由于这些应用程序变得越来越复杂,一长串的jQuery回调语句或者通过应用程序在各个状态执行不同的函数调用,这些做法都会变得无法再让人接受,这导致了JavaScript开发人员开始寻找一种组织和效率更优秀的开发方式. 实现组织和效率的其中一个最常用的架构模式,就是我们熟知的Model View Controller (MVC)模式,这种模式鼓励开发人员将其应用程序的不同部分分割为更易于管理的模块,我们不必使用一个函数直接调用数据库,通过创

Ember.js 入门指南——总目录

Ember.js 是什么?我想对于想学习它的人应该知道它是个什么东西,如果你想了解那就赶紧去 Google 或者百度,本系列教程是通过学习官网教程然后摘抄个人觉得比较重要的部分,加上学习实例整合而成,如有疏漏欢迎提出修改意见,一起成长! Ember官网:http://emberjs.com/ 教程官网:http://guides.emberjs.com/v2.0.0/ 在此简单介绍下 Ember: Ember是一个雄心勃勃的Web应用程序,消除了样板,并提供了一个标准的应用程序架构的JavaSc

emberjs学习二(ember-data和localstorage_adapter)

emberjs学习二(ember-data和localstorage_adapter) 准备工作 首先我们加入ember-data和ember-localstorage-adapter两个依赖项,使用bower install安装这两个插件.如下 "dependencies": { "jquery": "~1.9.1", "ember": "~1.13.10", "handlebars"

Ember.js 入门指南--目录

本系列文章全部从(http://ibeginner.sinaapp.com/)迁移过来,欢迎访问原网站. Ember.js 是什么?我想对于想学习它的人应该知道它是个什么东西,如果你想了解那就赶紧去 Google 或者百度,本系列教程是通过学习官网教程然后摘抄个人觉得比较重要的部分,加上学习实例整合而成,如有疏漏欢迎提出修改意见,一起成长! Ember官网:http://emberjs.com/ 教程官网:http://guides.emberjs.com/v2.0.0/ 在此简单介绍下 Emb

Ember.js 入门指南——自定义序列号器

在Ember应用中,序列化器会格式化与后台交互的数据,包括发送和接收的数据.默认情况下会使用JSON API序列化数据.如果你的后端使用不同的格式,Ember Data允许你自定义序列化器或者定义一个完全不同的序列化器. Ember Data内置了三个序列化器.JSONAPISerializer是默认的序列化器,用与处理后端的JSON API.JSONSerializer是一个简单的序列化器,用与处理单个JSON对象或者是处理记录数组.RESTSerializer是一个复杂的序列化器,支持侧面加

Ember.js 入门指南——自定义适配器

在Ember应用中适配器决定了数据保存到后台的方式,比如URL格式和请求头部.Ember Data默认的适配器是内置的REST API回调. 实际使用中经常会扩展默认的适配器.Ember的立场是应该通过扩展适配器来添加不同的功能,而非添加标识.这样可以使得代码更加容易测试.更加容易理解,同时也降低了可能需要扩展的适配器的代码. 如果你的后端使用的是Ember约定的规则那么可用使用适配器adapters/application.js.适配器application优先级比默认的适配器高,但是比指定的

Ember.js的那些坑

用了一年Ember.js,从2.3到2.10,因为数据量大,以及项(xu)目(qiu)的复(bian)杂(tai)性踩了不少坑,感觉再也不会爱了.在把这个锅甩出去之前,小小总结一下,以示后人,知己知彼方能百战百胜.注意,这篇我只吐槽. 首先 肯定要吐槽一下压缩后仍旧占用几兆的巨无霸内核JS代码.光这点来说,Ember绝对不适合移动端以及小型项目的开发.哪怕像我参与的这个平台级项目,对于这个大小也是深感蛋疼.而且,Ember的默认配置还是只压缩成vender.js与app.js两个文件而已. 此外

Ember.js 入门指南——查询记录

store提供了统一的获取数据的接口.包括创建新记录.修改记录.删除记录等,更多有关Store API请看这个网址的介绍:http://devdocs.io/ember/data/classes/ds.store. 为了演示这些方法的使用我们结合firebase,关于firebase与Ember的整合前面的文章已经介绍,就不过多介绍了. 做好准备工作: ember g route articles ember g route articles/article 1,查询方法findAll,find

EmberJs之3W

写在前面 最近比较忙,换了新工作还要学习很多全新的技术栈,并给自己找了很多借口来不去坚持写博客.常常具有讽刺意味的是,更多剩下的时间并没有利用而更多的是白白浪费,也许这就是青春吧,挥霍吧,这不是我想要的,既然这样,我还要继续写下去,坚持把博客做好,争取进前100博客,在此谨记. 2015年5月7日深夜,于电脑旁. 文章索引 JS前端框架之Ember.js系列 What is EmberJs? 现如今Js框架层出不穷,各自独领风骚.你争我夺,还有各种新鲜框架来抢占市场吸引眼球,那究竟我们该如何选择