From 4c912d29a3f4eeb64fc59220f81c7c866d765fd3 Mon Sep 17 00:00:00 2001 From: Mike Ryan Date: Mon, 26 Sep 2016 07:24:50 -0500 Subject: [PATCH] feat(testing): Add testing module for easily mocking out actions --- README.md | 40 ++++++++++++++++++++++++++++++++++++++- testing/index.ts | 2 ++ testing/runner.ts | 14 ++++++++++++++ testing/testing.module.ts | 16 ++++++++++++++++ 4 files changed, 71 insertions(+), 1 deletion(-) create mode 100644 testing/index.ts create mode 100644 testing/runner.ts create mode 100644 testing/testing.module.ts diff --git a/README.md b/README.md index 8e297b5..d38f0c3 100644 --- a/README.md +++ b/README.md @@ -62,4 +62,42 @@ To help you compose new action sources, @ngrx/effects exports an `Actions` obser ### Testing Effects -WIP + +1. Declare the `EffectsTestingModule` in your testing module: + ```ts + import { EffectsTestingModule, EffectsTestRunner } from '@ngrx/effects'; + + describe('My Effect', () => { + beforeEach(() => TestBed.configureTestingModule({ + imports: [ + EffectsTestingModule + ], + declarations: [ + AuthEffects + ] + })); + }); + ``` + +2. Inject the `EffectsTestRunner` and use it queue actions: + ```ts + let runner: EffectsTestRunner; + + beforeEach(inject([ + EffectsTestRunner, + (_runner) => { + runner = _runner; + } + ])); + ``` + +3. Queue up actions then subscribe to the effect you want to test, asserting on the result: + ```ts + it('should return a LOGIN_SUCCESS action after logging in', () => { + runner.queue({ type: 'LOGIN' }); + + authEffects.login$.subscribe(result => { + expect(result).toEqual({ type: 'LOGIN_SUCCESS' }); + }); + }); + ``` diff --git a/testing/index.ts b/testing/index.ts new file mode 100644 index 0000000..1437159 --- /dev/null +++ b/testing/index.ts @@ -0,0 +1,2 @@ +export * from './runner'; +export * from './testing.module'; diff --git a/testing/runner.ts b/testing/runner.ts new file mode 100644 index 0000000..0d23b76 --- /dev/null +++ b/testing/runner.ts @@ -0,0 +1,14 @@ +import { Injectable } from '@angular/core'; +import { ReplaySubject } from 'rxjs/ReplaySubject'; + + +@Injectable() +export class EffectsTestRunner extends ReplaySubject { + constructor() { + super(); + } + + queue(action: any) { + this.next(action); + } +} diff --git a/testing/testing.module.ts b/testing/testing.module.ts new file mode 100644 index 0000000..afcda1d --- /dev/null +++ b/testing/testing.module.ts @@ -0,0 +1,16 @@ +import { NgModule } from '@angular/core'; +import { Actions } from '../src/actions'; +import { EffectsTestRunner } from './runner'; + + +export function _createActions(runner: EffectsTestRunner): Actions { + return new Actions(runner); +} + +@NgModule({ + providers: [ + EffectsTestRunner, + { provide: Actions, deps: [ EffectsTestRunner ], useFactory: _createActions } + ] +}) +export class EffectsTestingModule { }