Skip to content

Commit b81782d

Browse files
committed
Add deployment context detection for targeted user guidance
Adds utility to detect whether user is running via: - CLI (command line) - Helm chart (Robusta) - Helm chart (Holmes standalone) This enables showing deployment-specific guidance for environment variable configuration and other setup instructions. Key features: - DeploymentContext class with method and chart_type detection - get_env_var_guidance() helper for generating targeted help messages - Detection based on PLAYBOOKS_CONFIG_FILE_PATH, INSTALLATION_NAMESPACE, RELEASE_NAME, HOLMES_ENABLED, and HOLMES_STANDALONE env vars - Different guidance for CLI users vs Robusta Helm vs Holmes Helm https://claude.ai/code/session_01DuWGiUa4DB1FBPG5mLmqhD
1 parent 1c19e63 commit b81782d

2 files changed

Lines changed: 439 additions & 0 deletions

File tree

Lines changed: 264 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,264 @@
1+
"""
2+
Utilities for detecting deployment context (CLI vs Helm, Robusta vs Holmes).
3+
4+
This module provides functions to detect how Robusta/Holmes is deployed and
5+
generate appropriate guidance messages for users based on their deployment method.
6+
"""
7+
8+
import os
9+
from enum import Enum
10+
from typing import Optional
11+
12+
13+
class DeploymentMethod(Enum):
14+
"""How the application is deployed."""
15+
CLI = "cli"
16+
HELM = "helm"
17+
UNKNOWN = "unknown"
18+
19+
20+
class ChartType(Enum):
21+
"""Which Helm chart is being used (if deployed via Helm)."""
22+
ROBUSTA = "robusta"
23+
HOLMES = "holmes"
24+
UNKNOWN = "unknown"
25+
26+
27+
class DeploymentContext:
28+
"""Detected deployment context information."""
29+
30+
def __init__(
31+
self,
32+
method: DeploymentMethod,
33+
chart_type: ChartType,
34+
release_name: Optional[str] = None,
35+
namespace: Optional[str] = None,
36+
):
37+
self.method = method
38+
self.chart_type = chart_type
39+
self.release_name = release_name
40+
self.namespace = namespace
41+
42+
@property
43+
def is_cli(self) -> bool:
44+
return self.method == DeploymentMethod.CLI
45+
46+
@property
47+
def is_helm(self) -> bool:
48+
return self.method == DeploymentMethod.HELM
49+
50+
@property
51+
def is_robusta_chart(self) -> bool:
52+
return self.chart_type == ChartType.ROBUSTA
53+
54+
@property
55+
def is_holmes_chart(self) -> bool:
56+
return self.chart_type == ChartType.HOLMES
57+
58+
59+
def detect_deployment_context() -> DeploymentContext:
60+
"""
61+
Detect the current deployment context based on environment variables.
62+
63+
Detection logic:
64+
- CLI: No PLAYBOOKS_CONFIG_FILE_PATH and no INSTALLATION_NAMESPACE set
65+
(or INSTALLATION_NAMESPACE is the default "robusta" without other indicators)
66+
- Helm (Robusta): Has PLAYBOOKS_CONFIG_FILE_PATH set to /etc/robusta/... path
67+
- Helm (Holmes standalone): Has HOLMES_ENABLED but no Robusta-specific paths,
68+
or explicitly marked via HOLMES_STANDALONE env var
69+
70+
Returns:
71+
DeploymentContext with detected method and chart type
72+
"""
73+
playbooks_config_path = os.environ.get("PLAYBOOKS_CONFIG_FILE_PATH")
74+
installation_namespace = os.environ.get("INSTALLATION_NAMESPACE")
75+
release_name = os.environ.get("RELEASE_NAME")
76+
holmes_enabled = os.environ.get("HOLMES_ENABLED", "false").lower() == "true"
77+
holmes_standalone = os.environ.get("HOLMES_STANDALONE", "false").lower() == "true"
78+
79+
# Check for explicit Holmes standalone marker
80+
if holmes_standalone:
81+
return DeploymentContext(
82+
method=DeploymentMethod.HELM,
83+
chart_type=ChartType.HOLMES,
84+
release_name=release_name,
85+
namespace=installation_namespace,
86+
)
87+
88+
# Robusta Helm deployment: has playbooks config path pointing to /etc/robusta/
89+
if playbooks_config_path and playbooks_config_path.startswith("/etc/robusta/"):
90+
return DeploymentContext(
91+
method=DeploymentMethod.HELM,
92+
chart_type=ChartType.ROBUSTA,
93+
release_name=release_name,
94+
namespace=installation_namespace,
95+
)
96+
97+
# Check if we're in a Kubernetes environment (has namespace set from pod metadata)
98+
# This would indicate Helm deployment even without the config path
99+
if installation_namespace and installation_namespace != "robusta":
100+
# Non-default namespace suggests actual Helm deployment
101+
chart_type = ChartType.HOLMES if holmes_enabled and not playbooks_config_path else ChartType.ROBUSTA
102+
return DeploymentContext(
103+
method=DeploymentMethod.HELM,
104+
chart_type=chart_type,
105+
release_name=release_name,
106+
namespace=installation_namespace,
107+
)
108+
109+
# If we have a release name that's not the default, likely Helm
110+
if release_name and release_name != "robusta":
111+
chart_type = ChartType.HOLMES if holmes_enabled and not playbooks_config_path else ChartType.ROBUSTA
112+
return DeploymentContext(
113+
method=DeploymentMethod.HELM,
114+
chart_type=chart_type,
115+
release_name=release_name,
116+
namespace=installation_namespace,
117+
)
118+
119+
# Default to CLI if no Helm indicators found
120+
return DeploymentContext(
121+
method=DeploymentMethod.CLI,
122+
chart_type=ChartType.UNKNOWN,
123+
)
124+
125+
126+
def get_env_var_guidance(var_name: str, context: Optional[DeploymentContext] = None) -> str:
127+
"""
128+
Generate guidance for setting an environment variable based on deployment context.
129+
130+
Args:
131+
var_name: The name of the environment variable
132+
context: Optional pre-detected deployment context. If None, will be detected.
133+
134+
Returns:
135+
A helpful message with instructions for the detected deployment method.
136+
"""
137+
if context is None:
138+
context = detect_deployment_context()
139+
140+
if context.is_cli:
141+
return _get_cli_guidance(var_name)
142+
elif context.is_helm:
143+
if context.is_robusta_chart:
144+
return _get_robusta_helm_guidance(var_name)
145+
elif context.is_holmes_chart:
146+
return _get_holmes_helm_guidance(var_name)
147+
else:
148+
# Generic Helm guidance
149+
return _get_generic_helm_guidance(var_name)
150+
else:
151+
return _get_generic_guidance(var_name)
152+
153+
154+
def _get_cli_guidance(var_name: str) -> str:
155+
"""Guidance for CLI users."""
156+
return f"""Environment variable '{var_name}' is not set.
157+
158+
To fix this issue, set the environment variable before running the command:
159+
160+
export {var_name}=<your-value>
161+
162+
Or pass it inline:
163+
164+
{var_name}=<your-value> robusta <command>"""
165+
166+
167+
def _get_robusta_helm_guidance(var_name: str) -> str:
168+
"""Guidance for Robusta Helm chart users."""
169+
return f"""Environment variable '{var_name}' is not set.
170+
171+
To fix this issue, add the environment variable to your Robusta Helm values.yaml:
172+
173+
runner:
174+
additional_env_vars:
175+
- name: {var_name}
176+
value: "<your-value>"
177+
178+
# Or use a Kubernetes secret:
179+
runner:
180+
additional_env_vars:
181+
- name: {var_name}
182+
valueFrom:
183+
secretKeyRef:
184+
name: <secret-name>
185+
key: <secret-key>
186+
187+
Then upgrade your Helm release:
188+
189+
helm upgrade robusta robusta/robusta -f values.yaml
190+
191+
For more information, see: https://docs.robusta.dev/master/configuration/index.html"""
192+
193+
194+
def _get_holmes_helm_guidance(var_name: str) -> str:
195+
"""Guidance for Holmes standalone Helm chart users."""
196+
return f"""Environment variable '{var_name}' is not set.
197+
198+
To fix this issue, add the environment variable to your Holmes Helm values.yaml:
199+
200+
additionalEnvVars:
201+
- name: {var_name}
202+
value: "<your-value>"
203+
204+
# Or use a Kubernetes secret:
205+
additionalEnvVars:
206+
- name: {var_name}
207+
valueFrom:
208+
secretKeyRef:
209+
name: <secret-name>
210+
key: <secret-key>
211+
212+
Then upgrade your Helm release:
213+
214+
helm upgrade holmes robusta/holmes -f values.yaml
215+
216+
For more information, see: https://holmesgpt.dev/getting-started/"""
217+
218+
219+
def _get_generic_helm_guidance(var_name: str) -> str:
220+
"""Generic Helm guidance when chart type is unknown."""
221+
return f"""Environment variable '{var_name}' is not set.
222+
223+
To fix this issue, add the environment variable to your Helm values.yaml:
224+
225+
additionalEnvVars:
226+
- name: {var_name}
227+
value: "<your-value>"
228+
229+
# Or use a Kubernetes secret:
230+
additionalEnvVars:
231+
- name: {var_name}
232+
valueFrom:
233+
secretKeyRef:
234+
name: <secret-name>
235+
key: <secret-key>
236+
237+
Then upgrade your Helm release with:
238+
239+
helm upgrade <release-name> <chart> -f values.yaml"""
240+
241+
242+
def _get_generic_guidance(var_name: str) -> str:
243+
"""Generic guidance when deployment method is unknown."""
244+
return f"""Environment variable '{var_name}' is not set.
245+
246+
To fix this issue:
247+
248+
For CLI users:
249+
export {var_name}=<your-value>
250+
251+
For Helm chart users (Holmes or Robusta):
252+
Add the environment variable to your values.yaml:
253+
254+
additionalEnvVars:
255+
- name: {var_name}
256+
value: "<your-value>"
257+
258+
# Or use a secret:
259+
additionalEnvVars:
260+
- name: {var_name}
261+
valueFrom:
262+
secretKeyRef:
263+
name: <secret-name>
264+
key: <secret-key>"""

0 commit comments

Comments
 (0)