eli*_*tbo 11 observable angular
我很难将我的大脑缠绕在Angular的观察者身上.我来自PHP的世界,事情肯定不是异步的.
我有一个组件,只显示一般主题的消息列表.现在,我有一个所有消息都属于的主题.如果主题不存在,则应创建该主题.消息和主题调用都是通过REST API完成的.
在非同步世界中,我会按顺序编程.消息服务将查看主题是否存在.如果没有,那么它有主题服务创建它.在有主题后,它会获取该主题中的所有消息.
我知道你订阅了一个observable,但是当需要按顺序发生一系列事情时会发生什么?的角2的HTTP文档经过当一个呼叫由更新英雄列表的一个非常简单的例子.
零件
export class NotificationListComponent implements OnInit {
constructor(private _notificationService:NotificationService) {
}
***
ngOnInit() {
this.getNotifications();
}
getNotifications() {
this._notificationService.getNotifications()
.subscribe(
notifications => this.notifications = notifications,
error => this.errorMessage = <any>error);
}
Run Code Online (Sandbox Code Playgroud)
通知服务
...
getNotifications() {
// call the topic service here for general topic??
return this.http.get('/messages?order[datesent]=DESC')
.map((res) => {
return res.json()["hydra:member"];
})
.map((notifications:Array<any>) => {
let result:Array<Notification> = [];
notifications.forEach((jsonNotification) => {
var Notification:Notification = {
message: jsonNotification.message,
topic: jsonNotification.topic,
datesent: new Date(jsonNotification.datesent),
};
result.push(Notification);
});
return result;
})
.catch(this.handleError);
}
...
Run Code Online (Sandbox Code Playgroud)
主题服务
...
getGeneralTopic() {
var generalTopic;
this.http.get('/topics?name=general')
.map((res) => {
return res.json()["hydra:member"][0];
})
.do(data => console.log(data))
.subscribe(generalTopic => res);
}
...
Run Code Online (Sandbox Code Playgroud)
Sas*_*sxa 14
Observable处理流.流可以是几乎任何东西,但您可以将它们视为异步事件的抽象数组.这很有用,因为您现在可以更清楚地推理它们:
String, Boolean, ObjectOperators工作类似于JavaScript的数组方法:map(), filter(), reduce()您通常在需要执行任务或涉及多个步骤的操作时使用Observable.这可以作为您的起点,您可以根据需要简化或增加复杂性.
你应该有一个"计划"或至少一个模糊的想法,这些步骤应该是什么.听起来很明显,但很多问题都出现了,因为你不知道自己想要什么(;
一旦你计划了一个动作(作为一系列步骤),你可以从任何一端开始,但我认为最好从最后开始.至少在你了解更多之前.
我有一个组件,只显示一般主题的消息列表.现在,我有一个所有消息都属于的主题.如果主题不存在,则应创建该主题.消息和主题调用都是通过REST API完成的.
在非同步世界中,我会按顺序编程.消息服务将查看主题是否存在.如果没有,那么它有主题服务创建它.在有主题后,它会获取该主题中的所有消息.
对于您的用例,该计划将是:["(create topic)", "select topic", "show messages"].messages是抽象的阵列,select和create是异步事件.
正如我上面所说,让我们从最后开始 - "show messages".
<div *ngFor="#message of messages"></div>
Run Code Online (Sandbox Code Playgroud)
我们知道我们正在处理Observable.of(messages)(这是你手动创建它的方式).接下来,您需要"填充" 消息流,并且可以使用Http返回的服务执行此操作Observable.由于您从服务器获得的消息被Http服务包含在几个"层"中,因此我们可以利用Observable的功能来链接运算符(运算符返回Observable)并获取我们需要的消息:
getMessages(topic) {
this.http.get("/messages?topic=" + topic)
.map(response => response.json())
// chain other operators here...
.filter(message => !message.private)
}
Run Code Online (Sandbox Code Playgroud)
你可以在这里使用你需要的任何操作符 ......这导致了Observables的下一个重要事项:
Observable 默认是冷的.这意味着当您创建一个observable时,您只需描述它应该做什么.它不会立即执行这些操作(如同Promises)需要触发它.
你通过订阅手动触发它,或者通过subscribe()方法手动触发它,或者你可以让Angular 用管道(它订阅你)使它变热async.
getMessages(topic) {
this.http.get("/messages?topic=" + topic)
.map(response => response.json())
.subscribe(messages => this.messages = messages);
}
Run Code Online (Sandbox Code Playgroud)
接下来要做的事情(或之前因为我们在计划中倒退)是为了"select topic".观看所选主题的价值并通过加载新消息来响应它的变化会很好.这可以用a来完成Subject.
Subject是一种桥接器或代理,在ReactiveX的某些实现中可用,它既充当观察者又充当Observable.因为它是一个观察者,它可以订阅一个或多个Observable,并且因为它是一个Observable,它可以通过重新发送它来传递它所观察的项目,并且它也可以发出新项目.
我们可以topic$像这样设置:
class ListComponent {
public messages;
public topic$ = new Subject();
constructor(private http: Http) {
this.getMessages('posts');
this.topic$
.subscribe(topic => this.getMessages(topic));
}
getMessages(topic: string) {....}
selectTopic(topic: string) {
this.topic$.next(topic)
}
}
Run Code Online (Sandbox Code Playgroud)
最后一步是"(create topic)"如果一个不存在.假设主题不存在,假设服务器将返回错误:
getMessages(topic: string) {
this.http.get(API_URL + topic)
.map(response => response.json())
.subscribe(
messages => this.messages = messages,
error => this.createTopic(topic)
);
}
createTopic(topic: string) {
this.http.post(API_URL + topic, { body: JSON.stringify(topic) })
.map(response => response.json())
.subscribe();
}
Run Code Online (Sandbox Code Playgroud)
这是这个例子的工作人员.正如你所看到的那样,这并不难(50行代码......).您可以轻松移动物品并根据需要创建服务.
| 归档时间: |
|
| 查看次数: |
3642 次 |
| 最近记录: |