Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
448 views
in Technique[技术] by (71.8m points)

routing - Testing Angular 2 parent route

I have a component that accesses a parent route value like this:

  ngOnInit() {
    this.route.parent.parent.params.subscribe(params => {
      this.placeService.getPlace(params['id']).subscribe(place => this.place = place);
    });
  }

Here's the full file in case it helps.

import { Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
import { PlaceService } from '../place.service';
import { Place } from '../place';

@Component({
  selector: 'app-diner-review-list',
  templateUrl: './diner-review-list.component.html',
  styleUrls: ['./diner-review-list.component.css'],
  providers: [PlaceService]
})
export class DinerReviewListComponent implements OnInit {
  place: Place;

  constructor(private route: ActivatedRoute, private placeService: PlaceService) { }

  ngOnInit() {
    this.route.parent.parent.params.subscribe(params => {
      this.placeService.getPlace(params['id']).subscribe(place => this.place = place);
    });
  }
}

My issue is that when I run the test I get

TypeError: Cannot read property 'parent' of null

This makes sense. this.route.parent is null. But I don't care about that; I'm not testing the route right now.

Here's my test:

/* tslint:disable:no-unused-variable */
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { RouterTestingModule } from '@angular/router/testing';
import { By } from '@angular/platform-browser';
import { DebugElement } from '@angular/core';
import { MockPlaceService } from '../../../testing/mock-place.service';

import { DinerReviewListComponent } from './diner-review-list.component';
import { PlaceService } from '../place.service';

let mockPlaceService = new MockPlaceService();

describe('DinerReviewListComponent', () => {
  let component: DinerReviewListComponent;
  let fixture: ComponentFixture<DinerReviewListComponent>;

  beforeEach(async(() => {
    TestBed.configureTestingModule({
      declarations: [
        DinerReviewListComponent
      ],
      imports: [RouterTestingModule]
    })
    .overrideComponent(DinerReviewListComponent, {
      set: {
        providers: [
          { provide: PlaceService, useValue: mockPlaceService }
        ]
      }
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(DinerReviewListComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

  it('should create', () => {
    expect(component).toBeTruthy();
  });
});

How can I get my test to either disregard the absent route value or provide a fake one?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

I ended up solving it the latter way: providing a fake route. Here's what I did.

Pay attention to the parts that mention mockActivatedRoute.

/* tslint:disable:no-unused-variable */
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { RouterTestingModule } from '@angular/router/testing';
import { ActivatedRoute } from '@angular/router';
import { By } from '@angular/platform-browser';
import { DebugElement } from '@angular/core';
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/observable/of';

import { MockPlaceService } from '../../../testing/mock-place.service';

import { DinerReviewListComponent } from './diner-review-list.component';
import { PlaceService } from '../place.service';

let mockPlaceService = new MockPlaceService();

class MockActivatedRoute {
  parent: any;
  params: any;

  constructor(options) {
    this.parent = options.parent;
    this.params = options.params;
  }
}

let mockActivatedRoute = new MockActivatedRoute({
  parent: new MockActivatedRoute({
    parent: new MockActivatedRoute({
      params: Observable.of({ id: '1' })
    })
  })
});

describe('DinerReviewListComponent', () => {
  let component: DinerReviewListComponent;
  let fixture: ComponentFixture<DinerReviewListComponent>;

  beforeEach(async(() => {
    TestBed.configureTestingModule({
      declarations: [
        DinerReviewListComponent
      ],
      imports: [RouterTestingModule]
    })
    .overrideComponent(DinerReviewListComponent, {
      set: {
        providers: [
          { provide: PlaceService, useValue: mockPlaceService },
          { provide: ActivatedRoute, useValue: mockActivatedRoute }
        ]
      }
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(DinerReviewListComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

  it('should create', () => {
    expect(component).toBeTruthy();
  });
});

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...