import {Component} from '@angular/core'; import {ComponentFixture, TestBed} from '@angular/core/testing'; import {ReactiveFormsModule, FormGroup, FormControl, Validators} from '@angular/forms'; import {HarnessLoader, parallel} from '@angular/cdk/testing'; import {TestbedHarnessEnvironment} from '@angular/cdk/testing/testbed'; import {MatStepperModule} from '@angular/material/stepper'; import {STEPPER_GLOBAL_OPTIONS} from '@angular/cdk/stepper'; import {NoopAnimationsModule} from '@angular/platform-browser/animations'; import {MatStepperHarness} from './stepper-harness'; import {MatStepperNextHarness, MatStepperPreviousHarness} from './stepper-button-harnesses'; import {StepperOrientation} from './step-harness-filters'; describe('MatStepperHarness', () => { let fixture: ComponentFixture; let loader: HarnessLoader; beforeEach(() => { TestBed.configureTestingModule({ imports: [MatStepperModule, NoopAnimationsModule, ReactiveFormsModule, StepperHarnessTest], providers: [ { provide: STEPPER_GLOBAL_OPTIONS, useValue: {showError: true}, // Required so the error state shows up in tests. }, ], }); fixture = TestBed.createComponent(StepperHarnessTest); fixture.detectChanges(); loader = TestbedHarnessEnvironment.loader(fixture); }); it('should load all stepper harnesses', async () => { const steppers = await loader.getAllHarnesses(MatStepperHarness); expect(steppers.length).toBe(3); }); it('should filter steppers by their orientation', async () => { const [verticalSteppers, horizontalSteppers] = await parallel(() => [ loader.getAllHarnesses(MatStepperHarness.with({orientation: StepperOrientation.VERTICAL})), loader.getAllHarnesses(MatStepperHarness.with({orientation: StepperOrientation.HORIZONTAL})), ]); expect(verticalSteppers.length).toBe(2); expect(horizontalSteppers.length).toBe(1); }); it('should get the orientation of a stepper', async () => { const steppers = await loader.getAllHarnesses(MatStepperHarness); expect(await parallel(() => steppers.map(stepper => stepper.getOrientation()))).toEqual([ StepperOrientation.VERTICAL, StepperOrientation.HORIZONTAL, StepperOrientation.VERTICAL, ]); }); it('should get the steps of a stepper', async () => { const steppers = await loader.getAllHarnesses(MatStepperHarness); const steps = await parallel(() => steppers.map(stepper => stepper.getSteps())); expect(steps.map(current => current.length)).toEqual([4, 3, 2]); }); it('should filter the steps of a stepper', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps({label: /Two|Four/}); expect(await parallel(() => steps.map(step => step.getLabel()))).toEqual(['Two', 'Four']); }); it('should be able to select a particular step that matches a filter', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ true, false, false, false, ]); await stepper.selectStep({label: 'Three'}); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ false, false, true, false, ]); }); it('should be able to get the text-based label of a step', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.getLabel()))).toEqual([ 'One', 'Two', 'Three', 'Four', ]); }); it('should be able to get the template-based label of a step', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#two-stepper'})); const steps = await stepper.getSteps(); expect( await parallel(() => { return steps.map(step => step.getLabel()); }), ).toEqual(['One', 'Two', 'Three']); }); it('should be able to get the aria-label of a step', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.getAriaLabel()))).toEqual([ null, null, null, 'Fourth step', ]); }); it('should be able to get the aria-labelledby of a step', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.getAriaLabelledby()))).toEqual([ null, null, 'some-label', null, ]); }); it('should get the selected state of a step', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ true, false, false, false, ]); }); it('should be able to select a step', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ true, false, false, false, ]); await steps[2].select(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ false, false, true, false, ]); }); it('should get whether a step is optional', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#two-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.isOptional()))).toEqual([false, true, true]); }); it('should be able to get harness loader for an element inside a tab', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const [step] = await stepper.getSteps({label: 'Two'}); const [nextButton, previousButton] = await parallel(() => [ step.getHarness(MatStepperNextHarness), step.getHarness(MatStepperPreviousHarness), ]); expect(await nextButton.getText()).toBe('Next'); expect(await previousButton.getText()).toBe('Previous'); }); it('should go forward when pressing the next button', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); const secondStep = steps[1]; const nextButton = await secondStep.getHarness(MatStepperNextHarness); await secondStep.select(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ false, true, false, false, ]); await nextButton.click(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ false, false, true, false, ]); }); it('should go backward when pressing the previous button', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#one-stepper'})); const steps = await stepper.getSteps(); const secondStep = steps[1]; const previousButton = await secondStep.getHarness(MatStepperPreviousHarness); await secondStep.select(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ false, true, false, false, ]); await previousButton.click(); expect(await parallel(() => steps.map(step => step.isSelected()))).toEqual([ true, false, false, false, ]); }); it('should get whether a step has errors', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#three-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.hasErrors()))).toEqual([false, false]); await steps[1].select(); expect(await parallel(() => steps.map(step => step.hasErrors()))).toEqual([true, false]); }); it('should get whether a step has been completed', async () => { const stepper = await loader.getHarness(MatStepperHarness.with({selector: '#three-stepper'})); const steps = await stepper.getSteps(); expect(await parallel(() => steps.map(step => step.isCompleted()))).toEqual([false, false]); fixture.componentInstance.oneGroup.setValue({oneCtrl: 'done'}); await steps[1].select(); expect(await parallel(() => steps.map(step => step.isCompleted()))).toEqual([true, false]); }); }); @Component({ template: ` One Two Three
`, standalone: true, imports: [MatStepperModule, ReactiveFormsModule], }) class StepperHarnessTest { oneGroup = new FormGroup({ oneCtrl: new FormControl('', Validators.required), }); twoGroup = new FormGroup({ twoCtrl: new FormControl('', Validators.required), }); }