Angular 6路由器解析-未调用组件

时间:2019-02-08 19:18:32

标签: angular firebase rxjs angular6

以下是我在路线上定义的解决方法。

@Injectable({
    providedIn: 'root'
})
export class CourseDetailResover implements Resolve<Observable<[Course, (Lesson[])]>>  {

    constructor(private coursesService: CoursesService) { }

    resolve(route: ActivatedRouteSnapshot,
        state: RouterStateSnapshot): Observable<[Course, (Lesson[])]> {
            return this.coursesService.findCourseByUrl(route.params['id'])
            .pipe(
                tap(data => console.log(data)),
                switchMap(
                    course => this.coursesService.findLessonsForCourse(course.id)
                        .pipe(
                             tap(data => console.log(data)),
                            map<Lesson[], [Course, Lesson[]]>(lessons => [course, lessons]),
                            tap(data => console.log(data))
                        )
                )
            );
    }
}

我的路线是

  {
        path: 'course/:id',
        component: CourseDetailComponent,
        resolve: {
            detail:CourseDetailResover
        }
    }

我发现,即使正在调用解析器,下面的ngOnInit组件也不会真正被调用

export class CourseDetailComponent implements OnInit {

  course$: Observable<Course>;
  lessons$:Observable<Lesson[]>;

  constructor(private route: ActivatedRoute) {}

  ngOnInit(): void {
    console.log('inside here');
    this.course$ = this.route.data.pipe(map(data => data['detail'][0]));

    this.lessons$ = this.route.data.pipe(map(data => data['detail'][1]));
  }
}

启用路由跟踪后,我可以看到以下内容。

Router Event: ResolveStart

但是,跟踪日志中没有Router Event: ResolveEnd

这里可能是什么问题?

1 个答案:

答案 0 :(得分:0)

看起来您在这里是RxJS observables的双重嵌套,这是您的意图吗?查看angular的Resolve接口时,您正在正确实现它,但是T实际上是Observable本身:

export interface Resolve<T> {
    resolve(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<T> | Promise<T> | T;
}

因此您的解析器类应类似于以下内容:

export class CourseDetailResover implements Resolve<[Course, (Lesson[])]>

您的ngOnInit从未被调用的事实导致了这样一个假设,即您的Observable方法返回的resolve永远不会终止/完成。请注意,Observable必须完成,以便解析器“结束”其工作并继续进行路由过程。看看这个问题以供参考:

https://github.com/angular/angular/issues/10556

以下代码将起作用

@Injectable({
    providedIn: 'root'
})
export class CourseDetailResover implements Resolve<Promise<Observable<[Course, (Lesson[])]>>>  {

    constructor(private coursesService: CoursesService) { }

    resolve(route: ActivatedRouteSnapshot,
        state: RouterStateSnapshot): Promise<Observable<[Course, (Lesson[])]>> {
            const routerObservable =   this.coursesService.findCourseByUrl(route.params['id'])
            .pipe(
                switchMap(
                    course => this.coursesService.findLessonsForCourse(course.id)
                        .pipe(
                            map<Lesson[], [Course, Lesson[]]>(lessons => [course, lessons]),
                        )
                )
            );

            return new Promise((resolve,reject) => {
                routerObservable.pipe(
                    first()
                ).subscribe((data) => {
                    console.log(data)
                    resolve(routerObservable)});
            })
    }
}

在组件方面

  ngOnInit(): void {
    console.log('inside here');
     const observableD:Observable<[Course, (Lesson[])]> = this.route.snapshot.data["detail"];
    this.course$ = observableD.pipe(
      map(data => data[0])
    );

    this.lessons$ = observableD.pipe(
      map(data => data[1])
    );
  }