在Angular 5中如何从URL中获取查询参数?

我使用的是angular 5.0.3,我想用一堆查询参数来启动我的应用程序,比如/app?param1=hallo&param2=123在Angular 2中如何从url中获取查询参数?中给出的每个技巧对我都不适用。

有什么想法如何获得查询参数工作?

private getQueryParameter(key: string): string {
const parameters = new URLSearchParams(window.location.search);
return parameters.get(key);
}

这个私有函数帮助我获取参数,但我认为在新的Angular环境中这不是正确的方式。

< p >(更新:) 我的主应用程序看起来像

@Component({...})
export class AppComponent implements OnInit {


constructor(private route: ActivatedRoute) {}


ngOnInit(): void {
// would like to get query parameters here...
// this.route...
}
}
514440 次浏览
import { ParamMap, Router, ActivatedRoute } from '@angular/router';


constructor(private route: ActivatedRoute) {}


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

更新

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


export class LoginComponent {
constructor(private router: Router) {
const snapshot: RouterStateSnapshot = router.routerState.snapshot;
console.log(snapshot);  // <-- hope it helps
}
}

当你有一个空路由对象时,这主要是因为你没有在app.component.html中使用路由器出口。

如果没有这个,你将无法获得一个有意义的路由对象与非空的子对象,特别是params &queryParams。

尝试在调用<代码>之前添加__abc0 & lt; app-main-component> & lt; / app-main-component> < /代码> < / p >

在此之前,确保你在App -routing >中准备好了查询参数,它导出了App组件使用的类Route:

param: '/param/:dynamicParam', path: MyMainComponent

当然,最后一件事,为了获得你的参数,我个人使用this.route.snapshot.params.dynamicParam,其中dynamicParam是在你的应用程序路由组件中使用的名称:)

小心你的路线。“redirectTo”将删除|删除任何查询参数。

const appRoutes: Routes [
{path: "one", component: PageOneComponent},
{path: "two", component: PageTwoComponent},
{path: "", redirectTo: "/one", pathMatch: full},
{path: "**", redirectTo: "/two"}
]

我用查询参数调用我的主组件,如“/main?param1=a¶m2=b”,并假设我的查询参数在重定向转发生效之前到达主组件中的“ngOnInit()”方法。

但这是错误的。重定向将出现在前面,删除查询参数并在没有查询参数的情况下调用主组件中的ngOnInit()方法。

我把第三条路线改成了

{path: "", component: PageOneComponent},

现在我的查询参数可以在主要组件ngOnInit和PageOneComponent中访问。

找到:父组件从ActivatedRoute获取空参数

对我有用:

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


@Component({
selector: 'app-navigation-bar',
templateUrl: './navigation-bar.component.html',
styleUrls: ['./navigation-bar.component.scss']
})
export class NavigationBarComponent implements OnInit, OnDestroy {
private sub: any;
constructor(private route: ActivatedRoute, private router: Router) {}


ngOnInit() {
this.sub = this.router.events.subscribe(val => {
if (val instanceof RoutesRecognized) {
console.log(val.state.root.firstChild.params);
}
});
}


ngOnDestroy() {
this.sub.unsubscribe();
}


}

在Angular 5中,查询参数是通过订阅this.route.queryParams来访问的(注意Angular的后续版本推荐 queryParamMap,也可以查看其他答案)。

例如:/app?param1=hallo&param2=123

param1: string;
param2: string;
constructor(private route: ActivatedRoute) {
console.log('Called Constructor');
this.route.queryParams.subscribe(params => {
this.param1 = params['param1'];
this.param2 = params['param2'];
});
}

而路径变量是通过this.route.snapshot.params访问的

例如:/param1/:param1/param2/:param2

param1: string;
param2: string;
constructor(private route: ActivatedRoute) {
this.param1 = this.route.snapshot.params.param1;
this.param2 = this.route.snapshot.params.param2;
}

它对我的作用是:

constructor(private route: ActivatedRoute) {}


ngOnInit()
{
this.route.queryParams.subscribe(map => map);
this.route.snapshot.queryParams;
}

查看更多选项如何获得查询参数从url在angular2?

当我在寻找类似的解决方案时偶然发现了这个问题,但我不需要像完整的应用程序级路由或更多导入模块之类的东西。

下面的代码非常适合我使用,不需要额外的模块或导入。

  GetParam(name){
const results = new RegExp('[\\?&]' + name + '=([^&#]*)').exec(window.location.href);
if(!results){
return 0;
}
return results[1] || 0;
}


PrintParams() {
console.log('param1 = ' + this.GetParam('param1'));
console.log('param2 = ' + this.GetParam('param2'));
}

http://localhost:4200/?param1=hello&param2=123输出:

param1 = hello
param2 = 123

这对我来说是最干净的解决方案

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


export class MyComponent {
constructor(
private route: ActivatedRoute
) {}


ngOnInit() {
const firstParam: string = this.route.snapshot.queryParamMap.get('firstParamKey');
const secondParam: string = this.route.snapshot.queryParamMap.get('secondParamKey');
}
}

我知道OP要求的是Angular 5的解决方案,但对于所有在更新的(6+)Angular版本中偶然遇到这个问题的人来说。引用文档,关于ActivatedRoute。queryParams(大多数其他答案都基于queryParams):

两个较旧的属性仍然可用。他们的能力比 它们的替换,不鼓励使用,将来可能会弃用 角版。< / p >

params -一个包含required和optional的Observable 指定路由的参数。使用paramMap代替

queryParams—包含可用查询参数的可观察对象 所有路线。使用queryParamMap代替

根据文档,获取查询参数的简单方法是这样的:

constructor(private route: ActivatedRoute) { }


ngOnInit() {
this.param1 = this.route.snapshot.paramMap.get('param1');
this.param2 = this.route.snapshot.paramMap.get('param2');
}

有关更高级的方法(例如高级组件重用),请参阅 Docs一章。

编辑:

正如下面注释中正确指出的那样,这个答案是错误的 -至少对于OP指定的情况是这样。

OP请求获取全局查询参数(/app?param1=hallo¶m2=123);在这种情况下,你应该使用queryParamMap(就像在@dapperdan1985回答)。

另一方面,paramMap用于特定于路由的参数(例如/app/:param1/:param2,导致/app/hallo/123)。

感谢@JasonRoyle和@daka指出这一点

你也可以使用HttpParams,例如:

  getParamValueQueryString( paramName ) {
const url = window.location.href;
let paramValue;
if (url.includes('?')) {
const httpParams = new HttpParams({ fromString: url.split('?')[1] });
paramValue = httpParams.get(paramName);
}
return paramValue;
}

如果你没有使用Angular的路由器try, 变量的名称。安装它

npm install --save querystring

对你的项目。在您的组件中执行如下操作

import * as qs from 'querystring';
...
ngOnInit() {
const params = qs.parse(window.location.search.substring(1));
...
}

substring(1)是必要的,因为如果你有这样的'/mypage?foo=bar',那么键名将是?foo

刚刚偶然发现了同样的问题,这里的大多数答案似乎只解决了Angular内部路由的问题,然后其中一些解决了路由参数,这与请求参数不一样。

我猜我的用例与Lars最初的问题类似。

对我来说,用例是推荐跟踪:

Angular运行在mycoolpage.com上,带有散列路由,因此mycoolpage.com重定向到mycoolpage.com/#/。然而,对于引用,像mycoolpage.com?referrer=foo这样的链接也应该可用。不幸的是,Angular立即删除了请求参数,直接转到mycoolpage.com/#/

任何使用空组件+ AuthGuard并获得queryParamsqueryParamMap的“技巧”,不幸的是,对我不起作用。它们总是空的。

我的解决方案最终是在index.html中的一个小脚本中处理这个问题,该脚本获得完整的URL, 请求参数。然后,我通过字符串操作获得请求参数值,并将其设置在窗口对象上。然后,一个单独的服务处理从窗口对象获取id。

index . html脚本

const paramIndex = window.location.href.indexOf('referrer=');
if (!window.myRef && paramIndex > 0) {
let param = window.location.href.substring(paramIndex);
param = param.split('&')[0];
param = param.substr(param.indexOf('=')+1);
window.myRef = param;
}

服务

declare var window: any;


@Injectable()
export class ReferrerService {


getReferrerId() {
if (window.myRef) {
return window.myRef;
}
return null;
}
}
/*
Example below url with two param (type and name)
URL : http://localhost:4200/updatePolicy?type=Medicare%20Insurance&name=FutrueInsurance
*/
constructor(private route: ActivatedRoute) {
//Read url query parameter `enter code here`
this.route.queryParams.subscribe(params => {
this.name= params['type'];
this.type= params['name'];
alert(this.type);
alert(this.name);


});


}

不幸的是,最干净的解决方案并不是最可扩展的解决方案。在Angular的最新版本中,其他答案中建议你可以使用ActivatedRoute injectable,特别是使用snapshot属性,轻松获取查询参数:

this.route.snapshot.queryParamMap.get('param')

或者订阅属性(在查询字符串会更新的情况下使用,例如通过用户id导航):

this.route.queryParamMap.subscribe(params => console.log(params));

我在这里告诉你,这些解决方案有一个巨大的缺陷,还没有解决一段时间:https://github.com/angular/angular/issues/12157

总而言之,唯一的防弹解决方案是使用优秀的老香草javascript。在本例中,我为URL操作创建了一个服务:

import { Injectable } from '@angular/core';
import { IUrl } from './iurl';


@Injectable()
export class UrlService {
static parseQuery(url: string): IUrl {
const query = url.slice(url.indexOf('?')+1).split('&').reduce( (acc,query) => {
const parts = query.split('=');
acc[parts[0]] = parts[1];
return acc;
}, {});


return {
a: query['a'],
b: query['b'],
c: query['c'],
d: query['d'],
e: query['e']
}
}
}

简单的解决方案

 // in routing file
{
path: 'checkout/:cartId/:addressId',
loadChildren: () => import('./pages/checkout/checkout.module').then(m => m.CheckoutPageModule)
},


// in Component file


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


constructor(
private _Router: ActivatedRoute
) { }


ngOnInit() {
this.cartId = this._Router.snapshot.params.cartId;
this.addressId = this._Router.snapshot.params.addressId;
console.log(this.addressId, "addressId")
console.log(this.cartId, "cartId")
}

查询和路径参数(Angular 8)

对于像https://myapp.com/user/666/read?age=23这样的url使用

import { combineLatest } from 'rxjs';
// ...


combineLatest( [this.route.paramMap, this.route.queryParamMap] )
.subscribe( ([pathParams, queryParams]) => {
let userId = pathParams.get('userId');    // =666
let age    = queryParams.get('age');      // =23
// ...
})

更新

如果你使用this.router.navigate([someUrl]);并且你的查询参数被嵌入到someUrl字符串中,那么angular会对URL进行编码,你会得到类似https://myapp.com/user/666/read%3Fage%323的东西——以上解决方案将会给出错误的结果(queryParams将为空,如果路径参数在路径端,路径参数可以粘在最后一个路径参数上)。在这种情况下,改变导航方式这个

this.router.navigateByUrl(someUrl);

我认为是Angular 8:

ActivatedRoute.params已被ActivatedRoute.paramMap取代 ActivatedRoute.queryParams已被ActivatedRoute.queryParamMap

取代

Angular 路由器提供了方法< em > parseUrl (url:字符串)< / em >,该方法将url解析为UrlTree。UrlTree的一个属性是queryParams。所以你可以这样做:

this.router.parseUrl(this.router.url).queryParams[key] || '';

这对我很管用。我已经在路由模块中使用了子路由。


this.route.firstChild.snapshot.paramMap.get('id');
   

最好的解决方案是使用ActivatedRoute:

    constructor(private route: ActivatedRoute) {}
    

ngOnInit(): void {
this.route.queryParams.subscribe((params) => {
console.log(params);
const queryparams = params['queryName'];
});
}