pub fn kube_str<'a, R: KubeReceiver + ?Sized>(
recv: &'a R,
field: &str,
) -> Option<&'a str>Expand description
Read a sub-<field> YAML scalar-str nested one hop under an
arbitrary &serde_yaml::Value mapping receiver as Option<&str>
— the value-level two-hop navigation primitive that folds
.get(<field>) → as_str into a single helper call. Scalar-str-
arity peer of the value-level sequence-arity kube_seq
(9c74ddb) and value-level first-entry kube_seq_first
(2d6cb54): the trio spans the value-level per-<field> axis at
the three arities every routed test-side + production per-nested-
mapping scalar-typed readback walks through — sequence via
kube_seq, head-entry via kube_seq_first, string-scalar via
this accessor. Structural peer to the spec-anchored
kube_spec_str_field (c4fe21d), metadata-anchored
kube_metadata_str_field (18827), and root-anchored
kube_root_str_field (18921) accessors at one altitude below —
where each of those folds an outer prelude (spec /
metadata / root shape-gate) before the same trailing
get → as_str two-hop, this accessor drops the outer prelude
and stays parametric on the receiver &Value — so a caller
already holding a nested &Value (a spec.ingress[0] bracket
returned from kube_spec_seq_first, a spec.rules[0] first-
rule bracket from the sibling per-HTTPRoute readback, a
spec.listeners[0] first-listener bracket from the sibling
per-Gateway readback, a spec.programs[N] per-entry aggregate
element returned from kube_root_seq_field indexing, any
two-hop nested-mapping bracket the M3 renderer set exposes)
reaches for this accessor directly instead of re-inlining the
two-line .get(<K>).and_then(|v| v.as_str()) block.
Returns None on any of the three short-circuit arms folded
through the underlying two-hop composition: the receiver value
carries a YAML type without a get(<field>) navigation surface
(serde_yaml::Value::get returns None on scalar arms —
string, bool, number, null — that expose no per-key lookup), the
requested <field> axis-key is absent from the receiver’s
mapping (serde_yaml::Value::get trailing miss), or the sub-
field value is present but carries a non-string YAML type (the
trailing .as_str() shape-gate short-circuit — a schema-invalid
scalar type per the K8s apiserver’s OpenAPI schema but
tolerated here as None so the readback stays a total function).
The returned &str borrows into the input Value — the caller
decides whether to assert_eq!(_, Some(<expected>)) for a
determinism pin, thread it through a downstream Option::map /
.filter(|s| _) predicate, or .expect(...) for a load-bearing
scalar identity.
The canonical shape ~18 test-side + production per-nested-
mapping scalar-str readback sites in caixa-mesh,
caixa-flux, and caixa-helm previously
carried inline as the two-line composition
<value>.get(<FIELD>).and_then(|v| v.as_str())
...around a one-token semantic payload (the <FIELD> sub-field
axis-key — KUBE_KEY_PROTOCOL on the per-CNP
toPorts[0].ports[0].protocol: L4 tuple, FLEET_PROGRAMS_KEY_APLICACAO
on the per-programs.yaml-entry parent-Aplicacao label,
CILIUM_KEY_PATH on the per-CNP L7 HTTP-rule path predicate,
GATEWAY_API_KEY_HOSTNAME on the per-Gateway listener
hostname, GATEWAY_API_KEY_NAME on the per-Gateway listener
name and per-HTTPRoute backendRef name, FLEET_PROGRAMS_KEY_NAME
on the per-fleet-programs entry name: axis,
KUBE_KEY_NAMESPACE on the per-programs-entry namespace-
scoping axis, M2_LIMITS_KEY_MEMORY / M2_LIMITS_KEY_CPU /
M2_LIMITS_KEY_WALL_CLOCK on the per-:limits slot rendered-
scalar readbacks). After this lift every routed consumer folds
the two-line navigation onto kube_str(<value>, <FIELD>) — the
two-hop get → as_str walk happens once inside the helper, and
the caller keeps its downstream assertion posture (assert_eq!(_, Some(<expected>)), .expect(...), an if let Some(s) = _
bind) unchanged — the lift closes the navigation surface, not
the per-site downstream posture.
Every future nested <field> scalar-str readback the M3.x + M4
renderer set materializes (per-:politicas
CiliumClusterwideEnvoyConfig per-policy scalar-typed fields,
the app-operator’s per-Aplicacao materializer’s
spec.entrada.host / spec.entrada.paths[N] per-string-scalar
readbacks, the future caixa-otel per-Servico per-receivers. <name>.endpoint scalar-str readback) reaches this one helper by
construction. No per-consumer two-hop re-inline; no coordinated
rewrite across every nested-scalar readback on a future
serde_yaml surface rebrand or shape-gate shift. The trio
(kube_seq, kube_seq_first, kube_str) now closes the
value-level axis at the three principal arities — sequence,
head-entry, string-scalar — matching the closed shape of the
spec/metadata/root-anchored families one altitude above.