subunit 协议

本文介绍了subunit协议,一种用于标准化多语言测试输出的序列化协议。文章详细阐述了subunit数据包结构,并展示了如何在Python中生成和处理subunit原始数据。此外,还提到了如何将subunit数据转换为JUnit XML格式和其他报告格式,以及一系列相关工具的使用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

subunit是一个协议, 用来对不同语言(C, Python, Shell)的测试输出结果进行标准序列化


subunit协议的数据结构

  • 数据包结构
PACKET := SIGNATURE FLAGSPACKET_LENGTH TIMESTAMP? TESTID? TAGS? MIME?FILECONTENT? ROUTING_CODE? CRC32
  • 一个数据包例子

Trivial test "foo"enumeration packet, with test id, runnable set,status=enumeration. Spaces beloware to visually break up signature / flags / length / testid / crc32

subunit Integrationwith Python


 用python生成subunit原始数据


使用subunit执行某个test case, 并输出原始 subunit 数据包

$ python-m subunit.run thinking.tests.core.test_string_service

�)@P@Ethinking.tests.core.test_string_service.StringTestCase.test_partition���T�)@Q@Fthinking.tests.core.test_string_service.StringTestCase.test_rpartition�'爳+[1]@XS�P���n�@Ethinking.tests.core.test_string_service.StringTestCase.test_partition�����+


@XS�P���Cp@Ethinking.tests.core.test_string_service.StringTestCase.test_partition�rm�+[1]@YS�P���@Fthinking.tests.core.test_string_service.StringTestCase.test_rpartition9��F�+
@YS�P���d8@Fthinking.tests.core.test_string_service.StringTestCase.test_rpartition���

 

使用subunit发现指定目录下的所有test case, 并输出原始 subunit 数据包

$ python-m subunit.run discover./thinking/tests

�)6-core.test_data_type.ArrayTestCase.test_append�e)90core.test_data_type.ArrayTestCase.test_enumerate�­‑��)6-core.test_data_type.ArrayTestCase.test_extend1Q�)5,core.test_data_type.ArrayTestCase.test_indexK��v�);2core.test_data_type.CollectionsTestCase.test_dequecj�߳)90core.test_data_type.DictTestCase.test_setdefaultz�Wp�)@C9core.test_generator.GeneratorTestCase.test_count_with_for��鯳)@D:core.test_generator.GeneratorTestCase.test_count_with_nextS%���)?6core.test_generator.GeneratorTestCase.test_iter_object���ٳ)90core.test_generator.GeneratorTestCase.test_yield�


���);2core.test_io_access.PathNameTestCase.test_basename�߭³)@A7core.test_metaclass.MetaClassTestCase.test_new_instance�G�g�)?6core.test_string_service.StringTestCase.test_partition���4�)@A7core.test_string_service.StringTestCase.test_rpartitionL6K�+[1]>S�R��

                                                                                                                                                            @�-core.test_data_type.ArrayTestCase.test_append8�bC�+


>S�R�-core.test_data_type.ArrayTestCase.test_append��K��+[1]@BS�R��,(0core.test_data_type.ArrayTestCase.test_enumerate���J�+
@BS�R��lx0core.test_data_type.ArrayTestCase.test_enumerateLfi�+[1]>S�R����-core.test_data_type.ArrayTestCase.test_extendX���+
>S�R��@-core.test_data_type.ArrayTestCase.test_extendrσ�+[1]=S�R��w�,core.test_data_type.ArrayTestCase.test_index�U߳+
=S�R���h,core.test_data_type.ArrayTestCase.test_index��;�+[1]@DS�R����2core.test_data_type.CollectionsTestCase.test_deque���ɳ+
@DS�R����2core.test_data_type.CollectionsTestCase.test_deque�~�[�+[1]@BS�R��W�0core.test_data_type.DictTestCase.test_setdefaultr�T��+
@BS�R����0core.test_data_type.DictTestCase.test_setdefault�| �+[1]@KS�R��­��9core.test_generator.GeneratorTestCase.test_count_with_for�­�x�+
@KS�R��$�`9core.test_generator.GeneratorTestCase.test_count_with_for�Q?�+[1]@LS�R��%��:core.test_generator.GeneratorTestCase.test_count_with_nextE՘�+
@LS�R��'!@:core.test_generator.GeneratorTestCase.test_count_with_next\����+[1]@HS�R��(|�6core.test_generator.GeneratorTestCase.test_iter_objectKJ�ȳ+
@HS�R��)��6core.test_generator.GeneratorTestCase.test_iter_object�w���+[1]@BS�R��*��0core.test_generator.GeneratorTestCase.test_yieldM�a�+
@BS�R��,20core.test_generator.GeneratorTestCase.test_yield �pO�+[1]@DS�R��.2core.test_io_access.PathNameTestCase.test_basename�|
��+
@DS�R��0p2core.test_io_access.PathNameTestCase.test_basenamei�z��+[1]@IS�R��1��7core.test_metaclass.MetaClassTestCase.test_new_instanceS�#�+
@IS�R��3�7core.test_metaclass.MetaClassTestCase.test_new_instance�
̳+[1]@HS�R��46core.test_string_service.StringTestCase.test_partition�7�Z�+
@HS�R��5��6core.test_string_service.StringTestCase.test_partition�A�7�+[1]@IS�R��7H7core.test_string_service.StringTestCase.test_rpartition��;5�+
@IS�R��84X7core.test_string_service.StringTestCase.test_rpartition��2

 

如何转换 subunit 原始数据


转换subunit数据为junit xml格式

$ python-m subunit.run thinking.tests.core.test_string_service | subunit2junitxml

<testsuiteerrors="0" failures="0" name=""tests="2" time="0.003">

<testcaseclassname="thinking.tests.core.test_string_service.StringTestCase"name="test_partition" time="0.000"/>

<testcaseclassname="thinking.tests.core.test_string_service.StringTestCase"name="test_rpartition" time="0.000"/>

</testsuite>


转换subunit数据为统计报告格式

$ python-m subunit.run thinking.tests.core.test_string_service | subunit-stats

Total tests:       2

Passed tests:      2

Failed tests:      0

Skipped tests:     0

Seen tags:

 

其他可以使用的转换工具

 * tap2subunit -convert perl's TestAnythingProtocol to subunit.

 * subunit2csv -convert a subunit stream to csv.

 * subunit2pyunit -convert a subunit stream to pyunit test results.

 * subunit2gtk - showa subunit stream in GTK.

 * subunit2junitxml -convert a subunit stream to JUnit's XML format.

 * subunit-diff -compare two subunit streams.

 * subunit-filter -filter out tests from a subunit stream.

 * subunit-ls - listinfo about tests present in a subunit stream.

 * subunit-stats -generate a summary of a subunit stream.

 * subunit-tags - addor remove tags from a stream.

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值