[Angular2 Router] Resolving route data in Angular 2
From Article: RESOLVING ROUTE DATA IN ANGULAR 2
If you know Anuglar UI router, you must know resolve function in ui router, which you can load data before template and controller get inited. In Angular2 router, you can also use resovler.
The recommended (personal preferred) way is use class to resolve the data, becasue you can inject servcie, so you can fetch data instead of hard cord data.
There is another way to use DI 'useValue'. Check out the article.
Create a resolver:
// hero-resolve.directive.ts
import {Resolve, ActivatedRouteSnapshot, RouterStateSnapshot} from "@angular/router";
import {Observable} from "rxjs";
import {StarWarsService} from "./heros.service";
import {Injectable} from "@angular/core";
@Injectable()
export class HeroDetailResolver implements Resolve<any> {
constructor(private startWarsService: StarWarsService){
}
resolve(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<any> | any{
const id = route.params['id'];
return this.startWarsService.getPersonDetail(id);
}
}
After create the resovler, you can add to the providers:
@NgModule({
imports: [
CommonModule,
herosRoutes
],
declarations: [HerosComponent, HeroComponent],
providers: [StarWarsService, CanHeroDeactivate, CanHeroActivateDirective, HeroDetailResolver]
})
Routers:
import {HerosComponent} from "./heros.component";
import {RouterModule} from "@angular/router";
import {HeroComponent} from "./hero/hero.component";
import {CanHeroDeactivate} from "./heros-can-deactivate.directive";
import {CanHeroActivateDirective} from "./heros-can-activate.directive";
import {HeroDetailResolver} from "./hero-resolver.directive";
const routes = [
{path: '', component: HerosComponent},
{
path: ':id',
component: HeroComponent,
canDeactivate: [CanHeroDeactivate],
canActivate: [CanHeroActivateDirective],
resolve: {
hero: HeroDetailResolver
}
},
];
export default RouterModule.forChild(routes)
Here 'hero' will be used to fetch data from router data.
Component:
import {
Component,
OnInit,
OnDestroy,
ViewChild,
} from '@angular/core';
import {ActivatedRoute, Router} from "@angular/router";
import {StarWarsService} from "../heros.service";
import {Observable, Subscription, BehaviorSubject} from "rxjs";
export interface Hero{
name: string,
image: string
}
@Component({
selector: 'app-hero',
templateUrl: 'hero.component.html',
styleUrls: ['hero.component.css']
})
export class HeroComponent implements OnInit, OnDestroy {
@ViewChild('inpRef') input;
heroId: number;
hero: BehaviorSubject<Hero>;
description: string;
querySub: Subscription;
routeParam: Subscription;
editing: boolean = false;
constructor(private route: ActivatedRoute,
private router: Router,
private starwarService: StarWarsService) {
}
ngOnInit() {
/* // Old way to get data from service when component inited
this.hero = new BehaviorSubject({name: 'Loading...', image: ''});
this.route.params
.map((p:any) => {
this.editing = false;
this.heroId = p.id;
return p.id;
})
.switchMap( id => this.starwarService.getPersonDetail(id))
.subscribe( this.hero);*/
// Here using resolver instead of fetch on fly
this.routeParam = this.route.params
.map((p:any) => p.id)
.subscribe( (id) => {
this.editing = false;
this.heroId = id;
});
this.hero = this.route.data
.map((d:any)=> d['hero']);
}
ngOnDestroy() {
this.querySub.unsubscribe();
this.routeParam.unsubscribe();
}
}
Child route and access parnet's router resolver's data
{path: ':url/:id', children: [
{path: '', component: LessonDetailComponent},
{path: 'edit', component: EditLessonComponent}
], resolve: {
lesson: LessonDataResolver
}},
For 'LessonDetailComponent' and 'EditLessonComponent' can both access the resolve data:
this.route.data
.subscribe(
(res) => {
this.lesson = res['lesson'];
}
)
ONE important note that: If return Observable from resolver, the observable should completed! Otherwise, it doesn't work. So why in the exmaple, it works, because $http.get(), it complete itself.
But if you use AngualrFire2, you fetch data from Firebase like:
findLessonByUrl(url){
return this.angularFireRef.database.list('lessons', {
query: {
orderByChild: 'url',
equalTo: url
}
})
.filter(r => !!r)
.map(res => res[]);
}
The observable doesn't complete itself, so in the resolver, you need to find a way to make the observable completed.
For example:
import {Resolve, RouterStateSnapshot, ActivatedRouteSnapshot} from "@angular/router";
import {Observable} from "rxjs";
import {CourseService} from "../course.service";
import {Injectable} from "@angular/core";
@Injectable()
export class LessonDataResolver implements Resolve {
constructor(private lessonService: CourseService){
}
resolve(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<any> {
const url = route.params['id'];
return this.lessonService.findLessonByUrl(url).first();
}
}
Here it calls .first() to complete the observable. Or you can use '.take(1)'.
[Angular2 Router] Resolving route data in Angular 2的更多相关文章
- [Angular2 Router] CanDeactivate Route Guard - How To Confirm If The User Wants To Exit A Route
In this tutorial we are going to learn how we can to configure an exit guard in the Angular 2 Router ...
- [Angular2 Router] CanActivate Route Guard - An Example of An Asynchronous Route Guard
In this tutorial we are going to learn how we can to configure an can activate route guard in the An ...
- [Angular2 Router] Optional Route Query Parameters - The queryParams Directive and the Query Parameters Observable
In this tutorial we are going to learn how to use the Angular 2 router to pass optional query parame ...
- Angular2 - Starter - Routes, Route Resolver
在基于Angualr的SPA中,路由是一个很重要的部分,它帮助我们更方便的实现页面上区域的内容的动态加载,不同tab的切换,同时及时更新浏览器地址栏的URN,使浏览器回退和前进能导航到历史访问的页面. ...
- [Angular2 Router] Preload lzay loading modules
From router v3.1.0, we have preloading system with router. PreloadAllModules After the init module l ...
- [Angular2 Router] Setup page title with Router events
Article import 'rxjs/add/operator/filter'; import 'rxjs/add/operator/map'; import 'rxjs/add/operator ...
- [Angular2 Router] Programmatic Router Navigation via the Router API - Relative And Absolute Router Navigation
In this tutorial we are going to learn how to navigate programmatically (or imperatively) by using t ...
- [Angular2 Router] Auxiliary Routes bit by bit
Article Github Auxiliary Routes is is little bit hard to understand. Here is demo, link You can see ...
- Vue中美元$符号的意思与vue2.0中的$router 和 $route的区别
vue的实例属性和方法 除了数据属性,Vue 实例还暴露了一些有用的实例属性与方法.它们都有前缀 $,以便与用户定义的属性区分开来.例如: var data = { a: 1 } var vm = n ...
随机推荐
- Ueditor 七牛集成
UEDITOR修改成功的 http://blog.csdn.net/uikoo9/article/details/41844747 http://blog.csdn.net/u010717403/ar ...
- 【试水CAS-4.0.3】第07节_CASclient配置单点登录
完整版见https://jadyer.github.io/2015/07/26/sso-cas-client-login/ 本文源代码下载:http://download.csdn.net/detai ...
- 火狐—火狐浏览器中的“HttpWatch”
在IE下通过HttpWatch能够查看HTTP请求的相关细节.这对我们分析程序的运行效率很有帮助,但是在火狐浏览器中的难道就没有相似的工具了吗?答案是否定的--火狐浏览器中也有.在火狐浏览器中该工具叫 ...
- AQS -> AbstractQueuedSynchronizer
前言 : 先说说这个 CLH锁: 加锁 1. 创建一个的需要获取锁的 Node 2. 通过 CAS操作 让自己 成为这个尾部的节点,然后令 设置自己的pre 3. 自旋,直到pre节点释放 释放: 1 ...
- 2.Xml与多个对象的映射(聚合或组合)及注意事项
在我们的实际应用中,Xml中的结构往往不止这么简单,一般都会有2,3层.也就是说如果映射成对象就是聚合(组合)的情况 . 就用我们上一章的例子继续来讲,简单我们的Book的author现在不止是一个S ...
- 一文了解sun.misc.Unsafe
Java语言和JVM平台已经度过了20岁的生日.它最初起源于机顶盒.移动设备和Java-Card,同时也应用在了各种服务器系统中,Java已成为物联网(Internet of Things)的通用语言 ...
- ftp实现图片上传,文件也类似
本来用得是easyui得控件 点击按钮实现选择图片得 ,但是老板非得要双击图片框实现上传代码....做个简单得记录 前端代码: 首先,<form>表单要加上 enctype="m ...
- gerrit-申请id跟本地配置
OpenID 是一个以用户为中心的数字身份识别框架,它具有开放.分散.自由等特性. 什么是gerrit? 看 了网上的介绍,感觉所谓的gerrit就是一个基于web实现代码管理的服务器.Gerrit ...
- Quick Sort Algorithm
快速排序算法实现代码: //============================================================================ // Name : ...
- Jquery+Ajax+Bootstrap Paginator实现分页的拼接
效果图如下 jsp页面引入bootstrap样式,jquery和bootstrap-paginator.js <link type="text/css" rel=" ...