编写可测试代码的ABAP编程方法
原文链接:ABAP Programming approach to writing testable code
作者:Akash Jain 阿卡什·贾因 | August 2, 2019
无论我们的代码有多好,如果我们不能正确地测试它,修改或增强它是一项乏味的任务。这种情况会给用户和开发人员带来问题。
简介
由于需求在开发过程中经常变化,你需要不断地修改代码。有时,需求的变化可能涉及到流程的完全改变。
编写可测试的代码总是比实际测试你的代码更困难。然而,从长远来看,可测试的代码使开发人员的生活比测试代码的人更容易。
你可能会面临以下情况:
- 您需要更改自己的代码。您可能喜欢这个想法,但您不记得您最初编写的代码的细节。
- 你必须修改别人的代码。这种情况并不理想,但却很常见。
如果你不能测试代码,你怎么能确定你在实现更改后不会破坏任何东西呢?多年来,我们看到的传统方法包括以下几种:
- 在开发环境中写一些测试,并检查是否有转储的情况。
- 转移到质量测试环境,再次测试。
- 交给模块顾问,让他们在他们的终端进行测试。
- 发布给用户进行用户验收测试(UAT)。
当有人遇到代码的问题时,我们很可能会归咎于测试数据的差异。即使这是真的,真正的问题是,软件写得不好,不够健壮。没有真实的数据,你无法测试它。换句话说,程序有依赖性,你无法测试它。
测试驱动开发和 ABAP
测试驱动开发(Test-driven development,TDD)解决了这些问题,使你能够交付高质量的软件和产品。
TDD 是一个软件开发过程,它依赖于一个非常短的开发周期的重复:当需求转化为非常具体的测试用例时,软件就会被改进,只通过新的测试。(维基百科)
在 ABAP 中,所有的代码都被转换为 ABAP 单元,它只不过是一段特定的代码。测试 ABAP 单元不一定是一个由开发人员执行的纯技术过程。因为你不需要开发人员的密钥来运行 ABAP 程序的单元测试,所以任何具有显示程序或类的适当授权的人都应该能够运行测试。作为一个最佳实践,只要有可能,请尽可能让我们的业务专家和职能顾问参与测试。
行为驱动开发
行为驱动开发(Behavior-driven development,BDD)是由 TDD 产生的一种软件开发过程。BDD 将 TDD 的一般技术和原则与领域驱动设计(domain-driven design)和面向对象的分析和设计的思想相结合,为软件开发和管理团队提供共享工具和共享流程,以协作进行软件开发。(维基百科)
BDD 简化了测试方法,所以在 ABAP 单元中标注的测试方法应该有对开发人员、业务分析人员和用户有意义的描述。你可以通过设置每个测试方法使其满足 IT SHOULD
(应该是这样的) 这句话来实现。
然后在这个方法里面,你通过使用以下模式创建三个辅助方法:
GIVEN
:包括程序收到的输入或初始条件。WHEN
: 描述你要测试的活动。THEN
:指定成功和失败的结果。
重构可测试类 Demo
下面的代码示例使用伪代码定义流程,是 zcl_instruments
类的重构测试类示例。
class lcl_test_class definition deferred.
"Allow access to private components within the class
class zcl_instruments definition local friends lcl_test_class.
class lcl_test_class definition final for testing
duration short
risk level harmless.
private section.
types: ty_guitars type standard table of zguitars with empty key.
data: mo_class_under_test type ref to zcl_instruments,
guitar_instance type ref to zcl_guitar,
guitars type ty_guitars.
guitar_to_add type ref to zcl_guitar.
guitar_to_search type ref to zcl_guitar.
mo_exception_raised type abap_bool.
found_guitars type zcl_instruments=>guitars_tab.
methods:
setup,
"User Acceptance tests:
"IT SHOULD....................
add_guitar_to_instruments for testing,
add_duplicate_and_get_error for testing,
search_within_the_instruments for testing,
"GIVEN ..................................................
given_guitar_attribs_entered,
given_initial_instruments,
"WHEN ..................................................
when_guitar_is_added,
when_same_guitar_twice,
when_guitar_is_searched,
"THEN ..................................................
then_instruments_has_guitar,
then_exception_is_raised,
then_guitar_is_found,
"Other helper methods
load_mockups returning value(re_guitars) type ty_guitars.
endclass.
您应该包括 IT SHOULD
直接从功能规范文档中出来的方法。
在此示例中,zcl_instruments
类应该能够:
- 将吉他添加到乐器中
- 限制重复行为
- 在乐器中搜索任何特定的吉他
下面的示例显示了该方法的实现 add_guitar_to_instruments()
:
method add_guitar_to_instruments.
given_guitar_attribs_entered ().
when_guitar_is_added ().
then_instruments_has_guitar ().
endmethod.
若要将吉他添加到乐器,请从一些吉他属性开始,将吉他添加到乐器,然后检查是否成功添加。如果在运行此方法的测试时没有绿色,则表明过程的这一部分出了问题。
下面的 given_guitar_attribs_entered()
方法只初始化一个吉他对象。
method given_guitar_attribs_entered.
data: guitar_spec_attributes type zcl_guitar_spec=>ty_guitar_attributes.
guitar_spec_attributes-builder = zcl_enum_builder=>fender.
guitar_spec_attributes-model = 'XYZ'.
guitar_spec_attributes-type = zcl_enum_guit_type=>electric.
guitar_spec_attributes-backwood = zcl_enum_wood=>maple.
guitar_spec_attributes-topwood = zcl_enum_wood=>maple.
data(guitar_spec) = new zcl_guitar_spec (guitar_spec_attributes).
data(guitar_record) = value zcl_guitar=>ty_guitar_attributes (serialnumber = 'ABC0001'
price = '1000'
specs = guitar_spec).
guitar_to_add = new zcl_guitar (guitar_record).
endmethod.
BDD WHEN
描述的一部分,来自被测试的类,使您能够测试该方法。
method when_guitar_is_added.
try.
mo_class_under_test->add_guitar (guitar_to_add).
catch zcx_guitar.
"Oops
endtry.
endmethod.
最后,您可以使用以下方法检查对象乐器是否有吉他。此检查表示BDD部分的helper方法 Then
。
method then_instruments_has_guitar.
data(guitar) = mo_class_under_test->guitars [ serial_number = 'ABC0001'].
cl_abap_unit_assert=>assert_not_initial (act = guitar
msg = 'Guitar is not in instruments').
endmethod.
总结
本博客强调了编写可测试代码的重要性,并展示了如何做到这一点。通过专注于测试驱动开发,您可以调整您的编程风格以包含可测试代码。因此,您最终会得到干净、易于维护和可重用的代码。编写可测试的代码可以帮助你成为一个更好的开发人员。有时,当交付期限更紧时,很容易忽略代码的可测试性方面,这样做可能会保存时间。然而,从长远来看,您最终会花费更多的时间和资源来修复 bug。
因此,通过采用这里描述的测试驱动开发概念,您不仅可以使自己的工作更轻松,而且还可以帮助下一个开发您的代码的开发人员。
- 点赞
- 收藏
- 关注作者
评论(0)