search-opentofu-registry
Search the OpenTofu Registry to find providers, modules, resources, and data sources for infrastructure configuration. Enter simple terms like 'aws' or 'kubernetes' to locate components.
Instructions
Search the OpenTofu Registry to find providers, modules, resources, and data sources. Use simple terms without prefixes like 'terraform-provider-' or 'terraform-module-'.
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| query | Yes | Search query for finding OpenTofu components (e.g., 'aws', 'kubernetes', 'database', 's3') | |
| type | No | Type of registry items to search for | all |
Implementation Reference
- src/servers/registry/index.ts:73-84 (handler)The inline async handler function for the 'search-opentofu-registry' tool. It invokes the RegistryClient.search method, handles empty results and errors, and formats the output using textResult and renderSearchResults.async (params) => { try { const results = await client.search(params.query, params.type); if (results.length === 0) { return textResult(`No results found for "${params.query}" in the OpenTofu Registry.`); } return textResult(`Found ${results.length} results for "${params.query}" in the OpenTofu Registry:\n\n${results.map((r) => renderSearchResults(r)).join("\n\n")}`); } catch (error: unknown) { const errorMessage = error instanceof Error ? error.message : "Unknown error"; return textResult(`Error searching the OpenTofu Registry: ${errorMessage}`); } },
- src/servers/registry/index.ts:7-10 (schema)Zod schema defining the input parameters for the search tool: query (string, min 2 chars) and type (enum with default 'all').const searchSchema = { query: z.string().min(2).describe("Search query for finding OpenTofu components (e.g., 'aws', 'kubernetes', 'database', 's3')"), type: z.enum(["provider", "module", "resource", "data-source", "all"]).default("all").describe("Type of registry items to search for"), };
- src/servers/registry/index.ts:70-85 (registration)MCP server.tool registration call that registers the 'search-opentofu-registry' tool with its name, description, schema, and handler function."search-opentofu-registry", "Search the OpenTofu Registry to find providers, modules, resources, and data sources. Use simple terms without prefixes like 'terraform-provider-' or 'terraform-module-'.", searchSchema, async (params) => { try { const results = await client.search(params.query, params.type); if (results.length === 0) { return textResult(`No results found for "${params.query}" in the OpenTofu Registry.`); } return textResult(`Found ${results.length} results for "${params.query}" in the OpenTofu Registry:\n\n${results.map((r) => renderSearchResults(r)).join("\n\n")}`); } catch (error: unknown) { const errorMessage = error instanceof Error ? error.message : "Unknown error"; return textResult(`Error searching the OpenTofu Registry: ${errorMessage}`); } }, );
- src/registry/index.ts:77-86 (helper)Core search logic in RegistryClient class: performs API fetch to /registry/docs/search with query 'q', optionally filters by type.async search(query: string, type?: string): Promise<apiDefinition["SearchResultItem"][]> { const params: Record<string, string> = { q: query }; const response = await this.fetchFromApi<apiDefinition["SearchResultItem"][]>("/registry/docs/search", params); let results = response; if (type && type !== "all") { results = response.filter((item) => item.type.toLowerCase() === type.toLowerCase()); } return results; }
- Utility function to render a formatted string for each search result item, including type-specific details and instructions for further tools.export function renderSearchResults(r: apiDefinition["SearchResultItem"]): string { let result = `- ${r.title} ${r.description.trim()} (${r.type})`; result += ` (latest version: ${r.version})`; switch (r.type) { case "provider": result += `\n Provider: ${r.link_variables.namespace}/${r.link_variables.name}`; result += `\n Provider Details: Use 'get-provider-details' with namespace="${r.link_variables.namespace}" and name="${r.link_variables.name}"`; break; case "module": result += `\n Module: ${r.link_variables.namespace}/${r.link_variables.name} (${r.link_variables.target})`; result += `\n Module Details: Use 'get-module-details' with namespace="${r.link_variables.namespace}", name="${r.link_variables.name}", target="${r.link_variables.target}"`; break; case "provider/resource": { const versionParam = r.version ? `, version="${r.version}"` : ""; result += `\n Resource: ${r.link_variables.namespace}/${r.link_variables.name} (${r.link_variables.id})`; result += `\n Full identifier: ${r.link_variables.name}_${r.link_variables.id}`; result += `\n Resource Docs: Use 'get-resource-docs' with namespace="${r.link_variables.namespace}", name="${r.link_variables.name}", resource="${r.link_variables.id}"${versionParam}`; result += `\n Provider Details: Use 'get-provider-details' with namespace="${r.link_variables.namespace}" and name="${r.link_variables.name}"`; break; } case "provider/data-source": { const versionParam = r.version ? `, version="${r.version}"` : ""; result += `\n Data Source: ${r.link_variables.namespace}/${r.link_variables.name} (${r.link_variables.id})`; result += `\n Full identifier: ${r.link_variables.name}_${r.link_variables.id}`; result += `\n Data Source Docs: Use 'get-datasource-docs' with namespace="${r.link_variables.namespace}", name="${r.link_variables.name}", dataSource="${r.link_variables.id}"${versionParam}`; result += `\n Provider Details: Use 'get-provider-details' with namespace="${r.link_variables.namespace}" and name="${r.link_variables.name}"`; break; } default: result += `\n Unknown type: ${r.type}`; } return result; }