【OpenStack】【转载】OpenStack中的测试

来源:互联网 发布:linux 修改帐号密码 编辑:程序博客网 时间:2024/06/06 17:24

OpenStack中的测试

原作者:张华

原文链接: http://blog.csdn.net/quqi99 

如需再次转载,请注明原作者信息!

          在openstack中写一个扩展API之后要写哪些测试代码呢?https://jenkins.openstack.org/view/Nova/?列出来了提交代码后jenkins所要做的测试。

          1)通过Mock带隔离的测试,包括单元测试,还有针对API和example的功能测试(在Mock环境中针对一个个具体的API和example做测试)
          2)不带隔离的真实环境的测试,包括功能测试(在真实环境中针对一个个具体的API一一测试),和集成测试(在真实环境中将多个API串起来测试),代码位于tempest工程

          
          至于如何写扩展API (位于目录$nova/nova/api/openstack/compute/contrib),请参见我的上一篇博文(Openstack extension api ( by quqi99 ) http://blog.csdn.net/quqi99/article/details/8502034) .

 1, Mock单元测试,  (位于目录$nova/nova/tests/api/openstack/compute/contrib) 可以参见文档:http://wiki.openstack.org/SmallTestingGuide
    Mock单元测试,就是经常说的Small Testing, 它强调隔离,也就是说我们只将精力集中在我们要测试的方法内,如果该方法调用了其他方法,都可以让它做Mock即返回一些假值。
    代码隔离有两种方法:
    1)一种是依赖注入,如下例子,想要测试FalilyTree类的话,应集中精力测试FalilyTree本身是否有错,至于它所依赖的PersonGateway可以做一个假的FakePersonGateway注入进去。
       class FamilyTree(object):         def __init__(self, person_gateway):           self._person_gateway = person_gateway       person_gateway = FakePersonGateway()       # ...       tree = FamilyTree(person_gateway)
    2) Monkey Patching, 如下例子,例用python脚本语言的特性,在运行时可以动态替换命名空间的方法,用FakePersonGateway替换掉命名空间mylibrary.dataaccess.PersonGateway
       class FamilyTree(object):         def __init__(self):            self._person_gateway = mylibrary.dataaccess.PersonGateway()        mylibrary.dataaccess.PersonGateway = FakePersonGateway        # ...        tree = FamilyTree()
    所以,相应地,也就有了下列几类实际隔离的方法:
    1) Test Stub,打桩
       比如在扩展API中调用了authorize这个函数,如下:
    authorize = extensions.extension_authorizer('compute', 'flavor_dynamic')    class FlavorDynamicController(servers.Controller):        @wsgi.extends        def create(self, req, body):            context = req.environ['nova.context']            authorize(context)
       那么在为它写单元测试时,对authorize函数打桩替换的代码如下:
    def authorize(context):        pass    class FlavorDynamicTest(test.TestCase):        def setUp(self):            super(FlavorDynamicTest, self).setUp()            self.controller = flavor_dynamic.FlavorDynamicController()            self.stubs.Set(flavor_dynamic, 'authorize', authorize)
    2) Mock对象,例如要测试的方法中调用了
        inst_type = instance_types. get_instance_type_by_name(flavor_name, context)
        现在可以用下面的方法将其替换:
        self.mox.StubOutWithMock(flavor_dynamic.instance_types,                                  'get_instance_type_by_name')        flavor_dynamic.instance_types.get_instance_type_by_name(                    mox.IgnoreArg(), mox.IgnoreArg()).AndReturn(None)        flavor_dynamic.instance_types.get_instance_type_by_name(                    mox.IgnoreArg(), mox.IgnoreArg()).AndReturn("{'a'='1'")        self.mox.ReplayAll()
    3) Fake对象,即创建大量的假对象。

2, 除了上面的单元测试,还有针对api和samples的功能测试,位于$nova/nova/tests/integrated/api_samples目录,它们和集成测试的区别在于集成测试采用的是真实环境,而它仍然需要做Mock隔离。
   https://blueprints.launchpad.net/nova/+spec/nova-api-samples 介绍了如何写这种测试
   https://review.openstack.org/#/c/17003/  是一个这种测试的具体例子


3, 集成测试,位于tempest工程中,一个好的例子, https://review.openstack.org/#/c/9507/