简体   繁体   English

为什么在@ angular / redux-store中使用@select时,Angular Guard的行为会有所不同

[英]Why do Angular guards behave differently when using @select from @angular/redux-store

  • I have an Angular setup that uses two guard. 我有一个使用两个防护装置的Angular装置。 canLoad and canActivate canLoadcanActivate
  • both get fed with the same observable from the @angular-redux/store via @select 两者都通过@select从@ angular-redux / store获得了相同的可观察@select

Question : Why does canActivate work with the observable that @select returns while canLoad breaks all routing from then on? 问题 :为什么canActivate可以与@select返回的可观察值canActivate工作,而canLoad中断了所有路由? What is the difference between the two guards? 两名警卫有什么区别?

Related angular issue: https://github.com/angular/angular/issues/18991 相关角度问题: https : //github.com/angular/angular/issues/18991

auth.guard.ts 认证卫士

@Injectable()
export class AuthGuard implements CanLoad, CanActivate {

  @select() readonly authenticated$: Observable<boolean>; // @angular-redux/store

  canLoad(): Observable<boolean> | boolean {
    // return true; // works
    return this.authenticated$; // ERROR: all routing stops from and to the current page
  }

  canActivate(): Observable<boolean> | boolean {
    // return true; // works
    return this.authenticated$; // works
  }

}

app-routing.module 应用程序路由模块

const routes: Routes = [
  {
    path: '',
    component: SomeAComponent,
    pathMatch: 'full'
  },
  {
    path: 'someb',
    component: SomeBComponent,
    canActivate: [
      AuthGuard
    ],
  },
  {
    path: 'lazy',
    loadChildren: './lazy/lazy.module#LazyModule',
    canLoad: [
      AuthGuard
    ]
  },
  {
    path: '**',
    redirectTo: '/'
  }
];

The same issue I had, so to resolve it and let working in both CanLoad and CanActivate, you should add operator take(1) 我遇到了同样的问题,因此要解决此问题并让它同时在CanLoad和CanActivate中工作,您应该添加运算符take(1)

@Injectable()
export class AuthGuard implements CanLoad, CanActivate {

  @select() readonly authenticated$: Observable<boolean>; // @angular-redux/store

  canLoad(): Observable<boolean> | boolean {
    // return true; // works
    return this.authenticated$.pipe(take(1));
  }

  canActivate(): Observable<boolean> | boolean {
    // return true; // works
    return this.authenticated$; 
  }

}

I just ran into the same issue and I do think that this is a bug in angular. 我遇到了同样的问题,但我确实认为这是一个有角度的错误。 I ended up just rewriting my guard to store a local variable that is populated by subscribing to the Observable. 我最终只是重写了我的后卫,以存储通过订阅Observable填充的局部变量。 I am using ngrx/store here. 我在这里使用ngrx / store。

@Injectable()
export class MustBeAuthenticatedGuard implements CanActivate, CanLoad {

  constructor(private store: Store<fromAuth.State>) {
    store.select(fromAuth.authenticated)
      .subscribe((authenticated) => {
        this.authenticated = authenticated;
      });
  }

  private authenticated: boolean

  canLoad(): boolean {
    return this.isAuthenticated();
  }

  canActivate(): boolean {
    return this.isAuthenticated();
  }

  private isAuthenticated() {
    if (!this.authenticated) {
      this.store.dispatch(new SignIn());
    }
    return this.authenticated;
  }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM