Created
June 1, 2020 22:08
-
-
Save LayZeeDK/3e80b507b31089da1bc9b5db07c1519f to your computer and use it in GitHub Desktop.
Hero detail: Integrated routed component test suite.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<div *ngIf="hero"> | |
<h2> | |
{{hero.name | uppercase}} Details | |
</h2> | |
<div> | |
<span>id:</span> | |
{{hero.id}} | |
</div> | |
<div> | |
<label> | |
name: | |
<input [(ngModel)]="hero.name" placeholder="name"> | |
</label> | |
</div> | |
<button (click)="goBack()">go back</button> | |
<button (click)="save()">save</button> | |
</div> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { Component } from '@angular/core'; | |
import { | |
ComponentFixture, | |
fakeAsync, | |
TestBed, | |
tick, | |
} from '@angular/core/testing'; | |
import { FormsModule } from '@angular/forms'; | |
import { By } from '@angular/platform-browser'; | |
import { Router } from '@angular/router'; | |
import { RouterTestingModule } from '@angular/router/testing'; | |
import { of } from 'rxjs'; | |
import { Hero } from '../hero'; | |
import { HeroService } from '../hero.service'; | |
import { HEROES } from '../mock-heroes'; | |
import { HeroDetailComponent } from './hero-detail.component'; | |
@Component({ | |
template: '<router-outlet></router-outlet>', | |
}) | |
class TestRootComponent {} | |
describe('HeroDetailComponent (integrated)', () => { | |
function advance() { | |
tick(); | |
rootFixture.detectChanges(); | |
} | |
function getTitle() { | |
const element = rootFixture.debugElement.query(By.css('h2')) | |
.nativeElement as HTMLElement; | |
return element.textContent.trim(); | |
} | |
function navigateByHeroId(id: number) { | |
rootFixture.ngZone.run(() => router.navigate(['detail', id])); | |
} | |
beforeEach(async () => { | |
const fakeService = { | |
getHero(id: number) { | |
const hero = [...fakeHeroes].find(h => h.id === id); | |
return of(hero); | |
}, | |
} as Partial<HeroService>; | |
TestBed.configureTestingModule({ | |
declarations: [ | |
TestRootComponent, | |
HeroDetailComponent, | |
], | |
imports: [ | |
RouterTestingModule.withRoutes([ | |
{ path: 'detail/:id', component: HeroDetailComponent }, | |
]), | |
FormsModule, | |
], | |
providers: [ | |
{ provide: HeroService, useValue: fakeService }, | |
], | |
}); | |
await TestBed.compileComponents(); | |
rootFixture = TestBed.createComponent(TestRootComponent); | |
router = TestBed.inject(Router); | |
}); | |
const fakeHeroes: ReadonlyArray<Hero> = [...HEROES]; | |
let router: Router; | |
let rootFixture: ComponentFixture<TestRootComponent>; | |
it("displays the hero's name in upper-case letters", fakeAsync(() => { | |
const [expectedHero] = fakeHeroes; | |
navigateByHeroId(expectedHero.id); | |
advance(); | |
expect(getTitle()).toContain(expectedHero.name.toUpperCase()); | |
})); | |
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { Location } from '@angular/common'; | |
import { Component, Input, OnInit } from '@angular/core'; | |
import { ActivatedRoute } from '@angular/router'; | |
import { Hero } from '../hero'; | |
import { HeroService } from '../hero.service'; | |
@Component({ | |
selector: 'app-hero-detail', | |
styleUrls: ['./hero-detail.component.css'], | |
templateUrl: './hero-detail.component.html', | |
}) | |
export class HeroDetailComponent implements OnInit { | |
@Input() hero: Hero; | |
constructor( | |
private route: ActivatedRoute, | |
private heroService: HeroService, | |
private location: Location, | |
) {} | |
ngOnInit(): void { | |
this.getHero(); | |
} | |
getHero(): void { | |
const id = +this.route.snapshot.paramMap.get('id'); | |
this.heroService.getHero(id) | |
.subscribe(hero => this.hero = hero); | |
} | |
goBack(): void { | |
this.location.back(); | |
} | |
save(): void { | |
this.heroService.updateHero(this.hero) | |
.subscribe(() => this.goBack()); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
@LayZeeDK
Thank you, I'll check it out!
I guess I'm not only one who doesn't want to waste time on e2e.