Angular2 相对路线在警卫中导航 [英] Angular2 relative route navigate in a guard

查看:46
本文介绍了Angular2 相对路线在警卫中导航的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们在这里提供了子路由定义,其中我们使用了一个守卫来检查用户在使用我们的服务之前是否接受了条款.

We have child routes definitions presented here, in which we use a guard to check if the user has accepted terms before using our service.

account/secret/secret.routes.ts:

account/secret/secret.routes.ts:

import { Routes } from '@angular/router';
import { SecretFormComponent } from './secret-form.component';
import { SecretTermsComponent } from './secret-terms.component';
import { TermsGuard } from './services/terms-guard.service';

export const secretRoutes: Routes = [
  {
    path: '',
    redirectTo: 'form'
  },
  {
    path: 'form',
    component: SecretFormComponent,
    canActivate: [TermsGuard]
  },
  { path: 'terms', component: SecretTermsComponent }

  // otherwise redirect to form
  { path: '**',  redirectTo: 'form' }
];

在我们的terms-guard中,我们定义了这个代码:

In our terms-guard, we have defined this code:

this.router.navigate(['/account/secret/terms']);
return false;

有没有办法在路由组"中使用相对路由导航进行重定向?因为如果有一天我们的帐户网站仪表板重命名为诸如 my-account 之类的任何其他内容,则定义绝对路径可能会中断.我们希望我们的秘密模块可以重复使用.

Is there a way to redirect using relative route navigation from within a "routing group"? Because defining an absolute path may be break if one day our account website dashboard is renamed to anything else like my-account for example. We want our secret module to be reusable.

我希望能够在我的守卫中导航到 ['./terms'] 但它不起作用,就像守卫不知道从哪里"到开始相对导航.

I'd like to be able to navigate to ['./terms'] in my guard but it doesn't work, just like the guard doesn't know "from where" to start relative navigation.

推荐答案

你要使用的是你的守卫的canActivate方法的RouterStateSnapshot参数.

What you want to use is the RouterStateSnapshot parameter of the canActivate method of your guard.

>

RouterStateSnapshot 包含您正在路由到的当前路径,而 Router.url 是您路由的当前路径(这就是为什么 @Günter Zöchbauer 的回答在这种情况下不太适用.

The RouterStateSnapshot has the current path you are in the process of routing to, whereas the Router.url is the current path your are routing from (which is why @Günter Zöchbauer's answer doesn't quite work in this scenario).

为了在没有额外代码的情况下完全适用于您的用例,您需要将路由更改为

For this to apply completely to your use case without additional code you will want to change your routes to

/account/secret/form/account/secret/form/terms

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

@Injectable()
export class ChildRouteGuard implements CanActivate {
    constructor(private router: Router) { }

    canActivate(_route: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<boolean> | Promise<boolean> | boolean {
        // user can view the specific route
        if (...) {
            return true;
        }

        // else route them to a variation of the route
        this.router.navigate([state.url, 'terms']);

        return false;
    }
}

编辑 1

您还可以利用 ActivatedRouteSnapshot 来保留当前的 ​​url 结构,如下所示

Edit 1

You could keep your current url structure by also taking advantage of the ActivatedRouteSnapshot as seen below

假设路由像 account/secret/formaccount/secret/terms

route.url 是一个 url 段数组,我们想要最后一个,因为那将是 form.我们在当前路径中找到它的索引,我们尝试去account/secret/formslice 把它切掉.在这一点上,我们有我们试图导航到 account/secret 的当前路由的父",我们可以将兄弟添加到 form,即 条款.

route.url is an array of url segments, we want the last one because that is going to be form. We find the index of that in the current route we are trying to go to account/secret/form and slice it out. At this point we have the 'parent' of the current route we are trying to navigate to account/secret and we can add on the sibling to form which is terms.

注意:当您在 url 中重复出现 form 时,此模式会失效

Note: this pattern breaks down when you have repeated occurrences of form in your url

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

@Injectable()
export class ChildRouteGuard implements CanActivate {
    constructor(private router: Router) { }

    canActivate(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<boolean> | Promise<boolean> | boolean {
        // user can view the specific route
        if (...) {
            return true;
        }

        let parentUrl = state.url
            .slice(0, state.url.indexOf(route.url[route.url.length - 1].path));

        this.router.navigate([parentUrl, 'terms']);

        return false;
    }
}

这篇关于Angular2 相对路线在警卫中导航的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆