角度单位测试输入值

时间:2016-12-09 14:48:36

标签: angular unit-testing angular2-testing

我一直在阅读单元测试的官方Angular2文档(https://angular.io/docs/ts/latest/guide/testing.html),但我正在努力设置组件的输入字段值,以便它反映在组件属性中(通过ngModel绑定)。屏幕在浏览器中工作正常,但在单元测试中我似乎无法设置字段值。

我正在使用下面的代码。 “夹具”已正确初始化,因为其他测试工作正常。 “comp”是我的组件的实例,输入字段通过ngModel绑定到“user.username”。

it('should update model...', async(() => {
    let field: HTMLInputElement = fixture.debugElement.query(By.css('#user')).nativeElement;
    field.value = 'someValue'
    field.dispatchEvent(new Event('input'));
    fixture.detectChanges();

    expect(field.textContent).toBe('someValue');
    expect(comp.user.username).toBe('someValue');
  }));

我的Angular2版本:"@angular/core": "2.0.0"

4 个答案:

答案 0 :(得分:54)

输入没有textContent,只有一个值。所以expect(field.textContent).toBe('someValue');没用。这可能是失败的原因。第二个期望应该通过。这是一个完整的测试。

@Component({
  template: `<input type="text" [(ngModel)]="user.username"/>`
})
class TestComponent {
  user = { username: 'peeskillet' };
}

describe('component: TestComponent', () => {
  beforeEach(() => {
    TestBed.configureTestingModule({
      imports: [FormsModule],
      declarations: [ TestComponent ]
    });
  });

  it('should be ok', async(() => {
    let fixture = TestBed.createComponent(TestComponent);
    fixture.detectChanges();
    fixture.whenStable().then(() => {
      let input = fixture.debugElement.query(By.css('input'));
      let el = input.nativeElement;

      expect(el.value).toBe('peeskillet');

      el.value = 'someValue';
      el.dispatchEvent(new Event('input'));

      expect(fixture.componentInstance.user.username).toBe('someValue');
    });
  }));
});

答案 1 :(得分:6)

添加

fixture.detectChanges();

fixture.whenStable().then(() => {
  // here your expectation
})

答案 2 :(得分:2)

whenStable.then函数中使用expect / assert,如下所示:

component.label = 'blah';
fixture.detectChanges();

fixture.whenStable().then(() => {
    expect(component.label).toBe('blah');
}

答案 3 :(得分:0)

如果您想使用@Input内容实现单元测试,请仔细阅读下面的代码。

testing.component.ts `

import { Component, OnInit } from '@angular/core';
@Component({
  selector: 'app-testing',
  templateUrl: `<app-input [message]='text'></app-input>`,
  styleUrls: ['./testing.component.css']
})
export class TestingComponent implements OnInit {
public text = 'input message';
  constructor() { }

  ngOnInit() {
  }

}

`

input.component.ts `

import { Component, OnInit, Input } from '@angular/core';

@Component({
  selector: 'app-input',
  templateUrl: `<div *ngIf="message">{{message}}</div>`,
  styleUrls: ['./input.component.css']
})
export class InputComponent implements OnInit {
@Input() public message: string;
  constructor() { }

  ngOnInit() {
    console.log(this.message);
  }

}

`

input.component.spec.ts

`

import { async, ComponentFixture, TestBed } from '@angular/core/testing';

import { InputComponent } from './input.component';
import { TestingComponent } from '../testing/testing.component';

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

  beforeEach(async(() => {
    TestBed.configureTestingModule({
      declarations: [ InputComponent, TestingComponent ]
    })
    .compileComponents();
  }));

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

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

  it('should correctly render the passed @Input value', () => {
    component.message = 'test input';
    fixture.detectChanges();
    expect(fixture.nativeElement.innerText).toBe('test input');
  });

});

`