Skip to main content
Glama

MCP Server for Splunk

Apache 2.0
16
  • Apple
  • Linux
splunk_docs.pyโ€ข36.6 kB
""" Splunk documentation resources for MCP server. Provides version-aware access to Splunk documentation, optimized for LLM consumption. """ import logging from datetime import datetime, timedelta from typing import Any from fastmcp import Context try: import httpx HAS_HTTPX = True except ImportError: HAS_HTTPX = False from src.core.base import BaseResource, ResourceMetadata from src.core.registry import resource_registry from .processors.html_processor import SplunkDocsProcessor logger = logging.getLogger(__name__) class DocumentationCache: """Version-aware caching for Splunk documentation.""" def __init__(self, ttl_hours: int = 24): self.cache: dict[str, dict[str, Any]] = {} self.ttl_hours = ttl_hours def cache_key(self, version: str, category: str, topic: str) -> str: """Generate cache key for documentation.""" return f"docs_{version}_{category}_{topic}" def is_expired(self, timestamp: datetime) -> bool: """Check if cached item is expired.""" return datetime.now() - timestamp > timedelta(hours=self.ttl_hours) async def get_or_fetch(self, version: str, category: str, topic: str, fetch_func) -> str: """Get from cache or fetch if expired/missing.""" key = self.cache_key(version, category, topic) if key in self.cache: cached_item = self.cache[key] if not self.is_expired(cached_item["timestamp"]): logger.debug(f"Cache hit for {key}") return cached_item["content"] # Fetch fresh content logger.debug(f"Cache miss for {key}, fetching") content = await fetch_func() self.cache[key] = {"content": content, "timestamp": datetime.now(), "version": version} return content def invalidate_version(self, version: str): """Invalidate all cached docs for a specific version.""" keys_to_remove = [k for k in self.cache.keys() if k.startswith(f"docs_{version}_")] for key in keys_to_remove: del self.cache[key] logger.info(f"Invalidated {len(keys_to_remove)} cache entries for version {version}") # Global documentation cache _doc_cache = DocumentationCache() class SplunkDocsResource(BaseResource): """Base class for Splunk documentation resources.""" # SPLUNK_DOCS_BASE = "https://docs.splunk.com" SPLUNK_HELP_BASE = "https://help.splunk.com" VERSION_MAPPING = { "10.0.0": "10.0", "9.4.0": "9.4", "9.3.0": "9.3", "9.2.1": "9.2", "9.1.0": "9.1", "latest": "10.0", # Current latest } def __init__(self, uri: str, name: str, description: str, mime_type: str = "text/markdown"): super().__init__(uri, name, description, mime_type) self.processor = SplunkDocsProcessor() async def get_splunk_version(self, ctx: Context) -> str: """Detect Splunk version from connected instance.""" try: # Import here to avoid circular imports from src.tools.health.status import GetSplunkHealth health_tool = GetSplunkHealth("get_splunk_health", "Get Splunk health status") health_result = await health_tool.execute(ctx) if health_result.get("status") == "connected": version = health_result.get("version", "latest") logger.debug(f"Detected Splunk version: {version}") return version except Exception as e: logger.warning(f"Failed to detect Splunk version: {e}") return "latest" def normalize_version(self, version: str) -> str: """Convert version to docs URL format.""" # Handle auto-detection if version == "auto": version = "latest" # Extract major.minor from full version if needed if version not in self.VERSION_MAPPING: # Try to match major.minor (e.g., "9.3.1" -> "9.3.0") parts = version.split(".") if len(parts) >= 2: major_minor = f"{parts[0]}.{parts[1]}.0" if major_minor in self.VERSION_MAPPING: version = major_minor return self.VERSION_MAPPING.get(version, self.VERSION_MAPPING["latest"]) def format_version_for_help_url(self, version: str) -> str: """Convert version to help URL format. Takes a version string (e.g., "9.4.0", "latest", "auto") and returns the normalized version suitable for help.splunk.com URLs (e.g., "9.4"). """ norm_version = self.normalize_version(version) return norm_version async def fetch_doc_content(self, url: str) -> str: """Fetch and process documentation content.""" if not HAS_HTTPX: return f"""# Documentation Unavailable HTTP client not available. To enable documentation fetching, install httpx: ```bash pip install httpx ``` **Requested URL**: {url} **Time**: {datetime.now().isoformat()} """ try: # Headers to bypass browser detection on help.splunk.com headers = { "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36" } async with httpx.AsyncClient( timeout=30.0, headers=headers, follow_redirects=True ) as client: logger.debug(f"Fetching documentation from: {url}") response = await client.get(url) response.raise_for_status() # Process HTML to LLM-friendly format content = self.processor.process_html(response.text, url) logger.debug(f"Successfully processed documentation from {url}") return content except httpx.HTTPStatusError as e: if e.response.status_code == 404: return f"""# Documentation Not Found The requested Splunk documentation was not found at this URL. **URL**: {url} **Status**: 404 Not Found **Time**: {datetime.now().isoformat()} This may indicate: - The documentation has moved or been renamed - The Splunk version doesn't have this specific documentation - The topic name may be incorrect Please check the [Splunk Documentation](https://help.splunk.com) for the correct location. """ else: return f"""# Documentation Error Failed to fetch documentation due to HTTP error. **URL**: {url} **Status**: {e.response.status_code} **Error**: {str(e)} **Time**: {datetime.now().isoformat()} """ except Exception as e: logger.error(f"Error fetching documentation from {url}: {e}") return f"""# Documentation Error Failed to fetch documentation due to an error. **URL**: {url} **Error**: {str(e)} **Time**: {datetime.now().isoformat()} Please check your internet connection and try again. """ class SplunkCheatSheetResource(SplunkDocsResource): """Static Splunk cheat sheet resource from Splunk blog.""" METADATA = ResourceMetadata( uri="splunk-docs://cheat-sheet", name="splunk_cheat_sheet", description="Splunk SPL cheat sheet with commands, regex, and query examples", mime_type="text/markdown", category="reference", tags=["cheat-sheet", "spl", "reference", "commands", "regex"], ) def __init__( self, uri: str = None, name: str = None, description: str = None, mime_type: str = "text/markdown", ): # Use metadata defaults if not provided uri = uri or self.METADATA.uri name = name or self.METADATA.name description = description or self.METADATA.description super().__init__(uri, name, description, mime_type) async def get_content(self, ctx: Context) -> str: """Get Splunk cheat sheet content.""" async def fetch_cheat_sheet(): # Use the custom processor that returns the complete cheat sheet content url = "https://www.splunk.com/en_us/blog/learn/splunk-cheat-sheet-query-spl-regex-commands.html" # The processor will handle this URL specially and return comprehensive content content = self.processor.process_cheat_sheet_content("", url) return content return await _doc_cache.get_or_fetch("static", "cheat-sheet", "main", fetch_cheat_sheet) class TroubleshootingResource(SplunkDocsResource): """Version-aware Splunk troubleshooting documentation.""" METADATA = ResourceMetadata( uri="splunk-docs://{version}/troubleshooting/{topic}", name="troubleshooting_guide", description="Splunk troubleshooting documentation for various topics and versions", mime_type="text/markdown", category="troubleshooting", tags=["troubleshooting", "documentation", "diagnostics", "performance"], ) # Comprehensive troubleshooting topics mapping TROUBLESHOOTING_TOPICS = { # Log files and internal logging "splunk-logs": { "title": "What Splunk Logs about Itself", "description": "Understanding Splunk's internal logging and log files", "url_path": "splunk-enterprise-log-files/what-splunk-software-logs-about-itself", }, "metrics-log": { "title": "About metrics.log", "description": "Understanding Splunk's metrics.log file for performance monitoring", "url_path": "splunk-enterprise-log-files/about-metrics.log", }, "troubleshoot-inputs": { "title": "Troubleshooting Inputs with metrics.log", "description": "Using metrics.log to diagnose input-related issues", "url_path": "splunk-enterprise-log-files/troubleshoot-inputs-with-metrics.log", }, # Platform instrumentation "platform-instrumentation": { "title": "About Platform Instrumentation", "description": "Understanding Splunk Enterprise platform instrumentation", "url_path": "platform-instrumentation/about-splunk-enterprise-platform-instrumentation", }, "platform-instrumentation-logs": { "title": "What Platform Instrumentation Logs", "description": "Understanding what platform instrumentation logs in Splunk", "url_path": "platform-instrumentation/what-does-platform-instrumentation-log", }, "platform-instrumentation-searches": { "title": "Sample Platform Instrumentation Searches", "description": "Example searches for monitoring platform instrumentation", "url_path": "platform-instrumentation/sample-platform-instrumentation-searches", }, # Search and web problems "search-problems": { "title": "Splunk Web and Search Problems", "description": "Troubleshooting Splunk web interface and search issues", "url_path": "splunk-web-and-search-problems/i-cant-find-my-data", }, "authentication-timeouts": { "title": "Intermittent Authentication Timeouts on Search Peers", "description": "Resolving authentication timeout issues between search head and peers", "url_path": "splunk-web-and-search-problems/intermittent-authentication-timeouts-on-search-peers", }, # Data acquisition and indexing "indexing-performance": { "title": "Identify and Triage Indexing Performance Issues", "description": "Diagnosing and resolving indexing performance problems", "url_path": "data-acquisition-problems/identify-and-triage-indexing-performance-problems", }, "indexing-delay": { "title": "Event Indexing Delay", "description": "Understanding and resolving event indexing delays", "url_path": "data-acquisition-problems/event-indexing-delay", }, } def __init__(self, version: str, topic: str): self.version = version self.topic = topic if topic not in self.TROUBLESHOOTING_TOPICS: available_topics = ", ".join(self.TROUBLESHOOTING_TOPICS.keys()) raise ValueError( f"Unknown troubleshooting topic: {topic}. Available topics: {available_topics}" ) topic_info = self.TROUBLESHOOTING_TOPICS[topic] uri = f"splunk-docs://{version}/troubleshooting/{topic}" super().__init__( uri=uri, name=f"troubleshooting_{topic}_{version}", description=f"Splunk troubleshooting: {topic_info['description']} (version {version})", ) async def get_content(self, ctx: Context) -> str: """Get troubleshooting documentation for specific topic.""" async def fetch_troubleshooting_docs(): topic_info = self.TROUBLESHOOTING_TOPICS[self.topic] help_version = self.format_version_for_help_url(self.version) url = f"{self.SPLUNK_HELP_BASE}/en/splunk-enterprise/administer/troubleshoot/{help_version}/{topic_info['url_path']}" content = await self.fetch_doc_content(url) result = f"""# Splunk Troubleshooting: {topic_info["title"]} **Version**: Splunk {self.version} **Category**: Troubleshooting Guide **Topic**: {topic_info["description"]} **Source URL**: {url} {content} ## Troubleshooting Context This documentation is part of Splunk's comprehensive troubleshooting guide. It helps administrators and users: - Understand Splunk's internal operations - Diagnose performance and operational issues - Monitor system health and metrics - Resolve common problems ### Related Troubleshooting Topics """ # Add links to related troubleshooting topics for topic_key, topic_data in self.TROUBLESHOOTING_TOPICS.items(): if topic_key != self.topic: result += f"- [{topic_data['title']}](splunk-docs://{self.version}/troubleshooting/{topic_key})\n" result += f""" ### Additional Resources For more troubleshooting information, see: - [Splunk Documentation](splunk-docs://{self.version}/admin/monitoring) - [SPL Reference](splunk-docs://{self.version}/spl-reference) - [Splunk Cheat Sheet](splunk-docs://cheat-sheet) --- **Generated**: {datetime.now().isoformat()} """ return result return await _doc_cache.get_or_fetch( self.version, "troubleshooting", self.topic, fetch_troubleshooting_docs ) class SPLReferenceResource(SplunkDocsResource): """SPL (Search Processing Language) reference documentation.""" METADATA = ResourceMetadata( uri="splunk-docs://spl-reference", name="spl_reference", description="Splunk SPL command and function reference documentation", mime_type="text/markdown", category="reference", tags=["spl", "search", "commands", "reference"], ) def __init__( self, uri: str = None, name: str = None, description: str = None, mime_type: str = "text/markdown", ): # Use metadata defaults if not provided uri = uri or self.METADATA.uri name = name or self.METADATA.name description = description or self.METADATA.description super().__init__(uri, name, description, mime_type) async def get_content(self, ctx: Context) -> str: """Get SPL reference documentation content.""" # This is a template resource - actual content comes from parameterized URIs return """# SPL Reference Documentation This resource provides access to Splunk's Search Processing Language (SPL) documentation. ## Available Resources Use these URI patterns to access specific SPL documentation: - `splunk-docs://{version}/spl-reference/{command}` - Specific SPL command documentation - `splunk-docs://latest/spl-reference/search` - Search command documentation - `splunk-docs://latest/spl-reference/stats` - Stats command documentation - `splunk-docs://latest/spl-reference/eval` - Eval command documentation ## Examples - `splunk-docs://9.3.0/spl-reference/chart` - Chart command for Splunk 9.3.0 - `splunk-docs://latest/spl-reference/timechart` - Timechart command (latest version) Replace `{version}` with a specific Splunk version (e.g., "9.3.0") or use "latest" for the current version. Replace `{command}` with the SPL command name you want to learn about. """ class SPLCommandResource(SplunkDocsResource): """Specific SPL command documentation resource.""" METADATA = ResourceMetadata( uri="splunk-docs://{version}/spl-reference/{command}", name="spl_command_reference", description="Splunk SPL command documentation for specific commands and versions", mime_type="text/markdown", category="reference", tags=["spl", "commands", "reference", "search"], ) def __init__(self, version: str, command: str): self.version = version self.command = command uri = f"splunk-docs://{version}/spl-reference/{command}" super().__init__( uri=uri, name=f"spl_command_{command}_{version}", description=f"SPL {command} command documentation for Splunk {version}", ) async def get_content(self, ctx: Context) -> str: """Get documentation for specific SPL command.""" async def fetch_command_docs(): norm_version = self.normalize_version(self.version) # help.splunk.com uses lowercase command names and different URL structure command_lower = self.command.lower() url = f"{self.SPLUNK_HELP_BASE}/en/splunk-enterprise/search/spl-search-reference/{norm_version}/search-commands/{command_lower}" content = await self.fetch_doc_content(url) # Add SPL-specific context return f"""# SPL Command: {self.command} **Version**: Splunk {self.version} **Category**: Search Processing Language Reference {content} ## Usage Context The `{self.command}` command is part of Splunk's Search Processing Language (SPL). It can be used in search queries and combined with other SPL commands using the pipe (|) operator. ### Common Usage Patterns ```spl index=main | {self.command} ... ``` For more SPL commands, see the complete [SPL Reference](splunk-docs://{self.version}/spl-reference). """ return await _doc_cache.get_or_fetch( self.version, "spl-reference", self.command, fetch_command_docs ) class AdminGuideResource(SplunkDocsResource): """Splunk administration documentation.""" METADATA = ResourceMetadata( uri="splunk-docs://{version}/admin/{topic}", name="admin_guide", description="Splunk administration documentation for various topics and versions", mime_type="text/markdown", category="administration", tags=["administration", "configuration", "management", "deployment"], ) def __init__(self, version: str, topic: str): self.version = version self.topic = topic uri = f"splunk-docs://{version}/admin/{topic}" super().__init__( uri=uri, name=f"admin_{topic}_{version}", description=f"Splunk administration guide: {topic} (version {version})", ) async def get_content(self, ctx: Context) -> str: """Get administration documentation for specific topic.""" async def fetch_admin_docs(): # help.splunk.com uses hyphenated topic names and different URL structure topic_url = self.topic.replace("_", "-").lower() url = f"{self.SPLUNK_HELP_BASE}/en/splunk-enterprise/administer/{topic_url}" content = await self.fetch_doc_content(url) return f"""# Splunk Administration: {self.topic} **Version**: Splunk {self.version} **Category**: Administration Guide {content} ## Administration Context This documentation covers administrative aspects of Splunk deployment and configuration. For related administration topics, see the complete [Admin Guide](splunk-docs://{self.version}/admin). """ return await _doc_cache.get_or_fetch(self.version, "admin", self.topic, fetch_admin_docs) class SplunkSpecReferenceResource(SplunkDocsResource): """Splunk configuration specification file reference documentation.""" METADATA = ResourceMetadata( uri="splunk-spec://{config}", name="splunk_spec_reference", description="Splunk configuration specification reference (auto-detects version)", mime_type="text/markdown", category="reference", tags=["spec", "configuration", "reference", "admin"], ) def __init__(self, config: str): self.config = config # Version will be detected dynamically in get_content() self._cached_version = None uri = f"splunk-spec://{config}" # Normalize config name for display display_config = self._normalize_config_name(config) super().__init__( uri=uri, name=f"spec_{config.replace('.', '_')}", description=f"Splunk configuration spec for {display_config} (auto-detected version)", ) def _parse_version_components(self, version: str) -> tuple[str, str]: """Parse version into minor (X.Y) and full (X.Y.Z) components. Args: version: Version string like "10.0", "9.4.0", "latest", "auto" Returns: Tuple of (minor, full) version strings """ # Handle auto-detection if version == "auto": version = "latest" # Normalize using existing method to get minor version minor = self.normalize_version(version) # Now construct full version # If input was already X.Y.Z, try to preserve it parts = version.split(".") if len(parts) >= 3: # Has patch version already full = f"{parts[0]}.{parts[1]}.{parts[2]}" elif len(parts) == 2: # Only has major.minor, add .0 for patch full = f"{parts[0]}.{parts[1]}.0" else: # Single component or "latest" - use minor + .0 full = f"{minor}.0" return minor, full def _normalize_config_name(self, config: str) -> str: """Normalize configuration file name to ensure .conf extension. Args: config: Config file name (with or without .conf) Returns: Config name with .conf extension """ # Always use .conf (not .conf.spec) if config.endswith(".conf.spec"): # Strip .spec suffix if present return config[:-5] # Remove ".spec" elif config.endswith(".conf"): return config else: return f"{config}.conf" async def get_content(self, ctx: Context) -> str: """Get configuration specification documentation for specific file.""" # Detect version once before caching version = await self.get_splunk_version(ctx) logger.info(f"Auto-detected Splunk version: {version}") async def fetch_spec_docs(): # Version already detected above minor, full = self._parse_version_components(version) config = self._normalize_config_name(self.config) # Primary URL pattern (most common) primary_url = f"{self.SPLUNK_HELP_BASE}/en/splunk-enterprise/administer/admin-manual/{minor}/configuration-file-reference/{full}-configuration-file-reference/{config}" # Fallback URL pattern (alternative IA structure) fallback_url = f"{self.SPLUNK_HELP_BASE}/en/data-management/splunk-enterprise-admin-manual/{minor}/configuration-file-reference/{full}-configuration-file-reference/{config}" # Try primary URL first content = await self.fetch_doc_content(primary_url) used_url = primary_url # If primary fails with 404, try fallback if content.startswith("# Documentation Not Found"): logger.debug("Primary URL failed for %s, trying fallback: %s", config, fallback_url) fallback_content = await self.fetch_doc_content(fallback_url) # Use fallback if it succeeds if not fallback_content.startswith("# Documentation Not Found"): content = fallback_content used_url = fallback_url else: # Both failed - provide helpful error return f"""# Configuration Spec Not Found The requested Splunk configuration specification was not found. **Config File**: {config} **Version**: {version} (minor: {minor}, full: {full}) **Time**: {datetime.now().isoformat()} **Attempted URLs**: 1. Primary: {primary_url} 2. Fallback: {fallback_url} This may indicate: - The configuration file name is incorrect or has a typo - This Splunk version doesn't document this configuration file - The documentation structure has changed **Common configuration files**: - alert_actions.conf - limits.conf - indexes.conf - inputs.conf - outputs.conf - props.conf - transforms.conf - server.conf - web.conf - authentication.conf Please verify the configuration file name and version, or check the [Splunk Documentation](https://help.splunk.com) directly. """ # Wrap successful content with metadata result = f"""# Splunk Configuration Spec: {config} **Version**: Splunk {version} **Category**: Configuration File Reference **Source URL**: {used_url} {content} ## Configuration Context This documentation describes the configuration specification for `{config}`. Configuration files in Splunk Enterprise: - Control behavior and features of the Splunk platform - Use INI-style stanza format with key-value pairs - Follow precedence rules (system โ†’ local โ†’ app โ†’ user) - Can be validated using `btool check` ### Related Resources - [Configuration File Precedence](splunk-docs://{version}/admin/configuration-file-precedence) - [List of Configuration Files](splunk-docs://{version}/admin/list-of-configuration-files) - [Admin Guide](splunk-docs://{version}/admin) --- **Generated**: {datetime.now().isoformat()} """ return result return await _doc_cache.get_or_fetch( version, "spec-reference", self.config, fetch_spec_docs ) class DocumentationDiscoveryResource(SplunkDocsResource): """Resource for discovering available Splunk documentation.""" METADATA = ResourceMetadata( uri="splunk-docs://discovery", name="documentation_discovery", description="Discover available Splunk documentation resources", mime_type="text/markdown", category="discovery", tags=["discovery", "documentation", "reference"], ) def __init__( self, uri: str = None, name: str = None, description: str = None, mime_type: str = "text/markdown", ): # Use metadata defaults if not provided uri = uri or self.METADATA.uri name = name or self.METADATA.name description = description or self.METADATA.description super().__init__(uri, name, description, mime_type) async def get_content(self, ctx: Context) -> str: """Discover available Splunk documentation resources.""" # Try to get actual Splunk version try: detected_version = await self.get_splunk_version(ctx) except Exception: detected_version = "latest" # Common SPL commands for quick reference common_spl_commands = [ "search", "stats", "eval", "chart", "timechart", "table", "sort", "where", "join", "append", "lookup", "rex", "fieldsfor", "top", "rare", "transaction", "streamstats", "eventstats", "bucket", "dedup", "head", "tail", "regex", "replace", "convert", "makemv", "mvexpand", "spath", "xmlkv", "kvform", ] # Common admin topics admin_topics = [ "indexes", "authentication", "deployment", "apps", "users", "roles", "monitoring", "performance", "clustering", "distributed-search", "forwarders", "inputs", "outputs", "licensing", "security", ] # All available troubleshooting topics troubleshooting_topics = list(TroubleshootingResource.TROUBLESHOOTING_TOPICS.keys()) content = f"""# Splunk Documentation Discovery **Detected Splunk Version**: {detected_version} **Discovery Time**: {datetime.now().isoformat()} This resource helps you discover and access Splunk documentation through the MCP server. ## Static Resources ### ๐Ÿ“‹ Splunk Cheat Sheet - **URI**: `splunk-docs://cheat-sheet` - **Description**: Complete SPL command reference, regex patterns, and quick examples - **Source**: Official Splunk blog ## Dynamic Resources ### ๐Ÿ” SPL Command Reference Access documentation for specific SPL commands: **Pattern**: `splunk-docs://{{version}}/spl-reference/{{command}}` **Common Commands**: """ # Add SPL commands in columns for i, cmd in enumerate(common_spl_commands): if i % 4 == 0: content += "\n" content += f"- [`{cmd}`](splunk-docs://{detected_version}/spl-reference/{cmd}) " content += """ ### ๐Ÿ› ๏ธ Troubleshooting Documentation Access version-specific troubleshooting guides: **Pattern**: `splunk-docs://{version}/troubleshooting/{topic}` **Available Topics**: """ # Add troubleshooting topics with descriptions for topic in troubleshooting_topics: topic_info = TroubleshootingResource.TROUBLESHOOTING_TOPICS[topic] content += f"- [`{topic}`](splunk-docs://{detected_version}/troubleshooting/{topic}) - {topic_info['description']}\n" content += """ ### โš™๏ธ Administration Guides Access administration documentation: **Pattern**: `splunk-docs://{version}/admin/{topic}` **Common Topics**: """ # Add admin topics in columns for i, topic in enumerate(admin_topics): if i % 3 == 0: content += "\n" content += f"- [`{topic}`](splunk-docs://{detected_version}/admin/{topic}) " # Common configuration files for spec reference common_config_files = [ "alert_actions.conf", "limits.conf", "indexes.conf", "inputs.conf", "outputs.conf", "props.conf", "transforms.conf", "server.conf", "web.conf", "authentication.conf", "authorize.conf", "savedsearches.conf", ] content += """ ### ๐Ÿงฉ Configuration Spec Reference Access configuration file specifications: **Pattern**: `splunk-spec://{config}` **๐Ÿ’ก Pro Tip**: Version is automatically detected from your connected Splunk instance! **Common Configuration Files**: """ # Add config files in columns for i, config in enumerate(common_config_files): if i % 3 == 0: content += "\n" content += f"- [`{config}`](splunk-spec://{config}) " content += f""" ## Version Support **Supported Versions**: 9.1.0, 9.2.1, 9.3.0, 9.4.0, 10.0.0, latest **Default Version**: latest (currently 10.0.0) **Auto-Detection**: Version automatically detected from your connected Splunk instance ### Examples ``` # Static resources (no version needed) splunk-docs://cheat-sheet # Dynamic resources with version splunk-docs://9.4/troubleshooting/metrics-log splunk-docs://latest/spl-reference/stats splunk-docs://9.3.0/admin/indexes # Configuration spec references (version auto-detected) splunk-spec://alert_actions.conf splunk-spec://limits.conf splunk-spec://inputs.conf splunk-spec://props.conf splunk-spec://transforms.conf # Auto-detect version for other resources (uses detected: {detected_version}) splunk-docs://auto/troubleshooting/platform-instrumentation ``` ## Quick Access Links ### Most Useful Resources - [๐Ÿ“‹ Splunk Cheat Sheet](splunk-docs://cheat-sheet) - Essential SPL reference - [๐Ÿ”ง Metrics Log Troubleshooting](splunk-docs://{detected_version}/troubleshooting/metrics-log) - Performance monitoring - [๐Ÿ“Š Platform Instrumentation](splunk-docs://{detected_version}/troubleshooting/platform-instrumentation) - System monitoring - [๐Ÿ” Search Problems](splunk-docs://{detected_version}/troubleshooting/search-problems) - Search troubleshooting - [๐Ÿ“ˆ Indexing Performance](splunk-docs://{detected_version}/troubleshooting/indexing-performance) - Index optimization ### For Administrators - [๐Ÿ‘ฅ User Management](splunk-docs://{detected_version}/admin/users) - User administration - [๐Ÿ—๏ธ Index Management](splunk-docs://{detected_version}/admin/indexes) - Index configuration - [๐Ÿ” Authentication](splunk-docs://{detected_version}/admin/authentication) - Security setup - [๐Ÿ“ก Distributed Search](splunk-docs://{detected_version}/admin/distributed-search) - Multi-instance setup ### Configuration References - [๐Ÿ”ง Alert Actions Spec](splunk-spec://{detected_version}/alert_actions.conf) - Alert configuration - [โšก Limits Spec](splunk-spec://{detected_version}/limits.conf) - Performance tuning - [๐Ÿ“Š Indexes Spec](splunk-spec://{detected_version}/indexes.conf) - Index configuration - [๐Ÿ“ฅ Inputs Spec](splunk-spec://{detected_version}/inputs.conf) - Data input configuration --- **Note**: All documentation is cached for 24 hours for optimal performance. URLs are automatically validated and content is processed for LLM consumption. """ return content # Registry and factory functions def register_all_resources(): """Register all documentation resources with the resource registry.""" try: # Register static resources that have METADATA defined resource_registry.register(SplunkCheatSheetResource, SplunkCheatSheetResource.METADATA) resource_registry.register( DocumentationDiscoveryResource, DocumentationDiscoveryResource.METADATA ) resource_registry.register(SPLReferenceResource, SPLReferenceResource.METADATA) # Register dynamic/parameterized resources using their class METADATA resource_registry.register(TroubleshootingResource, TroubleshootingResource.METADATA) resource_registry.register(SPLCommandResource, SPLCommandResource.METADATA) resource_registry.register(AdminGuideResource, AdminGuideResource.METADATA) resource_registry.register( SplunkSpecReferenceResource, SplunkSpecReferenceResource.METADATA ) logger.info( "Successfully registered 7 Splunk documentation resources (3 static, 4 dynamic templates)" ) except Exception as e: logger.error(f"Failed to register documentation resources: {e}") def create_spl_command_resource(version: str, command: str) -> SPLCommandResource: """Factory function to create SPL command documentation resources.""" return SPLCommandResource(version, command) def create_admin_guide_resource(version: str, topic: str) -> AdminGuideResource: """Factory function to create admin guide documentation resources.""" return AdminGuideResource(version, topic) def create_troubleshooting_resource(version: str, topic: str) -> TroubleshootingResource: """Factory function to create troubleshooting documentation resources.""" return TroubleshootingResource(version, topic) def create_spec_reference_resource(config: str) -> SplunkSpecReferenceResource: """Factory function to create configuration spec reference resources. Args: config: Configuration file name (e.g., "alert_actions.conf", "limits.conf") Returns: SplunkSpecReferenceResource instance (version auto-detected from Splunk instance) """ return SplunkSpecReferenceResource(config) # Auto-register resources when module is imported register_all_resources()

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/deslicer/mcp-for-splunk'

If you have feedback or need assistance with the MCP directory API, please join our Discord server