status.py•6.54 kB
"""
Tool for checking Splunk connection health.
"""
from typing import Any
from fastmcp import Context
from src.core.base import BaseTool, ToolMetadata
from src.core.utils import log_tool_execution
class GetSplunkHealth(BaseTool):
"""
Get Splunk connection health status.
Supports both server-configured and client-provided Splunk connections.
"""
METADATA = ToolMetadata(
name="get_splunk_health",
description=(
"Check Splunk server connectivity and return comprehensive health status information "
"including server version, connection status, and system information. Supports both "
"server-configured connections and custom connection parameters for testing different "
"Splunk instances. Essential for connectivity troubleshooting and server validation.\\n\\n"
"Args:\\n"
" splunk_host (str, optional): Splunk server hostname or IP address "
"(e.g., 'localhost', 'splunk.example.com', '10.1.1.100')\\n"
" splunk_port (int, optional): Splunk management port, typically 8089 "
"(e.g., 8089, 8000, 9997)\\n"
" splunk_username (str, optional): Splunk username for authentication "
"(e.g., 'admin', 'splunk', 'analyst')\\n"
" splunk_password (str, optional): Splunk password for authentication\\n"
" splunk_scheme (str, optional): Connection scheme - 'http' or 'https'\\n"
" splunk_verify_ssl (bool, optional): Whether to verify SSL certificates\\n\\n"
"Note: If connection parameters are not provided, uses the server's configured connection.\\n\\n"
"Response Format:\\n"
"Returns dictionary with 'status', 'version', 'server_name', and 'connection_source' fields. "
"Status can be 'connected' or 'error'."
),
category="health",
tags=["health", "status", "monitoring", "connectivity"],
requires_connection=False, # This tool should work even when connection is down
)
async def execute(
self,
ctx: Context,
splunk_host: str | None = None,
splunk_port: int | None = None,
splunk_username: str | None = None,
splunk_password: str | None = None,
splunk_scheme: str | None = None,
splunk_verify_ssl: bool | None = None,
) -> dict[str, Any]:
"""
Check Splunk server connectivity and health status.
Args:
splunk_host (str, optional): Splunk server hostname or IP address. If not provided,
uses the server's configured connection.
splunk_port (int, optional): Splunk management port (typically 8089). Defaults to
server configuration.
splunk_username (str, optional): Splunk username for authentication. Uses server
configuration if not provided.
splunk_password (str, optional): Splunk password for authentication. Uses server
configuration if not provided.
splunk_scheme (str, optional): Connection scheme ('http' or 'https'). Defaults to
server configuration.
splunk_verify_ssl (bool, optional): Whether to verify SSL certificates. Defaults to
server configuration.
Returns:
Dict containing connection status, Splunk version, server name, and connection source
"""
log_tool_execution("get_splunk_health")
self.logger.info("Checking Splunk health status...")
await ctx.info("Checking Splunk health status...")
# Extract client configuration from parameters
kwargs = locals().copy()
kwargs.pop("self")
kwargs.pop("ctx")
client_config = self.extract_client_config(kwargs)
try:
# Try to get Splunk service with client config or fallback to server default
service = await self.get_splunk_service(ctx, client_config)
# If we got here, we have a working connection
info = {
"status": "connected",
"version": service.info["version"],
"server_name": service.info.get("host", "unknown"),
"connection_source": "client_config" if client_config else "server_config",
}
# splunklib.client.Service.get is synchronous and returns a Record object
host_wide = service.get("/services/server/status/resource-usage/hostwide")
self.logger.info("Host wide: %s", host_wide)
await ctx.info(f"Health check successful: {info}")
self.logger.info("Health check successful: %s", info)
return info
except Exception as e:
# If client config fails, also try server default if we haven't already
if client_config:
self.logger.info("Client config failed, trying server default...")
try:
# Check server default connection
splunk_ctx = ctx.request_context.lifespan_context
if splunk_ctx.is_connected and splunk_ctx.service:
service = splunk_ctx.service
info = {
"status": "connected",
"version": service.info["version"],
"server_name": service.info.get("host", "unknown"),
"connection_source": "server_config",
"note": "Client config failed, using server default",
}
await ctx.info(f"Health check successful with server config: {info}")
self.logger.info("Health check successful with server config: %s", info)
return info
except Exception as fallback_error:
self.logger.error("Both client and server configs failed: %s", fallback_error)
# Both attempts failed
self.logger.error("Health check failed: %s", str(e))
await ctx.error(f"Health check failed: {str(e)}")
return {
"status": "error",
"error": str(e),
"connection_source": "client_config" if client_config else "server_config",
}