网络排查
本页介绍怎样确认网络策略、Egress 与 Resolver 的修改已经生效,以及连接或 DNS 查询失败时怎样分辨原因。
确认策略已经生效
对 AVAILABLE 的 Workspace,修改策略的请求成功,说明 node 已经应用了新策略,见修改什么时候生效。以下情形需要查看 node 报告的生效情况:
- 修改策略失败或超时。
- 修改时 Workspace 处于
STOPPED,策略在下次启动时应用。 - 更新了 Egress 或 Resolver。更新在保存后即返回,引用它的每个运行中的 Workspace 随后才切换过去。
- 旧版本的连接仍在宽限期内。
kibo workspace get 显示 node 报告的生效情况;加 --wide 还能看到各个版本:
kibo workspace get "$workspace_id"
kibo workspace get "$workspace_id" --wide对运行中的 Workspace,输出里有这些行:
| 行 | 内容 |
|---|---|
| Network | 期望的 mode。还没有确认应用时附 (not confirmed yet);已应用的是旧策略时附 (applied: <mode>, change pending);还有旧策略 revision 的连接在宽限期内时附 connections of revision N still draining |
| Allow、Deny | 策略的目的地规则,每个条目一行 |
| Egress、Via Egress | 策略引用的 Egress 与它的网段,每条一行 |
| Egress applied | 每个 Egress 新连接所用的 Egress revision;旧 revision 的连接还在宽限期内时附上那个 revision |
| Egress fault | 故障类别与开始时间,见 Egress 的故障 |
| Resolver | 策略引用的 Resolver 与它的路径 |
| Resolver applied | 新查询所用的 Resolver revision |
| Resolver fault | 故障类别与开始时间,见 Resolver 的故障 |
- 期望策略与已应用策略的版本在
workspace get --wide的 Revisions 一节与 JSON 输出中。 Egress applied一行的 revision 与kibo egress get给出的一致时,Egress 的更新已经生效。Resolver applied一行的 revision 与kibo resolver get给出的一致时,Resolver 的更新已经生效。
这些行背后的状态字段见策略状态。
排查
| 现象 | 原因 | 处理 |
|---|---|---|
| 连接立即失败,不是超时 | 目的地在 deny 里,或直出的目的地是私网与特殊用途地址 | 检查 allow、deny;要到调用方内网的地址,把它写进 Egress 网段 |
| 目的地在 Egress 网段里的连接被重置 | Egress 故障,连接不回退直出 | 看 Egress fault 一行或 egress_observations |
DNS 查询得到 SERVFAIL | 引用的 Resolver 上游不可用 | 看 Resolver fault 一行或 resolver_observations;路径经 Egress 时也看 Egress 的故障 |
| DNS 查询立即失败 | 策略是 DENY_ALL | 改为 PUBLIC_INTERNET |
ping 公网没有回应 | 上联的网关只转换 TCP 与 UDP,Echo Request 停在网关上。在 guest 里看,这与 node 拒绝没有区别 | 请部署方确认上联出口会转发 ICMP |
修改返回 failed_precondition,reason 为 CAPABILITY_UNAVAILABLE | Workspace 所在的 node 不支持目的地规则、Egress 或 Resolver | 不带这一部分,或请部署方升级 node |
引用 Resolver 返回 failed_precondition,reason 为 CONFLICT | Workspace 在升级前启动,仍用原来的 DNS 配置 | 停止再启动 Workspace,然后重新引用 |
kibo 退出 14 | 服务端没有宣告对应的能力 | 见能力名 |
kibo 退出 13 | 期间被别人改过,或要删除的 Egress、Resolver 仍被引用 | 重新读取后再决定;删除前先解除引用 |
Egress 的故障
Egress 出故障时,guest 只看到连接被重置,不回退直出。端点恢复后,下一次经 Egress 的连接成功,故障记录随之清除。下图依次展示这两步:
原因记在 Workspace 里,每个有故障的 Egress 一项。kibo workspace get 在 Egress fault 一行显示故障类别与开始时间:
| 类别 | 含义 |
|---|---|
ENDPOINT_UNREACHABLE | 连不上端点,或端点地址都被拒绝 |
TLS_VERIFICATION_FAILED | 证书不受信任,或与校验名不符 |
HANDSHAKE_FAILED | SOCKS5 协商失败、应答非法或超时 |
AUTHENTICATION_FAILED | 端点明确拒绝凭证 |
UDP_ASSOCIATION_FAILED | 端点拒绝 UDP 关联、答复的中继地址被拒绝,或向中继发送时收到不可达 |
- 它是观测,不是状态。 有故障时 Workspace 仍是
AVAILABLE,读取不访问 node。故障持续时内容不变,下一次经 Egress 的连接成功后清除。 - 没有
AUTHENTICATION_FAILED不说明凭证正确。 端点对错误凭证不作应答时,观测是ENDPOINT_UNREACHABLE或HANDSHAKE_FAILED。 - 代理报告目的地不可达或拒绝连接是单次连接的结果,不产生观测。
- 类别以后会增加取值。 遇到不认识的值时按出口故障处理,不当作没有故障。
kibo把它显示为UNKNOWN_FAULT(n)。 - 多久能看到: 从故障出现到 ctrl 读得到,一般在 2 分钟以内。
Resolver 的故障
上游出故障时,guest 的查询得到 SERVFAIL,不回退部署 DNS 服务器。原因记在 Workspace 里,策略中每个有故障的 Resolver 项一项。kibo workspace get 在 Resolver fault 一行显示故障类别与开始时间:
| 类别 | 含义 |
|---|---|
UPSTREAM_UNREACHABLE | 连不上上游,或直出时上游地址都被拒绝 |
UPSTREAM_TIMEOUT | 时限内没有应答 |
TLS_VERIFICATION_FAILED | tls 或 https 上游的证书不受信任,或与 host 不符 |
HTTP_ERROR_STATUS | https 上游返回非 2xx |
- 上游正常回答的
NXDOMAIN、SERVFAIL是 DNS 的结果,不产生观测。 - 经 Egress 时,Egress 自身的故障记为 Egress 的故障,这里不重复。
- 其余规则同 Egress 的故障。 故障不改变 Workspace 状态,读取不访问 node,故障持续时内容不变,下一次查询成功后清除;类别以后会增加取值,遇到不认识的值时按上游故障处理。
用 API
策略状态
Workspace 的 network_policy_status 是 node 报告的生效情况,从未确认生效或已失效时为空:
| 字段 | 含义 |
|---|---|
applied_revision、mode | node 上正在执行的策略 revision 与 mode |
draining_revision | 还有按更早策略 revision 建立、仍在宽限期内的连接时,给出其中最早的 revision;没有时为 0 |
egresses | 策略引用的每个 Egress 一项:egress_id;applied_revision 是新连接所用的 Egress revision;draining_revision 是还在宽限期内的连接所用的最早 Egress revision,没有时为 0 |
resolvers | 策略 resolvers 的每一项一项,用 resolver_id 加 path 对应;applied_revision 是新查询所用的 Resolver revision |
| 要确认的事 | 判断 |
|---|---|
| 策略的修改已经生效 | applied_revision 等于策略的 revision |
| 已下发、还没确认 | applied_revision 小于策略的 revision,Workspace 不是 FAILED |
| Egress 的更新已经生效 | egresses 里这个 Egress 的 applied_revision 等于 Egress 的 revision |
| Resolver 的更新已经生效 | resolvers 里对应项的 applied_revision 等于 Resolver 的 revision |
| 旧连接都已关闭 | draining_revision 与 egresses 各项的 draining_revision 都是 0 |
故障观测
Egress 的故障在 Workspace 的 egress_observations 里,每个有故障的 Egress 一项,没有故障时为空;Resolver 的故障在 resolver_observations 里,每个有故障的列表项一项,没有故障时为空。kibo workspace get 的 Egress fault 与 Resolver fault 两行取自这两个字段。
| 字段 | 含义 |
|---|---|
egress_id(Egress);resolver_id、path(Resolver) | 有故障的 Egress,或有故障的列表项 |
kind | 故障类别,见 Egress 的故障与 Resolver 的故障里的表 |
failing_since | 这一轮连续故障开始的时间,取 node 的时钟 |
observed_at | ctrl 记下这份报告的时间,取 ctrl 的时钟 |
下一步
- 网络策略:策略的修改什么时候生效。
- Egress:Egress 的更新怎样切换连接。
- DNS 与 Resolver:guest 的 DNS 查询去哪里。