Inspect 是 Fuchsia 组件的一项强大的诊断功能。
本文档详细介绍了组件如何托管其检查数据,以及各种工具如何发现这些数据。
Hosting 检查数据
组件可能会通过以下方式显示检查数据:
fuchsia.inspect.Tree
(C++、Rust)VmoFile
(Dart)fuchsia.inspect.deprecated.Inspect
(Go 版)
组件无需联系其他服务即可公开检查数据。
组件通常不需要关注所使用的方法,客户端库会将具体的托管机制抽象化。几乎所有实现最终都会使用 Tree
。
功能 | fuchsia.inspect.Tree |
VmoFile |
fuchsia.inspect.deprecated.Inspect |
说明 |
---|---|---|---|---|
非延迟值 | 是 | 是 | 是 | 组件可以记录字符串和整数等值。 |
延迟值 | 是 | 否 | 是 | 组件可以在读取时动态生成值。 |
可变树 | 是 | 是 | 是 | 组件可能会修改存储在其输出中的值。 |
事后检查 | 是 | 是 | 否 | 组件记录的值在组件退出后可用。 |
低延迟快照 | 是 | 是 | 否 | 以较低的延迟获得数据的完整快照。 |
一致的快照 | 是* | 是 | 否 | 该树的快照保证能呈现其在某个时间点的状态。 |
(*:每个树的快照都是一致的,但无法保证树间一致性)
fuchsia.inspect.Tree
fuchsia.inspect.Tree
支持 Inspect API 的所有功能,因此建议您使用此方式公开组件中的 Inspect 数据。
组件使用 fuchsia.inspect.InspectSink
协议发布 fuchsia.inspect.Tree
。
实现
fuchsia.inspect.Tree
FIDL 文件定义了由组件托管的协议,用于提供其 Inspect 数据。
Tree
协议在“树状树”中将多个检查 VMO 链接在一起。
在上图中,名为“root”的树会处理托管在 fuchsia.inspect.Tree
下的顶级服务上的连接的 fuchsia.inspect.Tree
协议。您可以使用协议中的方法枚举和打开子树。例如,“子项 B”在打开并读取之前可能不存在于内存中。
该协议通过以下方式支持此行为:
GetContent
此方法会获取树的内容,目前采用检查 VMO 的形式。按照惯例,在根树上调用此方法应返回一个 VMO,该 VMO 将用新数据持续更新。客户端无需重新读取树的内容即可读取新值。
ListChildNames
此方法接受一个迭代器,系统将根据该迭代器返回树的子项名称。例如,在根树上运行时,上图中的树将返回名称为“子 A”和“子 B”。
OpenChild
此方法接受对
fuchsia.inspect.Tree
的请求,该请求将绑定到由给定名称指定的树。使用此方法,客户端可以遍历在根 iterface 上公开的所有树。
fuchsia.inspect.deprecated.Inspect
这个已废弃的接口供 Go 用于公开 Inspect 数据。虽然 fuchsia.inspect.Tree
会公开“树树”,但此接口仅公开一个树,其中子树可以动态实例化。
此接口已废弃,取而代之的是由检查树托管的 VMO 格式,原因如下:
- VMO 格式支持低延迟快照,而无需与托管程序通信。
- VMO 格式快照对于整个树始终是一致的。
- VMO 格式支持事后分析,所有使用已弃用接口的 Inspect 数据都会随组件一起终止。
Tree
协议支持的动态功能与已弃用的接口相同。
读取检查数据
读取检查数据的两种主要方式是:
iquery
iquery (Inspect Query) 是用于与 Inspect 数据交互的 CLI。
iquery
的主要操作模式接受用于检查数据的选择器列表,并输出包含的信息。选择器由三部分组成,三部分由 :
分隔:
- 组件选择器:这是 v2 中的名称,或者 v1 中的领域路径加上组件名称。
- 节点路径:指向检查层次结构中某个节点的路径。
- 属性路径:属性的名称。
对于 iquery
,必须提供 (1)。如果只提供 (1)(例如 realm/component
),iquery 将使用选择器 realm/component:*
获取所有检查数据。
iquery
包含两个实用程序命令,可用于了解哪些组件可用以及哪些选择器可用于:
list
:iquery 将输出所有可用的组件选择器,这包含所有 v2 名称以及带有组件名称的所有 v1 Realm 路径。selectors
:iquery 将输出提供的选择器位置下的所有可用选择器。
这些模式可以按如下方式一起使用:
$ iquery show `iquery list | grep component_name`
或者,iquery
还允许在某个位置输出检查数据。位置包含 .inspect
文件的路径或包含 fuchsia.inspect.Tree
的目录的路径。iquery
包含一个实用程序命令,用于列出包含检查数据 (list-files
) 的所有文件。
iquery 的次要操作模式(由 list-files
触发)以递归方式标识来自给定目录路径的 Inspect 数据的位置。这两种模式可以一起使用,如下所示:
$ iquery list-files [component_moniker]
bootstrap/driver_manager
class/display-coordinator/000.inspect
... additional output
$ iquery show --file 'class/display-coordinator/000.inspect'
在上面的示例中,系统会运行 iquery list-files
以查找 Inspect 位置列表。然后,对其中一个输出运行 iquery
,以递归方式列出匹配位置中的数据。您可以改为编写:
$ fx iquery show --manifest component_name
存档人员
由 Archivist 托管的 Fuchsia Diagnostics Platform 负责监控和汇总检查数据(按需)。
在组件管理器下运行时,可通过事件功能向 Archivist 提供诊断数据。
The Archivist 由根领域提供活动。因此,它可以查看来自整个系统的事件。它可以查看和订阅的事件如下所示:
- CapabilityRequested:当组件连接到
InspectSink
或LogSink
时,发送到 Archivist,而不是常规目录连接。这样一来,Archivist 就可以知道连接到这些协议的组件的名称和网址。
希望公开 Inspect 的组件需要使用 fuchsia.inspect.InspectSink
协议。通常如下所示:
{
use: [
{
protocol: "fuchsia.inspect.InspectSink",
from: "parent",
},
],
}
有一个有用的清单 include 可以简化该清单,并且是 Inspect 库所必需的:
{
include: [
"inspect/client.shard.cml",
]
}
从 Archivist 读取检查
Archivist 托管了 fuchsia.diagnostics.ArchiveAccessor
,它提供了 StreamDiagnostics
方法,用于从正在运行的组件中获取 Inspect 数据。