可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I use angular2.0.0-beta.7. When a component is loaded on path like "/path?query=value1" it is redirected to "/path". Why was GET params deleted? How can I preserve params?
I have an error in routers. If I have a main route like
@RouteConfig([
{
path: '/todos/...',
name: 'TodoMain',
component: TodoMainComponent
}
])
and my child route like
@RouteConfig([
{ path: '/', component: TodoListComponent, name: 'TodoList', useAsDefault:true },
{ path: '/:id', component: TodoDetailComponent, name:'TodoDetail' }
])
I cant get params in TodoListComponent.
I can get matrix
params("/my/path;param1=value1;param2=value2")
but I want classic
query params("/my/path?param1=value1¶m2=value2")
回答1:
By injecting an instance of ActivatedRoute
one can subscribe to a variety of observables, including a queryParams
and a params
observable:
import {Router, ActivatedRoute, Params} from '@angular/router';
import {OnInit, Component} from '@angular/core';
@Component({...})
export class MyComponent implements OnInit {
constructor(private activatedRoute: ActivatedRoute) {}
ngOnInit() {
// Note: Below 'queryParams' can be replaced with 'params' depending on your requirements
this.activatedRoute.queryParams.subscribe(params => {
const userId = params['userId'];
console.log(userId);
});
}
}
A NOTE REGARDING UNSUBSCRIBING
@Reto and @codef0rmer had quite rightly pointed out that, as per the official docs, an unsubscribe()
inside the components onDestroy()
method is unnecessary in this instance. This has been removed from my code sample. (see the Do I need to unsubscribe? section of this tutorial)
回答2:
When an URL like this
http://stackoverflow.com?param1=value
You can get the param1 by code follow:
import { Component, OnInit } from '@angular/core';
import { Router, ActivatedRoute, Params } from '@angular/router';
@Component({
selector: '',
templateUrl: './abc.html',
styleUrls: ['./abc.less']
})
export class AbcComponent implements OnInit {
constructor(private route: ActivatedRoute) { }
ngOnInit() {
// get param
let param1 = this.route.snapshot.queryParams["param1"];
}
}
回答3:
Even though the question specifies version beta 7, this question also comes up as top search result on Google for common phrases like angular 2 query parameters. For that reason here's an answer for the newest router (currently in alpha.7).
The way the params are read has changed dramatically. First you need to inject dependency called Router
in your constructor parameters like:
constructor(private router: Router) { }
and after that we can subscribe for the query parameters on our ngOnInit
method (constructor is okay too, but ngOnInit
should be used for testability) like
this.router
.routerState
.queryParams
.subscribe(params => {
this.selectedId = +params['id'];
});
In this example we read the query param id from URL like example.com?id=41
.
There are still few things to notice:
- Accessing property of
params
like params['id']
always returns a string, and this can be converted to number by prefixing it with +
.
- The reason why the query params are fetched with observable is that it allows re-using the same component instance instead of loading a new one. Each time query param is changed, it will cause a new event that we have subscribed for and thus we can react on changes accordingly.
回答4:
I really liked @StevePaul's answer but we can do the same without extraneous subscribe/unsubscribe call.
import { ActivatedRoute } from '@angular/router';
constructor(private activatedRoute: ActivatedRoute) {
let params: any = this.activatedRoute.snapshot.params;
console.log(params.id);
// or shortcut Type Casting
// (<any> this.activatedRoute.snapshot.params).id
}
回答5:
To send query params
import { Router } from '@angular/router';
this.router.navigate([ '/your-route' ], { queryParams: { key: va1, keyN: valN } });
To receive query params
import { ActivatedRoute } from '@angular/router';
this.activatedRoute.queryParams.subscribe(params => {
let value_1 = params['key'];
let value_N = params['keyN'];
});
Official source
回答6:
Hi you can use URLSearchParams, you can read more about it here.
import:
import {URLSearchParams} from "@angular/http";
and function:
getParam(){
let params = new URLSearchParams(window.location.search);
let someParam = params.get('someParam');
return someParam;
}
Notice: It's not supported by all platforms and seems to be in "EXPERIMENTAL" state by angular docs
回答7:
First off, what I have found working with Angular2 is that the url with a query string would be /path;query=value1
To access it in a component you use
So is this, but now follows a code block:
constructor(params: RouteParams){
var val = params.get("query");
}
As to why it would be removed when you load the component, that isn't default behavior. I checked specificly in a clean test project and wasn't redirected or changed. Is it a default route or something else that is special about the routing?
Read about routing with query strings and params in the Angular2 Tutorial at https://angular.io/docs/ts/latest/guide/router.html#!#query-parameters
回答8:
You can get the query parameters when passed in URL using ActivatedRoute as stated below:-
url:- http:/domain.com?test=abc
import { Component } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
@Component({
selector: 'my-home'
})
export class HomeComponent {
constructor(private sharedServices : SharedService,private route: ActivatedRoute) {
route.queryParams.subscribe(
data => console.log('queryParams', data['test']));
}
}
回答9:
Get URL param as an object.
import { Router } from '@angular/router';
constructor(private router: Router) {
console.log(router.parseUrl(router.url));
}
回答10:
If you only want to get query parameter once, the best way is to use take method so you do not need to worry about unsubscription.
Here is the simple snippet:-
constructor(private route: ActivatedRoute) {
route.snapshot.queryParamMap.take(1).subscribe(params => {
let category = params.get('category')
console.log(category);
})
}
Note: Remove take(1) if you want to use parameter values in future.
回答11:
now it is:
this.activatedRoute.queryParams.subscribe((params: Params) => {
console.log(params);
});
回答12:
I hope it will help someone else.
Question above states that query param value is needed after page has been redirected and we can assume that snapshot value (the no-observable alternative) would be sufficient.
No one here mentioned about snapshot.paramMap.get from the official documentation.
this.route.snapshot.paramMap.get('id')
So before sending it add this in sending/re-directing component:
import { Router } from '@angular/router';
then re-direct as either (documented here):
this.router.navigate(['/heroes', { id: heroId, foo: 'foo' }]);
or simply:
this.router.navigate(['/heroes', heroId ]);
Make sure you have added this in your routing module as documented here:
{ path: 'hero/:id', component: HeroDetailComponent }
And finally, in your component which needs to use the query param
add imports (documented here):
import { Router, ActivatedRoute, ParamMap } from '@angular/router';
inject ActivatedRoute
( documentation also imports switchMap and also injects Router and HeroService - but they are needed for observable alternative only - they are NOT needed when you use snapshot alternative as in our case ):
constructor(
private route: ActivatedRoute
) {}
NOTE: IF YOU ADD ROUTING-MODULE TO A FEATURE MODULE (AS SHOWN IN DOCUMENTATION) MAKE SURE THAT IN APP.MODULE.ts THAT ROUTING MODULE COMES BEFORE AppRoutingModule (or other file with root-level app routes) IN IMPORTS: [] . OTHERWISE FEATURE ROUTES WILL NOT BE FOUND (AS THEY WOULD COME AFTER { path: '**', redirectTo: '/not-found' } and you would see only not-found message).
回答13:
You cannot get a parameter from the RouterState if it's not defined in the route, so in your example, you have to parse the querystring...
Here is the code I used:
let re = /[?&]([^=#&]+)=([^&#]*)/g;
let match;
let isMatch = true;
let matches = [];
while (isMatch) {
match = re.exec(window.location.href);
if (match !== null) {
matches[decodeURIComponent(match[1])] = decodeURIComponent(match[2]);
if (match.index === re.lastIndex) {
re.lastIndex++;
}
}
else {
isMatch = false;
}
}
console.log(matches);
回答14:
A variation on Steve Paul's solution, I prefer to avoid unnecessary ivars, so to remove the need for the unsubscribe()
call during ngOnDestroy
, just subscribe to the observable with take(1)
and it will be automatically released after the first value - preventing memory leaks
import 'rxjs/add/operator/take';
import {Router, ActivatedRoute} from '@angular/router';
@Component({...})
export class MyComponent implements OnInit {
constructor(private activatedRoute: ActivatedRoute) {
this.activatedRoute.params.take(1).subscribe((params: any) => {
let userId = params['userId'];
console.log(userId);
});
}
}
回答15:
You just need to inject ActivatedRoute in constructor and then just access params or queryParams over it
constructor(private route:AcitvatedRoute){}
ngOnInit(){
this.route.queryParams.subscribe(params=>{
let username=params['username'];
});
}
In Some cases it doesn give anything in NgOnInit ...may be because of init call before initilization of params in this case you can achieve this by asking observable to wait for some time by function debounceTime(1000)
e.g=>
constructor(private route:AcitvatedRoute){}
ngOnInit(){
this.route.queryParams.debounceTime(100).subscribe(params=>{
let username=params['username'];
});
}
debounceTime() Emits a value from source observable only after perticular time span passed without another source emission