Skip to content

Commit

Permalink
test(navigation-plan): add tests for navigation plan and activation s…
Browse files Browse the repository at this point in the history
…trategy
  • Loading branch information
bryanrsmith committed Dec 24, 2015
1 parent 70789d7 commit c6af5d1
Show file tree
Hide file tree
Showing 3 changed files with 175 additions and 27 deletions.
37 changes: 10 additions & 27 deletions test/activation.spec.js
Expand Up @@ -3,6 +3,7 @@ import {
CanActivateNextStep
} from '../src/activation';
import {activationStrategy} from '../src/navigation-plan';
import {createPipelineState} from './test-util';

describe('activation', () => {
describe('CanDeactivatePreviousStep', () => {
Expand All @@ -18,7 +19,7 @@ describe('activation', () => {

beforeEach(() => {
step = new CanDeactivatePreviousStep();
state = getState();
state = createPipelineState();
});

it('should return true for context that canDeactivate', () => {
Expand All @@ -39,7 +40,7 @@ describe('activation', () => {
let instruction = { plan: { first: viewPortFactory(() => (false)) } };

step.run(instruction, state.next);
expect(state.result).toBe('cancel');
expect(state.rejection).toBeTruthy();
});

it('should return true for context that cannot Deactivate with unknown strategy', () => {
Expand All @@ -63,7 +64,7 @@ describe('activation', () => {
let instruction = { plan: {first: viewPortFactory(() => (Promise.resolve(false))) } };

step.run(instruction, state.next).then(() => {
expect(state.result).toBe('cancel');
expect(state.rejection).toBeTruthy();
done();
});
});
Expand All @@ -72,7 +73,7 @@ describe('activation', () => {
let instruction = { plan: {first: viewPortFactory(() => { throw new Error('oops'); }) } };

step.run(instruction, state.next).then(() => {
expect(state.result).toBe('cancel');
expect(state.rejection).toBeTruthy();
done();
});
});
Expand All @@ -88,7 +89,7 @@ describe('activation', () => {
let instruction = { plan: {first: viewPortFactory(() => (true)), second: viewPortFactory(() => (false))} };

step.run(instruction, state.next);
expect(state.result).toBe('cancel');
expect(state.rejection).toBeTruthy();
});

describe('with a childNavigationInstruction', () => {
Expand All @@ -109,7 +110,7 @@ describe('activation', () => {
viewPort.childNavigationInstruction = { plan: { first: viewPortFactory(() => (false)) } };

step.run(instruction, state.next);
expect(state.result).toBe('cancel');
expect(state.rejection).toBeTruthy();
});
});

Expand All @@ -133,7 +134,7 @@ describe('activation', () => {
instruction.plan = { first: viewPort };

step.run(instruction, state.next);
expect(state.result).toBe('cancel');
expect(state.rejection).toBeTruthy();
});
});
});
Expand All @@ -159,7 +160,7 @@ describe('activation', () => {

beforeEach(() => {
step = new CanActivateNextStep();
state = getState();
state = createPipelineState();
});

it('should return true for context that canActivate', () => {
Expand All @@ -180,25 +181,7 @@ describe('activation', () => {
let instruction = getNavigationInstruction(() => (false));

step.run(instruction, state.next);
expect(state.result).toBe('cancel');
expect(state.rejection).toBeTruthy();
});
});
});

function getState() {
let nextResult = null;
let next = () => {
nextResult = true;
return Promise.resolve(nextResult);
};

next.cancel = () => {
nextResult = 'cancel';
return Promise.resolve(nextResult);
};

return {
next,
get result() { return nextResult; }
};
}
145 changes: 145 additions & 0 deletions test/navigation-plan.spec.js
@@ -0,0 +1,145 @@
import {BuildNavigationPlanStep} from '../src/navigation-plan';
import {NavigationInstruction} from '../src/navigation-instruction';
import {Redirect} from '../src/navigation-commands';
import {createPipelineState} from './test-util';

describe('NavigationPlanStep', () => {
let step;
let state;
let redirectInstruction;
let firstInstruction;
let sameAsFirstInstruction;
let secondInstruction;

beforeEach(() => {
step = new BuildNavigationPlanStep();
state = createPipelineState();

redirectInstruction = new NavigationInstruction({
fragment: 'first',
queryString: 'q=1',
config: { redirect: 'second' }
});

firstInstruction = new NavigationInstruction({
fragment: 'first',
config: { viewPorts: { default: { moduleId: './first' }}},
params: { id: '1' }
});

sameAsFirstInstruction = new NavigationInstruction({
fragment: 'first',
config: { viewPorts: { default: { moduleId: './first' }}},
previousInstruction: firstInstruction,
params: { id: '1' }
});

secondInstruction = new NavigationInstruction({
fragment: 'second',
config: { viewPorts: { default: { moduleId: './second' }}},
previousInstruction: firstInstruction
});
});

it('cancels on redirect configs', (done) => {
step.run(redirectInstruction, state.next)
.then(e => {
expect(state.rejection).toBeTruthy();
expect(e instanceof Redirect).toBe(true);
expect(e.url).toBe('#/second?q=1');
done();
});
});

describe('generates navigation plans', () => {
it('with no prev step', (done) => {
step.run(firstInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(firstInstruction.plan).toBeTruthy();
done();
});
});

it('with prev step', (done) => {
step.run(secondInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(secondInstruction.plan).toBeTruthy();
done();
});
});

it('with prev step with viewport', (done) => {
firstInstruction.addViewPortInstruction('default', 'no-change', './first', {});

step.run(secondInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(secondInstruction.plan).toBeTruthy();
done();
});
});
});

describe('activation strategy', () => {
it('is replace when moduleId changes', (done) => {
firstInstruction.addViewPortInstruction('default', 'no-change', './first', {});

step.run(secondInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(secondInstruction.plan.default.strategy).toBe('replace');
done();
});
});

it('is no-change when nothing changes', (done) => {
firstInstruction.addViewPortInstruction('default', 'ignored', './first', { viewModel: {}});

step.run(sameAsFirstInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(sameAsFirstInstruction.plan.default.strategy).toBe('no-change');
done();
});
});

it('can be determined by route config', (done) => {
sameAsFirstInstruction.config.activationStrategy = 'fake-strategy';
firstInstruction.addViewPortInstruction('default', 'ignored', './first', { viewModel: {}});

step.run(sameAsFirstInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(sameAsFirstInstruction.plan.default.strategy).toBe('fake-strategy');
done();
});
});

it('can be determined by view model', (done) => {
let viewModel = { determineActivationStrategy: () => 'vm-strategy'};
firstInstruction.addViewPortInstruction('default', 'ignored', './first', { viewModel });

step.run(sameAsFirstInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(sameAsFirstInstruction.plan.default.strategy).toBe('vm-strategy');
done();
});
});

it('is invoke-lifecycle when only params change', (done) => {
firstInstruction.params = { id: '1' };
sameAsFirstInstruction.params = { id: '2' };
firstInstruction.addViewPortInstruction('default', 'ignored', './first', { viewModel: {}});

step.run(sameAsFirstInstruction, state.next)
.then(() => {
expect(state.result).toBe(true);
expect(sameAsFirstInstruction.plan.default.strategy).toBe('invoke-lifecycle');
done();
});
});
});
});
20 changes: 20 additions & 0 deletions test/test-util.js
@@ -0,0 +1,20 @@
export function createPipelineState() {
let nextResult = null;
let cancelResult = null;

let next = () => {
nextResult = true;
return Promise.resolve(nextResult);
};

next.cancel = (rejection) => {
cancelResult = rejection || 'cancel';
return Promise.resolve(cancelResult);
};

return {
next,
get result() { return nextResult; },
get rejection() { return cancelResult; }
};
}

0 comments on commit c6af5d1

Please sign in to comment.