这段代码是 Kitex 框架中 `callopt` 包的一部分,它负责管理远程过程调用 (RPC) 的选项。
1. **导入包**:
- 该包导入了 Kitex 框架中的几个包,包括 `client`、`discovery`、`fallback`、`http`、`retry`、`rpcinfo` 和 `remoteinfo`。
2. **CallOptions 结构体**:
- 这个结构体表示单个 RPC 调用的选项。
- 它包含以下字段:
- `configs`: 可变的 RPC 配置。
- `svr`: 服务器的远程信息。
- `locks`: 客户端的配置锁。
- `httpResolver`: HTTP 解析器。
- `RetryPolicy`: RPC 调用的重试策略。
- `Fallback`: RPC 调用的回退策略。
- `CompressorName`: 用于 RPC 调用的压缩器名称。
3. **同步池**:
- 该包使用一个同步池 (`callOptionsPool`) 来有效管理 `CallOptions` 实例的创建和重复使用。
- `newOptions` 函数被用作同步池的 `New` 函数,用于创建新的 `CallOptions` 实例。
4. **Recycle 方法**:
- `Recycle` 方法用于重置 `CallOptions` 实例的字段并将其返回到同步池以供重复使用。
5. **Option 结构体**:
- `Option` 结构体表示 RPC 调用开始时使用的一系列选项。
- 它包含一个字段 `f`,是一个函数,用于修改 `CallOptions` 实例和构建调试信息。
-
Option
结构体:- 这个结构体表示 RPC 调用选项,包含一个
f
字段,是一个函数类型,用于修改CallOptions
实例和构建调试信息。
- 这个结构体表示 RPC 调用选项,包含一个
-
F
方法:- 这个方法返回
Option
结构体中的函数f
。 - 这对于从
callopt.Option
创建streamcall.Option
很有用,但需要注意不是所有的callopt.Option
都可用于流客户端。
- 这个方法返回
-
NewOption
函数:- 这个函数返回一个新的
Option
实例,其f
字段为给定的函数。 - 这对于将
streamcall.Option
转换回callopt.Option
很有用。
- 这个函数返回一个新的
-
WithHostPort
函数:- 这个函数返回一个
Option
实例,用于在 RPC 调用时指定目标地址。 - 给定的地址将覆盖从解析器获得的结果。
- 该函数的实现如下:
- 将给定的
hostport
字符串添加到调试信息字符串中。 - 使用
setInstance
函数设置o.svr
字段的值。如果出现错误,则抛出 panic。
- 将给定的
- 这个函数返回一个
这段代码提供了一些有用的函数,用于处理和创建 RPC 调用选项,以及在调用过程中指定目标地址。这些选项可用于控制 RPC 调用的各个方面。
1. `setInstance` 函数:
- 这个函数用于设置 `svr` 字段的值。
- 它首先尝试使用 `net.ResolveTCPAddr` 解析给定的 `hostport` 字符串为 TCP 地址。如果成功,则使用 `discovery.NewInstance` 创建一个新的实例,并将其设置到 `svr` 中。
- 如果 TCP 解析失败,它会尝试使用 `net.ResolveUnixAddr` 解析 Unix 地址。如果成功,同样创建一个新的实例并设置到 `svr` 中。
- 如果两种解析都失败,则返回一个错误,指示 `hostport` 无效。
2. `WithURL` 函数:
- 这个函数返回一个 `Option` 实例,用于在 RPC 调用时指定目标 URL。
- 给定的 URL 将被解析为 `hostport`,并覆盖从解析器获得的结果。
- 该函数的实现如下:
- 将给定的 URL 字符串添加到调试信息字符串中。
- 将 URL 设置到 `svr` 的标签中,使用 `rpcinfo.HTTPURL` 作为键。
- 使用 `o.httpResolver.Resolve` 函数解析 URL 为 `hostport`。如果出现错误,则抛出 panic。
- 使用 `setInstance` 函数设置 `o.svr` 字段的值。如果出现错误,则抛出 panic。
总的来说,这段代码提供了两个额外的选项函数:`WithHostPort` 和 `WithURL`。它们允许在 RPC 调用时指定目标地址,并覆盖从解析器获得的结果。这些选项可以帮助开发者更细粒度地控制 RPC 调用的目标。
1. `WithHTTPHost` 函数:
- 这个函数返回一个 `Option` 实例,用于在 HTTP 头中指定主机名。
- 当 RPC 通过 HTTP 进行时,这个选项可能会有作用。
- 该函数的实现很简单,只是将给定的主机名设置到 `svr` 的标签中,使用 `rpcinfo.HTTPHost` 作为键。
2. `WithRPCTimeout` 函数:
- 这个函数返回一个 `Option` 实例,用于指定 RPC 调用的超时时间。
- 但需要注意,`callopt.WithRPCTimeout` 只有在客户端使用了 `client.WithRPCTimeout` 或 `client.WithTimeoutProvider` 时才会生效。
- 该函数的实现如下:
- 将 `"WithRPCTimeout()"` 字符串添加到调试信息字符串中。
- 使用 `o.configs.SetRPCTimeout` 设置 RPC 超时时间。
- 设置 `o.locks.Bits` 的 `rpcinfo.BitRPCTimeout` 位,以标记 RPC 超时已被设置。
- 还设置了 `o.configs.SetReadWriteTimeout`,但这可能需要考虑是否删除。
3. `WithConnectTimeout` 函数:
- 这个函数返回一个 `Option` 实例,用于指定连接超时时间。
- 该函数的实现与 `WithRPCTimeout` 类似,只是设置的是连接超时时间,并标记 `rpcinfo.BitConnectTimeout` 位。
4. `WithTag` 函数:
- 这个函数返回一个 `Option` 实例,用于设置服务发现的标签。
- 该函数的实现如下:
- 将 `"WithTag"` 字符串和给定的 key-value 对添加到调试信息字符串中。
- 使用 `o.svr.SetTag` 设置标签。
- 将 key 添加到 `o.locks.Tags` 集合中,以标记该标签已被设置。
总的来说,这段代码提供了几个额外的选项函数,用于在 RPC 调用时设置 HTTP 头部、超时时间和服务发现标签。这些选项可以帮助开发者更好地控制 RPC 调用的各个方面。
1. `WithRetryPolicy` 函数:
- 这个函数返回一个 `Option` 实例,用于设置重试策略。
- 如果传入的重试策略 `p` 的 `Enable` 字段为 `false`,直接返回。
- 根据 `p.Type` 的值,在调试信息字符串中写入 `"WithBackupRequest"` 或 `"WithFailureRetry"`。
- 将重试策略 `p` 设置到 `o.RetryPolicy` 字段中。
2. `WithFallback` 函数:
- 这个函数返回一个 `Option` 实例,用于设置回退策略。
- 首先调用 `fallback.IsPolicyValid` 检查传入的回退策略 `fb` 是否有效,如果无效直接返回。
- 在调试信息字符串中写入 `"WithFallback"`。
- 将回退策略 `fb` 设置到 `o.Fallback` 字段中。
3. `WithGRPCCompressor` 函数:
- 这个函数返回一个 `Option` 实例,用于指定 GRPC 数据帧的压缩器。
- 在调试信息字符串中写入 `"WithGRPCCompressor("` 和传入的压缩器名称,并以 `)` 结尾。
- 将压缩器名称设置到 `o.CompressorName` 字段中。
4. `Apply` 函数:
- 这个函数用于应用一组 `CallOptions` 到 `rpcinfo.RPCConfig` 和 `remoteinfo.RemoteInfo` 中。
- 首先从池中获取一个 `CallOptions` 实例,并设置其中的一些字段。
- 遍历传入的 `CallOptions` 数组,依次调用每个 `Option` 的 `f` 函数,将调试信息写入到 `strings.Builder` 中。
- 最后调用 `co.locks.ApplyLocks` 将设置应用到 `rpcinfo.RPCConfig` 和 `remoteinfo.RemoteInfo` 中。
- 返回调试信息字符串和 `CallOptions` 实例。
总的来说,这段代码提供了几个额外的选项函数,用于在 RPC 调用时设置重试策略、回退策略和 GRPC 压缩器,以及一个 `Apply` 函数用于将这些选项应用到 RPC 配置中。这些选项可以帮助开发者更好地控制 RPC 调用的各个方面,提高 RPC 的可靠性和性能。