为什么我不能将RouterStateSnapshot注入Angular 2 App中的登录组件?

时间:2017-11-01 21:42:25

标签: javascript angular typescript routing

Simple Angular 2问题:当我将LoginStateSnapshot注入我的Login Component中的构造函数时,为什么会出现DI(依赖注入)错误?我正在尝试在注销之前获取URL,因此我可以在用户重新登录时传递它(因此它将加载其上次访问的组件/页面)。这比我预期的要困难得多。即使在我的构造函数中导入并包含RouterStateSnapshot之后,我也会收到DI错误。这就是我在登录组件中设置的方式:

import { ActivatedRoute, ActivatedRouteSnapshot, Router, RouterStateSnapshot } from '@angular/router';

constructor(private router: Router,
            private route: ActivatedRoute,
            private authenticationService: AuthenticationService,
            private alertService: AlertService,
            private state: RouterStateSnapshot,
            private authGuardService: AuthGuardService,
            private idle: Idle)
{

这里有什么问题?我错过了与ActivatedRoute,ActivatedRouteSnapshot等不同的RouterStateSnapshot - 我可以导入并注入没有问题?为什么我不能以相同的方式注入RouterStateSnapshot?

顺便说一句,我可以在我的authGuardService中使用RouterStateSnapshot而不会出现问题。它在我的canActivate()函数中使用 - 并返回正确的结果。那么这种情况有什么不同呢?为什么我不能在我的登录组件中使用它?

3 个答案:

答案 0 :(得分:5)

我认为你可以从RouterStateSnapshot获得RouterState。考虑这个例子:

constructor(private router: Router) {
    let routerStateSnapshot = this.router.routerState.snapshot;
{

答案 1 :(得分:0)

RouteGuardService.ts

import {Injectable} from '@angular/core';
import {ActivatedRouteSnapshot, CanActivate, Router} from '@angular/router';

import {LoginService} from './login.service';

@Injectable({
  providedIn: 'root'
})
export class RouteGuardService implements CanActivate {

  constructor(private loginService: LoginService, private router: Router) {
  }

  canActivate(activatedRoute: ActivatedRouteSnapshot): boolean {
    if (this.loginService.isLoggedIn()) {
      return true;
    }
    this.router.navigate(['login'], {queryParams: {returnUrl: activatedRoute.routeConfig.path}});
    return false;
  }
}

LoginComponent.ts

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

@Component({
  selector: 'app-login',
  templateUrl: './login.component.html',
  styleUrls: ['./login.component.css']
})
export class LoginComponent implements OnInit {
  errorMessage = 'Invalid Credentials';
  invalidLogin = false;
  username = 'in28minutes';
  password = 'novell';
  returnUrl: string;

  constructor(private router: Router, public loginService: LoginService, private activatedRoute: ActivatedRoute) {
  }

  ngOnInit(): void {
  }

  handleLogin(): any {
    this.returnUrl = this.activatedRoute.snapshot.queryParams.returnUrl || `/welcome/${this.username}`;
    if (this.loginService.authenticate(this.username, this.password)) {
      this.router.navigateByUrl(this.returnUrl);
    } else {
      this.router.navigate(['login']);
      this.invalidLogin = true;
    }
  }


}

app-routing.module.ts

import {Component, NgModule} from '@angular/core';
import {RouterModule, Routes} from '@angular/router';
import {LoginComponent} from './login/login.component';
import {TodoListComponent} from './todo-list/todo-list.component';
import {WelcomeComponent} from './welcome/welcome.component';
import {ErrorComponent} from './error/error.component';
import {RouteGuardService} from './service/route-guard.service';
import {TodoComponent} from './todo/todo.component';

const routes: Routes = [
  {path: '', component: LoginComponent, canActivate: [RouteGuardService]},
  {path: 'login', component: LoginComponent},
  {path: 'welcome/:username', component: WelcomeComponent, canActivate: [RouteGuardService]},
  {path: 'todos', component: TodoListComponent, canActivate: [RouteGuardService]},
  {path: 'todo/:id', component: TodoComponent, canActivate: [RouteGuardService]},
  {path: '**', component: ErrorComponent}
];

@NgModule({
  imports: [RouterModule.forRoot(routes)],
  exports: [RouterModule]
})
export class AppRoutingModule {

}

答案 2 :(得分:0)

如果您要从方法/函数创建returnUrl而不是使用canActivate接口或Authguard, 在功能中,

constructor (
    private route: ActivatedRoute,
}

sampleFunction (){
    this.router.navigate(['/auth/login'], {
        queryParams: {
            returnUrl: this.router.routerState.snapshot.url
        }
    })
}