From 8301705070522c0b2598cf17a3002fa667b024b2 Mon Sep 17 00:00:00 2001 From: Lee Smith Date: Fri, 1 Nov 2024 17:49:09 +0000 Subject: [PATCH] Add agent-metrics-listener-port annotation --- agent-inject/agent/agent.go | 17 ++++++++++ agent-inject/agent/annotations.go | 3 ++ agent-inject/agent/config.go | 35 ++++++++++++++------ agent-inject/agent/container_init_sidecar.go | 7 ++++ agent-inject/agent/container_sidecar.go | 7 ++++ 5 files changed, 58 insertions(+), 11 deletions(-) diff --git a/agent-inject/agent/agent.go b/agent-inject/agent/agent.go index 4a21bbb5..51e4cabe 100644 --- a/agent-inject/agent/agent.go +++ b/agent-inject/agent/agent.go @@ -37,6 +37,7 @@ const ( DefaultServiceAccountMount = "/var/run/secrets/vault.hashicorp.com/serviceaccount" DefaultEnableQuit = false DefaultAutoAuthEnableOnExit = false + DefaultAgentMetricsListenerPort = -1 ) // Agent is the top level structure holding all the @@ -131,6 +132,9 @@ type Agent struct { // template_config specific configuration VaultAgentTemplateConfig VaultAgentTemplateConfig + // VaultAgentMetricsListenerPort is the port used to server the Vault agent metrics + VaultAgentMetricsListenerPort int64 + // RunAsUser is the user ID to run the Vault agent container(s) as. RunAsUser int64 @@ -544,6 +548,19 @@ func New(pod *corev1.Pod) (*Agent, error) { return nil, err } + if pod.Annotations[AnnotationAgentMetricsListenerPort] != "" { + agentMetricsListenerPort, err := parseutil.SafeParseInt(pod.Annotations[AnnotationAgentMetricsListenerPort]) + if err != nil { + return agent, err + } + if agentMetricsListenerPort < 0 || agentMetricsListenerPort > 65535 { + return agent, errors.New("invalid port number: must be in the range 0 to 65535") + } + agent.VaultAgentMetricsListenerPort = agentMetricsListenerPort + } else { + agent.VaultAgentMetricsListenerPort = DefaultAgentMetricsListenerPort + } + return agent, nil } diff --git a/agent-inject/agent/annotations.go b/agent-inject/agent/annotations.go index 4a12a8a1..747c7580 100644 --- a/agent-inject/agent/annotations.go +++ b/agent-inject/agent/annotations.go @@ -323,6 +323,9 @@ const ( // should map to the same unique value provided in // "vault.hashicorp.com/agent-inject-secret-". Defaults to false AnnotationErrorOnMissingKey = "vault.hashicorp.com/error-on-missing-key" + + // AnnotationAgentMetricsListenerPort configures the port the agent metrics server should listen on + AnnotationAgentMetricsListenerPort = "vault.hashicorp.com/agent-metrics-listener-port" ) type AgentConfig struct { diff --git a/agent-inject/agent/config.go b/agent-inject/agent/config.go index e4437291..9ea8d3e5 100644 --- a/agent-inject/agent/config.go +++ b/agent-inject/agent/config.go @@ -90,12 +90,13 @@ type Template struct { ErrMissingKey bool `json:"error_on_missing_key,omitempty"` } -// Listener defines the configuration for Vault Agent Cache Listener +// Listener defines the configuration for Vault Agent Cache Listener and/ or Vault Agent Metrics Listener type Listener struct { Type string `json:"type"` Address string `json:"address"` TLSDisable bool `json:"tls_disable"` AgentAPI *AgentAPI `json:"agent_api,omitempty"` + Role string `json:"role,omitempty"` } // AgentAPI defines the agent_api stanza for a listener @@ -271,7 +272,7 @@ func (a *Agent) newConfig(init bool) ([]byte, error) { cacheListener := makeCacheListener(a.VaultAgentCache.ListenerPort) if a.VaultAgentCache.Persist { - config.Listener = cacheListener + config.Listener = append(config.Listener, &cacheListener) config.Cache = &Cache{ UseAutoAuthToken: a.VaultAgentCache.UseAutoAuthToken, Persist: &CachePersist{ @@ -281,7 +282,7 @@ func (a *Agent) newConfig(init bool) ([]byte, error) { }, } } else if a.VaultAgentCache.Enable && !a.PrePopulateOnly && !init { - config.Listener = cacheListener + config.Listener = append(config.Listener, &cacheListener) config.Cache = &Cache{ UseAutoAuthToken: a.VaultAgentCache.UseAutoAuthToken, } @@ -296,7 +297,7 @@ func (a *Agent) newConfig(init bool) ([]byte, error) { EnableQuit: a.EnableQuit, } } else { - config.Listener = makeCacheListener(a.VaultAgentCache.ListenerPort) + config.Listener = append(config.Listener, &cacheListener) config.Listener[0].AgentAPI = &AgentAPI{ EnableQuit: a.EnableQuit, } @@ -307,6 +308,11 @@ func (a *Agent) newConfig(init bool) ([]byte, error) { } } + if a.VaultAgentMetricsListenerPort != -1 { + metricsListener := makeMetricsListener(a.VaultAgentMetricsListenerPort) + config.Listener = append(config.Listener, &metricsListener) + } + return config.render() } @@ -314,12 +320,19 @@ func (c *Config) render() ([]byte, error) { return json.Marshal(c) } -func makeCacheListener(port string) []*Listener { - return []*Listener{ - { - Type: "tcp", - Address: fmt.Sprintf("127.0.0.1:%s", port), - TLSDisable: true, - }, +func makeCacheListener(port string) Listener { + return Listener{ + Type: "tcp", + Address: fmt.Sprintf("127.0.0.1:%s", port), + TLSDisable: true, + } +} + +func makeMetricsListener(port int64) Listener { + return Listener{ + Type: "tcp", + Address: fmt.Sprintf("0.0.0.0:%d", port), + TLSDisable: true, + Role: "metrics_only", } } diff --git a/agent-inject/agent/container_init_sidecar.go b/agent-inject/agent/container_init_sidecar.go index 2e36d229..ad1ed939 100644 --- a/agent-inject/agent/container_init_sidecar.go +++ b/agent-inject/agent/container_init_sidecar.go @@ -95,6 +95,13 @@ func (a *Agent) ContainerInitSidecar() (corev1.Container, error) { if a.SetSecurityContext { newContainer.SecurityContext = a.securityContext() } + if a.VaultAgentMetricsListenerPort > 0 { + containerPort := corev1.ContainerPort{ + Name: "agent-metrics", + ContainerPort: int32(a.VaultAgentMetricsListenerPort), + } + newContainer.Ports = append(newContainer.Ports, containerPort) + } // apply any JSON patch requested if a.InitJsonPatch == "" { diff --git a/agent-inject/agent/container_sidecar.go b/agent-inject/agent/container_sidecar.go index c89645e0..be621ed9 100644 --- a/agent-inject/agent/container_sidecar.go +++ b/agent-inject/agent/container_sidecar.go @@ -110,6 +110,13 @@ func (a *Agent) ContainerSidecar() (corev1.Container, error) { if a.SetSecurityContext { newContainer.SecurityContext = a.securityContext() } + if a.VaultAgentMetricsListenerPort > 0 { + containerPort := corev1.ContainerPort{ + Name: "agent-metrics", + ContainerPort: int32(a.VaultAgentMetricsListenerPort), + } + newContainer.Ports = append(newContainer.Ports, containerPort) + } // apply any JSON patch requested if a.JsonPatch == "" {