要求跟踪示例报告
Azure DevOps Services | Azure DevOps Server 2022 | Azure DevOps Server 2020
可以使用要求跟踪报告跟踪属于“要求”类别的工作项的质量。 “要求”类别包括工作项,如用户情景(敏捷)、产品积压工作项(Scrum)、问题(基本)和要求(CMMI)。 有关工作项类别的详细信息,请参阅 跟踪用户情景、问题、bug 和其他工作项。
下图显示了要求跟踪报表的示例。
此报表显示它列出的每个要求的以下信息:
- 已完成工时百分比:进度栏,显示所有链接到要求的任务的已完成工时的汇总百分比。
- 通过的测试:基于最新测试运行通过的测试用例数。
- 失败的测试:基于最新测试运行失败的测试用例数。
- 运行测试:已执行的测试运行数。
- 活动 bug:处于活动状态的链接 bug 数。
- 已关闭的 bug:处于“已关闭”、“完成”或“已完成”状态的链接 bug 数。
注意
仅支持通过 基于要求的测试套件链接的测试用例进行要求跟踪。 要求工作项(User Story(Agile)、产品积压工作项(Scrum)、要求(CMMI)、要求(基本)和手动测试执行之间的关联仅在测试用例通过基于要求的测试套件链接时形成。
报告解答的问题
要求跟踪报告可用于回答以下类型的问题。
工作进度
- 每个要求剩余的工作量是否与预期相对应?
- 是否首先实施排名靠前的要求?
- 为每个要求定义了多少个测试? 通过多少个测试?
- 正在实施哪些要求,这些要求没有为其定义测试用例?
质量进度
- 针对每个要求运行了多少个测试用例,以及已通过了多少个测试用例?
- 每个要求有多少个活动 bug?
- 是否发现针对正在测试的要求的 bug?
- bug 是否正在解决,或者它们是否处于活动状态?
风险评估
- 哪些要求面临风险?
- 哪些要求不足以稳定发布?
- 我们今天可以交付哪些要求?
重要
Power BI 集成 和对 分析服务的 OData 源 的访问权限通常用于 Azure DevOps Services 和 Azure DevOps Server 2020 及更高版本。 本文中提供的示例查询仅适用于 Azure DevOps Server 2020 及更高版本,具体取决于 v3.0-preview 或更高版本。 我们鼓励你使用这些查询并提供反馈。
先决条件
- Access:至少是具有基本访问权限的项目的成员。
- 权限: 默认情况下,项目成员有权查询 Analytics 和创建视图。
- 有关服务和功能启用和常规数据跟踪活动的其他先决条件的详细信息,请参阅 访问 Analytics 的权限和先决条件。
注意
本文假设你阅读 了使用 OData 查询 的示例报表概述,并基本了解 Power BI。
要使报表生成有用的数据,需要执行以下任务:
- 你已定义要求工作项,并将其分配给感兴趣的区域和迭代路径。 有关如何定义区域和迭代路径的信息,请参阅 “定义区域路径 ”和 “定义迭代路径”。
- 若要获取工时完成百分比,需要填写与子链接类型要求的任务或 bug 的“完成工时”和“剩余工时”字段。
- 若要获取测试用例的执行状态,需要在与这些要求相对应的测试计划中创建 基于要求的测试套件 。 通过开发板添加的内联测试满足此先决条件,但链接到测试的要求并不满足。 有关详细信息,请参阅 创建测试计划和测试套件。
- 若要获取 bug 的状态,你将创建 bug 并将其链接到子链接类型的要求。
示例查询
若要生成报表,必须将三个 Power BI 查询添加到 Power BI Desktop,然后链接它们。 每个查询执行 WorkItems
或 TestPoints
实体集。
注意
以下部分中提供的 Power BI 查询片段包括扩展列和更改数据类型所需的数据转换。
注意
若要确定用于筛选或报表的可用属性,请参阅Azure Boards元数据参考。 可以使用 提供的 EntitySet
或 NavigationPropertyBinding Path
值下EntityType
的任何Property
值筛选查询或返回属性。 每个对应 EntitySet
一个 EntityType
。 有关每个值的数据类型的详细信息,请查看为相应 EntityType
值提供的元数据。
查询区域和迭代路径
若要将报表的范围限定为特定的区域和迭代路径,可以使用 AreaSK 和 IterationSK 筛选查询。 有关详细信息,请参阅 使用 OData Analytics 定义基本查询。
查询满足要求的小时数百分比
注意
以下查询适用于敏捷过程,因为它定义了 Remaining Work
工作项和 Completed Work
字段。
将以下 Power BI 查询直接复制并粘贴到 “获取数据>空白查询” 窗口中。 有关详细信息,请参阅 使用 OData 查询的示例报告概述。
let
Source = OData.Feed("https://analytics.dev.azure.com/{organization}/{project}/_odata/v3.0-preview/WorkItems?
$filter=(
IterationSK eq {iterationSK}
and AreaSK eq {areaSK}
and Processes/any(p:p/BacklogType eq 'RequirementBacklog')
and Processes/all(p:p/IsBugType eq false)
)
&$expand=Descendants(
$apply=filter(
CompletedWork ne null
or RemainingWork ne null
)
/aggregate(
iif(CompletedWork ne null, CompletedWork, 0) with sum as SumCompletedWork,
iif(RemainingWork ne null, RemainingWork, 0) with sum as SumRemainingWork
)/compute(
(SumCompletedWork add SumRemainingWork) as TotalWork,
SumCompletedWork as SumCompleted
)/compute(
iif(TotalWork gt 0,(SumCompleted div cast(TotalWork, Edm.Double) mul 100), 0) as PercCompletedWork
)
)&$select=WorkItemId, Title", null, [Implementation="2.0"]),
#"Expanded Descendants" = Table.ExpandTableColumn(Source, "Descendants", {"SumCompletedWork", "SumRemainingWork", "TotalWork", "SumCompleted", "PercCompletedWork"}, {"Descendants.SumCompletedWork", "Descendants.SumRemainingWork", "Descendants.TotalWork", "Descendants.SumCompleted", "Descendants.PercCompletedWork"}),
#"Changed Type" = Table.TransformColumnTypes(#"Expanded Descendants",{{"Descendants.SumCompletedWork", type number}, {"Descendants.SumRemainingWork", type number}, {"Descendants.TotalWork", type number}, {"Descendants.SumCompleted", type number}, {"Descendants.PercCompletedWork", type number}})
in
#"Changed Type"
查询要求的测试执行状态
注意
若要确定用于筛选器或报表目的的可用属性,请参阅 测试计划分析的元数据参考。 可以使用 提供的 EntitySet
或 NavigationPropertyBinding Path
值下EntityType
的任何Property
值筛选查询或返回属性。 每个对应 EntitySet
一个 EntityType
。 有关每个值的数据类型的详细信息,请查看为相应 EntityType
值提供的元数据。
将以下 Power BI 查询直接复制并粘贴到 “获取数据>空白查询” 窗口中。 有关详细信息,请参阅 使用 OData 查询的示例报告概述。
let
Source = OData.Feed ("https://analytics.dev.azure.com/{organization}/{project}/_odata/v3.0-preview/TestPoints?
$apply=filter(
(TestSuite/RequirementWorkItem/IterationSK eq {iterationSK}
and TestSuite/RequirementWorkItem/AreaSK eq {areaSK}
and TestSuite/RequirementWorkItem/Processes/any(p:p/BacklogType eq 'RequirementBacklog')
and TestSuite/RequirementWorkItem/Processes/all(p:p/IsBugType eq false)
)
)
/compute(TestSuite/RequirementWorkItem/WorkItemId as WorkItemId, TestSuite/RequirementWorkItem/Title as WorkItemTitle)
/groupby(
(WorkItemId, WorkItemTitle),
aggregate(
$count as TotalCount,
cast(LastResultOutcome eq 'Passed', Edm.Int32) with sum as PassedCount,
cast(LastResultOutcome eq 'Failed', Edm.Int32) with sum as FailedCount,
cast(LastResultOutcome eq 'Blocked', Edm.Int32) with sum as BlockedCount,
cast(LastResultOutcome eq 'NotApplicable', Edm.Int32) with sum as NotApplicableCount,
cast(LastResultOutcome eq 'None', Edm.Int32) with sum as NotRunCount,
cast(LastResultOutcome ne 'None', Edm.Int32) with sum as RunCount)
)", null, [Implementation="2.0"]),
#"Changed Type" = Table.TransformColumnTypes(Source,{{"TotalCount", type number}, {"PassedCount", type number}, {"FailedCount", type number}, {"BlockedCount",type number}, {"NotApplicableCount", type number}, {"NotRunCount", type number}, {"RunCount", type number}})
in
#"Changed Type"
注意
该 TestSuite/RequirementWorkItem/...
条目指示工作项必须通过 基于要求的测试套件链接到测试套件 , 如先决条件中所述。
查询链接到要求的 bug 的状态
将以下 Power BI 查询直接复制并粘贴到 “获取数据>空白查询” 窗口中。 有关详细信息,请参阅 使用 OData 查询的示例报告概述。
let
Source = OData.Feed("https://analytics.dev.azure.com/{organization}/{project}/_odata/v3.0-preview/WorkItems?
$filter=(
IterationSK eq {iterationSK}
and AreaSK eq {areaSK}
and Processes/any(p:p/BacklogType eq 'RequirementBacklog')
and Processes/all(p:p/IsBugType eq false)
)
&$expand=Links(
$apply=filter(
(LinkTypeName eq 'Child' or LinkTypeName eq 'Related')
and TargetWorkItem/WorkItemType eq 'Bug'
)
/groupby(
(TargetWorkItem/State),
aggregate($count as Count)
)
)&$select=WorkItemId,Title", null, [Implementation="2.0"]),
#"Expanded Links" = Table.ExpandTableColumn(Source, "Links", {"TargetWorkItem", "Count"}, {"Links.TargetWorkItem", "Links.Count"}),
#"Expanded Links.TargetWorkItem" = Table.ExpandRecordColumn(#"Expanded Links", "Links.TargetWorkItem", {"State"}, {"Links.TargetWorkItem.State"}),
#"Filtered Rows" = Table.SelectRows(#"Expanded Links.TargetWorkItem", each [Links.Count] <> null and [Links.Count] <> ""),
#"Pivoted Column" = Table.Pivot(#"Filtered Rows", List.Distinct(#"Filtered Rows"[Links.TargetWorkItem.State]), "Links.TargetWorkItem.State", "Links.Count", List.Sum),
#"Changed Type" = Table.TransformColumnTypes(#"Pivoted Column",{{"Active", type number}, {"Closed", type number}})
in
#"Changed Type"
替换字符串和查询明细
将以下字符串替换为值。 不要在替换中包含括号 {} 。 例如,如果组织名称为“Fabrikam”,请将 替换为 {organization}
Fabrikam
,而不是 {Fabrikam}
。
{organization}
- 组织名称{project}
- 项目的名称{iterationSK}
- 与 感兴趣的迭代路径 关联的 GUID。 若要查找 GUID,请参阅 [../extend-analytics/wit-analytics.md#iterationsk](返回特定迭代路径的 IterationSK){areaSK}
- 与感兴趣的区域路径关联的 GUID。 若要查找 GUID,请参阅 [../extend-analytics/wit-analytics.md#areask](返回特定区域路径的 AreaSK)。
查询明细
下表描述了查询的每个部分。
查询部件
描述
$filter=( IterationSK eq {iterationSK} and AreaSK eq {areaSK}
)`
仅返回所选迭代、区域和积压工作项的数据。
Processes/any(p:p/BacklogType eq 'RequirementBacklog')
以这样的方式筛选工作项,使其至少应属于“要求”类别,以处理与其关联的至少一个进程。
Processes/all(p:p/IsBugType eq false)
获取要求时省略 bug 类型工作项。 在基本进程模板中,问题工作项也是 bug 类型,因此对于基本进程,请从查询中删除此子句。
filter( (TestSuite/RequirementWorkItem/IterationSK eq {iterationSK} and TestSuite/RequirementWorkItem/AreaSK eq {areaSK} and TestSuite/RequirementWorkItem/Processes/any(p:p/BacklogType eq 'RequirementBacklog') and TestSuite/RequirementWorkItem/Processes/all(p:p/IsBugType eq false) ) )
仅根据迭代和区域返回所选要求的数据。
/aggregate($count as TotalCount,
聚合筛选的测试点中的数据,其计数为 TotalCount
。
cast(LastResultOutcome eq 'Passed', Edm.Int32) with sum as Passed
聚合时,类型强制转换测试点将最新的执行结果“传递”到 1,并将其汇总为“”Passed
指标。
&$expand=Descendants( $apply=filter( CompletedWork ne null or RemainingWork ne null )
返回 筛选父项的子工作项的已完成工时 和 剩余工时 数据。
/aggregate( iif(CompletedWork ne null, CompletedWork, 0) with sum as SumCompletedWork, iif(RemainingWork ne null, RemainingWork, 0) with sum as SumRemainingWork
跨筛选的工作项聚合 已完成工时 和 剩余工时 数据。
)/compute( (SumCompletedWork add SumRemainingWork) as TotalWork, SumCompletedWork as SumCompleted
计算已完成工时和剩余工时的总汇总。
)/compute( iif(TotalWork gt 0,(SumCompleted div cast(TotalWork, Edm.Double) mul 100), 0) as PercCompletedWork )
计算已完成的 wor 百分比。
创建表报表
若要创建报表,请执行以下步骤:
- 在“建模”选项卡中,选择管理关系并按列链接三个
WorkItemId
查询结果。 - 在“可视化效果”下,选择“表”。
- 从三个 Power BI 查询中添加感兴趣的列。
- 选择 Sum 作为累加列(例如 通过的测试 等)的聚合。
报表应如下图所示。