【问题标题】:Routing child to parent is not working when navigates in Angular在 Angular 中导航时,将子级路由到父级不起作用
【发布时间】:2018-05-13 04:29:35
【问题描述】:

我使用的是 Angular 5.1.0,我的路由系统有问题,让我解释一下:

在我的应用程序路由模块中,我有一个 url /api 可以延迟加载另一个模块,在那个延迟加载的模块中,我有下一个路由实现:

api-routing.module.ts

const routes: Routes = [
  {
    path: '',
    component: ApisComponent,
    data: {
      breadcrumbs: 'APIs',
    },
    children: [
      {
        path: '',
        component: ApiListComponent,
      },
      {
        path: ':id',
        component: ApiDetailComponent,
        resolve: {
          api: ApiResolverService
        },
        data: {
          breadcrumbs: '{{ api.title }}',
        },
      },
    ],
  },
];

这里重要的是路由器接收到的data 参数。

在我的应用程序中,我有一个通用错误行为,当抛出异常时,我有一个 errorHandler 类,它可以捕获错误并重定向到另一个 url:/error,这是处理程序代码:

import { ErrorHandler, Injectable, Injector } from '@angular/core';
import { Router } from '@angular/router';

@Injectable()
export class AppErrorHandler implements ErrorHandler {

  constructor(private injector: Injector) { }

  handleError(error: any): void {
    const routerService = this.injector.get(Router);
    routerService.navigateByUrl('/error', { skipLocationChange: true });
  }
}

问题是,当在/api 中引发异常并执行handleError 时,我看到我的通用错误页面呈现在最后一条路由中加载的面包屑:/api by data 参数。

有没有办法让路由器在加载时重置数据?还是我做错了什么?


更新

此时我认为问题出在data 参数上,但现在我发现这不是问题所在。让我展示我的error.component,它是在路由器加载/error 时呈现的:

import { Component, OnInit } from '@angular/core';
import { Router, ActivatedRoute } from '@angular/router';

@Component({
  selector: 'app-error',
  templateUrl: './error.component.html',
  styleUrls: ['./error.component.scss']
})
export class ErrorComponent implements OnInit {

  constructor(private router: Router, private route: ActivatedRoute) { }

  ngOnInit() {
    console.log('snapshot trace');
    console.log(this.route.snapshot);
  }
}

我在 onInit 组件方法中包含了ActivatedRoute 快照的跟踪以查看它有什么,问题是当errorHandler 从/api 导航到/error 时跟踪没有显示。

但是如果我直接加载/error,则会显示跟踪,因此无论出于何种原因,错误组件在第一种情况下都没有正确实例化(从/api 导航到/error)


更新 我已经升级到 Angular 5.2.9,但问题仍然存在。

【问题讨论】:

  • 我不确定你能不能像这样注入路由器。我认为这是路由器的不同副本。您需要正常注入并使用工厂提供程序
  • 感谢您的评论!这是注入 ErrorHandler 的正确方法,因为它是在提供程序之前创建的,并且需要使用注入器,如果不使用,则会出现循环依赖错误
  • 这就是我的想法,但这仍然是错误的方式。你应该使用工厂函数
  • 我不明白你的意思,也许你在说另一种正确的方式,但是这种方式是正确的,我已经解决了我的问题,顺便谢谢你的cmets。
  • 工厂提供者不用于此目的,这里的问题是引导时,这个错误类是在提供者之前创建的。 medium.com/@aleixsuau/error-handling-angular-859d529fa53a顺便说一句,这里的主要问题不是注入

标签: javascript angular typescript


【解决方案1】:

我已经使用 NgZone 解决了这个问题,我认为 angular 的“时序”路由问题涉及到 angular zone 之外的渲染错误组件,所以,AppErrorHandler 类看起来像这样:

import { ErrorHandler, Injectable, Injector, NgZone } from '@angular/core';
import { Router } from '@angular/router';

@Injectable()
export class AppErrorHandler implements ErrorHandler {

  constructor(private injector: Injector) { }

  handleError(error: any): void {
    const routerService = this.injector.get(Router);
    const ngZone = this.injector.get(NgZone);
    ngZone.run(() => {
      routerService.navigate(['/error'], { skipLocationChange: true });
    });
  }
}

Here 与我的问题相关的 github 问题

【讨论】:

  • 虽然这个修复对我有用,但我想指出一个错误,因为它可以帮助某人。我收到“错误 TS2339:类型 '{}' 上不存在属性 'run'。”。我设法通过强输入变量名来解决这个问题 - let router: Router = this.injector.get(Router);
  • 完美@Nandun,你有一个严格的 tslint 规则,谢谢,我相信它会对某人有所帮助。
  • 在迁移到 Angular 8 后出现此问题时帮助我们
  • 即使没有{ skipLocationChange: true },它也会唤醒我——这样 url 会正常变化
猜你喜欢
  • 2020-02-19
  • 1970-01-01
  • 2017-08-20
  • 2017-06-04
  • 2018-01-04
  • 2019-06-04
  • 2017-04-06
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多