Angular????????????Component??Directive??Pipe ???Service
?????cipchk ???????[ 2017/6/15 10:55:18 ] ??????????????? ??????? Angular
????4???????
?????????????о???Щ?????
????????? TradeService ???????????????????????? TradeService ?????????????????????????????????????????? TradeService ??????????????????г????????????????????
?????????
????????Angular???????DI??????????????????????????????????????????????????????????????????????????????г?????????????????????????
???????? TradeService ????????? UserService ????????????????? UserService ????????????
??????????????????????????????????????
????Stub
????trade-list ??????? TradeService ???? TradeService ?????? UserService ??????β?????????????????? TradeService ???????????????????????
????Angular???DI????????????????????????????????? trade-list ????????
const tradeServiceStub = {
query(): Observable<any[]> {
return Observable.of(tradeData);
}
};
beforeEach(async(() => {
TestBed.configureTestingModule({
declarations: [TradeListComponent?? TradePipe]??
providers: [
{ provide: TradeService?? useValue: tradeServiceStub }
]
}).compileComponents();
// ???????
}));
????@NgModule ????????д????????????????????????????????????? tradeServiceStub ??????????? TradeService ???????????????????????……
???????????????? HttpModule ?? UserService ?????????
????5??С??
????????????????????????????????????????а?????Directive??Pipe??Service??Щ??????????
??????????????????????????????Щ??Component??????????
????????Directive
????1?????
???????????ε???
@Directive({ selector: '[log]' })
export class LogDirective {
tick: number = 0;
@Output() change = new EventEmitter();
@HostListener('click'?? [ '$event' ])
click(event: any) {
++this.tick;
this.change.emit(this.tick);
}
}
2????????? @NgModule
// ???????????
@Component({
template: `<div log (change)="change($event)"></div>`
})
class TestComponent {
@Output() changeNotify = new EventEmitter();
change(value) {
this.changeNotify.emit(value);
}
}
beforeEach(() => {
TestBed.configureTestingModule({
declarations: [TestComponent?? LogDirective]
});
fixture = TestBed.createComponent(TestComponent);
context = fixture.componentInstance;
el = fixture.nativeElement;
let directives = fixture.debugElement.queryAll(By.directive(LogDirective));
directive = directives.map((d: DebugElement) => d.injector.get(LogDirective) as LogDirective)[0];
????});
????????????漰?????????????????????? beforeEach ????
?????????????????в??????????????? By.directive ?????????????????? LogDirective ??
????By
????By ??Angular???????????????????????????? Type ?????????????????????????????????????? css ?? all ??
????3??????????
????A??????????
??????????? beforeEach ??????????????????????????????????????????????????
??it('should be defined on the test component'?? () => {
expect(directive).not.toBeUndefined();
});
????B??HostListener????
????[log] ??????????????? click ????????????????? change ???????????????????????????????????? (change) ?????????????????????????????????????????е??????????????????
it('should increment tick (fakeAsync)'?? fakeAsync(() => {
context.changeNotify.subscribe(val => {
expect(val).toBe(1);
});
el.click();
tick();
}));
??????????? fakeAsync ?????????????? changeNotify ?????????????????????????????
????????????????????????? changeNotify ???????????????? 1 ???????????????????????????+1???????????0????
??????Σ?????DOM???? click() ?????
?????? tick() ???ж???У???????????????
???????Pipe
????1?????
?????????????????????????????Pipe??
@Pipe({ name: 'trade' })
export class TradePipe implements PipeTransform {
transform(value: any?? ...args: any[]) {
switch (value) {
case 'new':
return '?????';
case 'wait_pay':
return '?????';
case 'cancel':
return `<a title="${args && args.length > 0 ? args[0] : ''}">?????</a>`;
default:
throw new Error(`??Ч????${value}`);
}
}
}
????2??????????
????A??????????
????Pipe??????????????????????????????????????????????
?????????????????? async ?? fakeAsync ????Angular??????????????
let pipe = new TradePipe();
it('should be defined'?? () => {
expect(pipe).not.toBeUndefined();
});
B??new ????
it(`should be return '?????' with 'new' string`?? () => {
expect(pipe.transform('new')).toEqual('?????');
});
C??????DOM???
???????????????Pipe????????У?????????DOM????????????á????????????????????????????
@Component({ template: `<h1>{{ value | trade }}</h1>` })
class TestComponent {
value: string = 'new';
}
let fixture: ComponentFixture<TestComponent>??
context: TestComponent??
el: HTMLElement??
de: DebugElement;
beforeEach(() => {
TestBed.configureTestingModule({
declarations: [TestComponent?? TradePipe]
});
fixture = TestBed.createComponent(TestComponent);
context = fixture.componentInstance;
el = fixture.nativeElement;
de = fixture.debugElement;
});
?????????????? NgModule ?????????????
????????????
???????? h1 DOM????????????????????????????ɡ?
it('should display `?????`'?? () => {
context.value = 'wait_pay';
fixture.detectChanges();
expect(el.querySelector('h1').textContent).toBe('?????');
});
?塢Service
1?????
??????
@Injectable()
export class TradeService {
constructor(private http: Http?? private userSrv: UserService) { }
query(): Observable<any[]> {
return this.http
.get('./assets/trade-list.json?token' + this.userSrv.token)
.map(response => response.json());
}
private getTrade() {
return {
"id": 10000??
"user_id": 1??
"user_name": "asdf"??
"sku_id": 10000??
"title": "???????"
}
}
get(tid: number): Promise<any> {
return new Promise(resolve => {
setTimeout(() => {
resolve(this.getTrade());
}?? 500);
})
}
}
?????
@Injectable()
export class UserService {
token: string = 'wx';
get() {
return {
"id": 1??
"name": "asdf"
};
}
type() {
return ['??????'?? 'VIP???'];
}
}
????2??????????
????A??????????
??????Service???κ????????????????? Pipe ??????????????????????ɡ?
?????????????????? async ?? fakeAsync ????Angular??????????????
let srv: UserService = new UserService();
it(`#token should return 'wx'`?? () => {
expect(srv.token).toBe('wx');
});
???????????????2????????????????????????????? Http ??飬???????????? Angular??????????????????? NgModule ??
let srv: TradeService;
beforeEach(() => TestBed.configureTestingModule({
imports: [HttpModule]??
providers: [TradeService?? UserService]
}));
beforeEach(inject([TradeService]?? s => { srv = s; }));
??????????????????κ???????????????
it('#query should return trade array'?? (done: DoneFn) => {
srv.query().subscribe(res => {
expect(Array.isArray(res)).toBe(true);
expect(res.length).toBe(2);
done();
});
});
????B??????????? async ?? fakeAsync
???????Service????????????????????????????????κ? async ?? fakeAsync ??????????????????? Observable ?? Promise??
?????????????????????Ρ?
?????????????????? async ?? fakeAsync ????Angular??????????????
????????????????檔
????????????汾???????? Angular ??????????? NgModule ??????????2????????????
it('#get should return trade (fakeAsync)'?? fakeAsync((done: DoneFn) => {
srv.get(1).then(res => {
expect(res).not.toBeNull();
expect(res.id).toBe(10000);
});
tick();
}));
??????????? tick() ?????????????DOM????????????Observable???Promise????????????????????? get() ????? setTimeout ????????????? 500ms ???????? tick() ?????????????????????????
????????????????????
????tick(600);
??????????????????? seTimeout ????????????
????????????
????Angular??????????????????????????????????????????????????к?????????? TestBed ???????DI????????????? spy ?????????????????
?????????????24???????????е????????? plnkr ??????????????? templateUrl ??plnkr?в???????????????plnkr??????? template ???????
??????
???·???
??????????????????
2023/3/23 14:23:39???д?ò??????????
2023/3/22 16:17:39????????????????????Щ??
2022/6/14 16:14:27??????????????????????????
2021/10/18 15:37:44???????????????
2021/9/17 15:19:29???·???????·
2021/9/14 15:42:25?????????????
2021/5/28 17:25:47??????APP??????????
2021/5/8 17:01:11