-
Notifications
You must be signed in to change notification settings - Fork 1
onRouterReuse implementation #1
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -8,4 +8,4 @@ | |
</li> | ||
</ul> | ||
|
||
<router-outlet appRouteReuseLifecycle></router-outlet> | ||
<router-outlet></router-outlet> |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -2,28 +2,21 @@ import {Component, OnDestroy} from '@angular/core'; | |
import {FormControl, FormGroup} from '@angular/forms'; | ||
import {BindQueryParamsFactory} from '@ngneat/bind-query-params'; | ||
import {of} from 'rxjs'; | ||
import {delay, tap} from 'rxjs/operators'; | ||
import {OnAttach} from '../directives/route-reuse-life-cycle.directive'; | ||
import {delay, filter, take, tap} from 'rxjs/operators'; | ||
import {OnRouterReuse} from "../onRouterReuse"; | ||
import {NavigationEnd, Router} from "@angular/router"; | ||
|
||
@Component({ | ||
template: ` | ||
|
||
<h2>My form!</h2> | ||
<label for="keep-data"> | ||
Keep form data | ||
<input style="display: inline" | ||
[(ngModel)]="keepFormData" | ||
id="keep-data" type="checkbox"> | ||
</label> | ||
|
||
<h3>Loaded at: {{loadedAt}}</h3> | ||
<h4>Slow request: | ||
{{ slowRequest$ | async }} | ||
<app-spinner *ngIf="showSpinner"></app-spinner> | ||
</h4> | ||
|
||
<p style="font-family: 'Courier New',sans-serif"> | ||
{{form.value | json}} keep={{ keepFormData }} | ||
{{form.value | json}} | ||
</p> | ||
|
||
<form [formGroup]="form" autocomplete="off"> | ||
|
@@ -67,9 +60,8 @@ import {OnAttach} from '../directives/route-reuse-life-cycle.directive'; | |
` | ||
] | ||
}) | ||
export class MyFormComponent implements OnDestroy, OnAttach { | ||
export class MyFormComponent implements OnDestroy, OnRouterReuse { | ||
showSpinner = true; | ||
keepFormData = true; | ||
|
||
slowRequest$ = of('A SERVER MESSAGE').pipe( | ||
delay(5000), | ||
|
@@ -87,23 +79,22 @@ export class MyFormComponent implements OnDestroy, OnAttach { | |
]).connect(this.form); | ||
loadedAt: number; | ||
|
||
constructor(private factory: BindQueryParamsFactory) { | ||
constructor(private factory: BindQueryParamsFactory, | ||
private router: Router) { | ||
this.loadedAt = Date.now(); | ||
} | ||
|
||
ngOnDestroy(): void { | ||
this.manager.destroy(); | ||
onRouterReuse(): void { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Added a callback function named Then I call a private function updateQueryParams with the form value. |
||
this.router.events.pipe(filter((e): e is NavigationEnd => e instanceof NavigationEnd), | ||
take(1)) | ||
.subscribe(() => { | ||
// @ts-ignore | ||
this.manager.updateQueryParams(this.form.value); | ||
}) | ||
} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nice I like it! It'd be great if a default implementation could be provided somehow (to reduce the boilerplate later) onRouterReuse(): void {
this.router.events.pipe(filter((e): e is NavigationEnd => e instanceof NavigationEnd),
take(1))
.subscribe(() => {
// yield here, code specific to a component
})
} I'm not sure how to go about this. The closest I got was this ugly thing: // OnRouterReuseImpl.ts
export class OnRouterReuseImpl {
fn?: () => void;
constructor(private router: Router) {
}
onRouterReuse(): void {
this.router.events.pipe(filter((e): e is NavigationEnd => e instanceof NavigationEnd),
take(1))
.subscribe(() => {
if (this.fn) {
this.fn();
}
})
}
}
// my-form.component.ts
private routeReuse: OnRouterReuseImpl;
constructor(private factory: BindQueryParamsFactory,
private router: Router) {
this.routeReuse = new OnRouterReuseImpl(router);
this.routeReuse.fn = () => {
// @ts-ignore
this.manager.updateQueryParams(this.form.value);
}
}
onRouterReuse(): void {
this.routeReuse.onRouterReuse();
} There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Unfortunately, I didn't manage to add There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 👍 I’m finding using a custom route reuse strategy quite tricky in practice. And having two events (attached/detached) seems to be quite useful for the app I’m working on. Thanks for your input though, I’ll have to think it some more :) |
||
|
||
onAttach(): void { | ||
console.log('ON ATTACH!!', this.form.value); | ||
// this.manager.syncAllDefs(); // does not work | ||
|
||
if (this.keepFormData) { | ||
this.form.setValue(this.form.value); // forces form<>URL sync | ||
} else { | ||
this.form.reset(); // Or reset the form | ||
} | ||
ngOnDestroy(): void { | ||
this.manager.destroy(); | ||
} | ||
|
||
refreshNav() { | ||
|
This file was deleted.
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
export declare interface OnRouterReuse { | ||
onRouterReuse: () => void; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
handle type isn't implemented correctly so I'm wrapping it in @ts-ignore.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Interesting. I'm curious as to how you found this private API (via debugger?)
I can only access the public API with my IDE (IntelliJ points me to
d.ts
files)If you have tips to get access the underlying Angular code I'm all ears :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm just familiar with bind-query-param repo... You can see it with debuggers or just look into its source code...
Of course that this is just a POC... You need to open a detailed issue for bind-query-param repo explaining the issue and asking for making it public (Calling it directly won't work for controls that uses a special URL parser...)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Got ya, thanks :)