Flex: FlexUnit单元测试

FlexUnit是FlashBuilder所自带的单元测试框架,从FlexUnit4.0开始,Test Case由[Test]元数据来指定,Test Case函数不再需要遵循任何命名规范(FlexUnit 4.0之前,Test Case函数名必须以”test”开头)。同时,Test类也不再需要从任何框架类进行继承。下面是两个简单的Test Case:

[Test]
public function addition():void {  
    assertEquals(12, simpleMath.add(7, 5));
}

[Test]
public function subtraction():void {  
    assertEquals(9, simpleMath.subtract(12, 3));
}

Before与After

有时候对于Test Case,我们需要在运行Case之前进行一些测试环境的搭建工作,而在测试完成之后又需要对测试用例进行收尾。在FlexUnit 4.0之前,这部分内容是通过覆写setup()方法与teardown()方法来完成的。FlexUnit 4.0引入了Before元数据与After元数据,从而使测试的准备与收尾工作更加灵活 — 任何标记有Before的函数都会在每一个Test Case执行前运行,而任何标记有After的函数都会在每一个Test Case执行后运行:

[Before]
public function runBeforeEveryTest():void {  
    simpleMath = new SimpleMath();
}

[Before]
public function alsoRunBeforeEveryTest():void {  
    simpleMath1 = new SimpleMath();
}

[After]
public function runAfterEveryTest():void {  
    simpleMath = null;
    simpleMath1 = null;
}

对于多个Before函数的情况,我们可以通过指定order参数来确定函数的执行顺序:

[Before(order=1)]
public function runFirst():void {  
    //...
}

[Before(order=2)]
public function runSecond():void {  
    //...
}

为了遵循FlexUnit 4.0之前版本的使用习惯,Before函数与After函数一般命名为setup()teardown():

[Before]
public function setup():void {  
    //...
}

[After]
public function teardown():void {  
    //...
}

BeforeClass与AfterClass

标记有Before或者After元数据的函数会在每一个Test方法执行前后运行,而BeforeClass和AfterClass元数据则允许定义静态函数在整个测试类执行前后运行:

[BeforeClass]
public static function runBeforeClass():void {  
    //run for one time before all test cases.
}

[AfterClass]
public static function runAfterClass():void {  
    //run for one time after all test cases.
}

与Before/After元数据一样,可以定义多个BeforeClass/AfterClass函数,并通过指定order参数来控制函数的运行顺序。

测试异常

在传统的单元测试中,异常的捕捉与测试可以通过try/catch来实现:

[Test]
public function testIOError():void {  
    try{
        //code causes an IOError
    } catch (err:IOError) {
        assertEquals(true, true);
    }

    assertEquals(true, false);
}

在FlexUnit 4.0中,Test元数据接受expects参数,从而可以快速的进行异常测试:

[Test(expects="flash.error.IOError")]
public function testIOError():void {  
    //code causes an IOError
}