Angular 手动输入URL时,由于延迟加载模块,无法从CanActivate Guard进行角度路由

Angular 手动输入URL时,由于延迟加载模块,无法从CanActivate Guard进行角度路由,angular,angular5,Angular,Angular5,如果用户使用书签或手动输入URL直接访问一些路由,则尝试停止访问这些路由。路线是一组按特定顺序链接的路线。例如,像一个向导 在过去,我在使用canActivate和使用服务时没有任何问题,如果没有正确的数据表明访问了以前的路由状态(即第2页之前的第1页等),它会将用户路由到初始路由(第1页),但是在使用enableTracing并在一对快速生成的组件上进行测试之后,应用程序似乎正在加载和访问阻止访问路由的CanActivate保护,调用this.router.navigate(['/exampl

如果用户使用书签或手动输入URL直接访问一些路由,则尝试停止访问这些路由。路线是一组按特定顺序链接的路线。例如,像一个向导

在过去,我在使用
canActivate
和使用服务时没有任何问题,如果没有正确的数据表明访问了以前的路由状态(即第2页之前的第1页等),它会将用户路由到初始路由(第1页),但是在使用
enableTracing
并在一对快速生成的组件上进行测试之后,应用程序似乎正在加载和访问阻止访问路由的
CanActivate
保护,调用
this.router.navigate(['/example/route/path'])似乎无法到达目的地(第1页)

将非延迟加载的
TestComponent
放入
approvutingmodule
或使用顶级
notfound
路由工作,但
main模块中的任何内容都不可路由。因此,它似乎可能与包含延迟加载模块的延迟加载模块有关

有人找到办法了吗?或者这只是与Angular-like
entryComponents
-中的延迟加载相关的另一个问题

我不知道为什么应用程序是这样设置的,所以在最坏的情况下,我将尝试快速重构并平缓功能模块的延迟加载

可激活

canActivate(
  next: ActivatedRouteSnapshot,
  state: RouterStateSnapshot): Observable<boolean> | Promise<boolean> | boolean {
  if (this.storeService.hasAccess) {
    return true;
  }

  this.router.navigate(['/store/page/1']); // Doesn't route to page 1
  return false;
}
const routes: Routes = [
  {
    path: '',
    children: [
      {
        path: 'page/1',
        component: Page1Component,
        data: {
          title: 'Store'
        }
      },
      {
        path: 'page/2',
        component: Page2Component,
        // Redirects to a blank page instead of page 1 when directly 
        // accessed by a browser bookmark
        canActivate: [CanActivateStoreGuard], 
        data: {
          title: 'Store'
        }
      },
      // ...
    ]
  }
];
主路由模块路由

const routes: Routes = [
  {
    path: '',
    loadChildren: './main/main.module#MainModule',
    canActivate: [AuthGuard]
  },
  // ...
  {
    path: 'not-found',
    loadChildren: './not-found/not-found.module#NotFoundModule'
  },
  {
    path: '**',
    redirectTo: 'not-found'
  }
];
const routes: Routes = [
  {
    path: '', component: MainComponent,
    children: [
      {
        path: '',
        redirectTo: 'store',
        pathMatch: 'full'
      },
      {
        path: 'store',
        loadChildren: './store/store.module#StoreModule'
      },
      // ...
    ]
  }
];
存储路由模块

canActivate(
  next: ActivatedRouteSnapshot,
  state: RouterStateSnapshot): Observable<boolean> | Promise<boolean> | boolean {
  if (this.storeService.hasAccess) {
    return true;
  }

  this.router.navigate(['/store/page/1']); // Doesn't route to page 1
  return false;
}
const routes: Routes = [
  {
    path: '',
    children: [
      {
        path: 'page/1',
        component: Page1Component,
        data: {
          title: 'Store'
        }
      },
      {
        path: 'page/2',
        component: Page2Component,
        // Redirects to a blank page instead of page 1 when directly 
        // accessed by a browser bookmark
        canActivate: [CanActivateStoreGuard], 
        data: {
          title: 'Store'
        }
      },
      // ...
    ]
  }
];

您需要在角度路由器订阅的可观测范围内执行路由更改

public canActivate(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<boolean> {
   return new Observable((subscriber) => {
       if (this.storeService.hasAccess) {
          subscriber.next(true);
       } else {
          this.router.navigate(['/store/page/1']);
          subscriber.next(false);
       }
       subscriber.complete();
   });
} 

能否添加路由配置以及如何使用
canActivate
。这不是canLoad的使用案例吗?Hi@cgTag我添加了一个代码示例Hi@bryan60,如果服务表明他们没有访问第1页,他们应该能够访问模块,但不能访问第2页路由组件。如果您尝试直接路由到第2页,则此方法有效,但如果他们手动输入URL以访问第2页,则会失败。好的,我现在明白了,您的问题是,由于延迟加载了一个模块,因此您有不同的服务副本。您需要创建一个核心模块,并在那里提供您的服务,以确保它是一个单独的模块。谢谢@cgTag的帮助。这些也不起作用,但由于它只影响尝试手动加载URL(或使用书签)的用户,而不是正常的应用程序路由,我想我会将此作为一个用户体验问题进行评论,稍后再讨论解决方法。我会发布我找到的任何东西。