Wednesday, April 4, 2018

Resolve in the Angular 4 paradigm should allow you to hand state on to a component.

Assuming a routing module like so:

import { Routes, RouterModule } from '@angular/router';
import { NgModule } from '@angular/core';
import { WhateverComponent } from './components/whatever.component';
import { WhateverResolverService } from './services/whatever-resolver.service';
export const PlanRoutes: Routes = [
   {
      path: 'yin/:yang',
      component: WhateverComponent,
      resolve: {
         'whateverResolver': WhateverResolverService
      }
   }
];
@NgModule({
   imports: [
      RouterModule.forChild(PlanRoutes)
   ],
   exports: [RouterModule]
})
export class WhateverRoutesModule { }

 
 

One should be able to have a WhateverResolverService to hand a DataContext, fished out of an NgRx store, on to WhateverComponent by crafting something like this:

import { DataContext } from '../../../../whatever/data-models';
import { WhateverAction, getStuff } from '../../../../whatever/store';
import { Observable } from 'rxjs/observable';
import { Injectable } from '@angular/core';
import { ActivatedRouteSnapshot, Resolve, Router, RouterStateSnapshot } from '@angular/router';
import { Store } from '@ngrx/store';
import 'rxjs/add/operator/take';
@Injectable()
export class WhateverResolverService implements Resolve<any> {
   constructor(private router: Router, private store: Store<DataContext>) { }
   
   resolve(route: ActivatedRouteSnapshot, state: RouterStateSnapshot):
         Observable<any> {
      const yang = route.params["yang"];
      this.store.dispatch(new WhateverAction(yang));
      return this.store.select(getStuff).take(1);
   }
}

 
 

You will notice that we make use of the yang parameter to go fishing for our data. I was surprised to see that this not like the typical routing snapshot which represents how the route first was and will not reflect updates. Instead, every time the route changes, the resolver will run once. Nice! At the constructor of WhateverComponent we could have something like private store: Store<DataContext> to catch what the resolver hands in. This is an example of a long lingering Observable too. The only one I have every used myself. For all of talk of how one could use an Observable to listen at a web socket and be constantly updated, for the most part I have just interacted with API endpoints and have only done things with Observables that could be done with promises. This is the next level stuff. Forgive the use of "next level" as I know that's all-too-modern slang. WhateverResolverService needs to be looped in at providers at the applicable module.

 
 

Addendum 4/5/2018: What I say above out catching a DataContext at the constructor of the component is wrong. Sorry, I am dealing with an NgRx store at work. Instead you could have a component constructor as follows and do note the reuse of "whateverResolver" too.

constructor(private activatedRoute: ActivatedRoute) {
   this.activatedRoute.data.subscribe(theCaught => {
      console.log('look at this:');
      console.log(theCaught.whateverResolver);
   });
}

 
 

If this were the end of the resolver...

      const simpleObservable = new Observable((observer) => {
         observer.next({ 'foo': 'bar', 'baz': 'qux' });
         observer.complete();
      });
      return simpleObservable;
   }
}

 
 

...then we would be able to log to the console the foo/bar/baz/qux object alright in this approach.

No comments:

Post a Comment