douping4436 2012-03-10 17:49
浏览 30
已采纳

单元测试,测试之间的耦合和级联故障

I'm curious how people deal with coupling between tests, and "cascaing failures". I don't know what else to call it, so I'll explain with some code.

I have a simple caching class that I want to test.

class Cache
{
    private $data = array();
    public function set($key, $data)
    {
        $this->data[$key] = $data;
        return true;
    }
    public function get($key)
    {
        if (!isset($this->data[$key])) {
            return false;
        }
        return $this->data[$key];
    }
}

Now I want to test the class, and both of the methods in the class. Here's the problem; the get() method depends on the set() method. So I can write my test case in one of two ways.

class TestCache extends Test
{
    private $cache = null;
    public function setup()
    {
        $this->cache = new Cache();
    }
    public function testSet()
    {
        $result = $this->cache->set('foo', 'bar');
        $this->asserTrue($result);
    }
    public function testGet()
    {
        $result = $this->cache->get('foo');
        $this->assertEquals($result, 'bar');
    }
}

The problem here is the second test, testGet(), replies on the first test, testSet(). If testSet() fails, so will testGet(). There's a kind of coupling between the two tests. Additionally the testGet() test will fail if I change the order of the test methods. So instead I write my test case like this:

class TestCache extends Test
{
    private $cache = null;
    public function setup()
    {
        $this->cache = new Cache();
    }
    public function testSet()
    {
        $result = $this->cache->set('foo', 'bar');
        $this->asserTrue($result);
    }
    public function testGet()
    {
        $this->cache->set('foo', 'bar');
        $result = $this->cache->get('foo');
        $this->assertEquals($result, 'bar');
    }
}

Now there's no coupling between the two tests, but there's still a problem. If the Cache::set() method is failing, then the second test will also fail along with the first, because the second test's call to Cache::get() replies on Cache::set() not failing.

So I'm wondering how you typically deal with a situation like this. Do you simply accept dozens of failures in your test output because of one bad test? Do you abort further testing on the class if an important test fails?

  • 写回答

2条回答 默认 最新

  • douaoli5328 2012-03-10 18:24
    关注

    This is what the @depends directive is for in phpunit: see the section on "Test Dependencies". If a dependency has failed, then subsequent tests dependent on that intial test will be skipped.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

悬赏问题

  • ¥15 八爪鱼爬数据为什么自己停了
  • ¥15 交替优化波束形成和ris反射角使保密速率最大化
  • ¥15 树莓派与pix飞控通信
  • ¥15 自动转发微信群信息到另外一个微信群
  • ¥15 outlook无法配置成功
  • ¥30 这是哪个作者做的宝宝起名网站
  • ¥60 版本过低apk如何修改可以兼容新的安卓系统
  • ¥25 由IPR导致的DRIVER_POWER_STATE_FAILURE蓝屏
  • ¥50 有数据,怎么建立模型求影响全要素生产率的因素
  • ¥50 有数据,怎么用matlab求全要素生产率