#
tokens: 48882/50000 49/92 files (page 1/4)
lines: on (toggle) GitHub
raw markdown copy reset
This is page 1 of 4. Use http://codebase.md/severity1/terraform-cloud-mcp?lines=true&page={x} to view the full context.

# Directory Structure

```
├── .gitignore
├── .python-version
├── CLAUDE.md
├── docs
│   ├── API_REFERENCES.md
│   ├── CLAUDE.md
│   ├── CONTRIBUTING.md
│   ├── conversations
│   │   ├── account.md
│   │   ├── apply-management-conversation.md
│   │   ├── assessment-results-conversation.md
│   │   ├── cost-estimate-conversation.md
│   │   ├── organization-entitlements-conversation.md
│   │   ├── organizations-management-conversation.md
│   │   ├── plan-management-conversation.md
│   │   ├── project-management-conversation.md
│   │   ├── runs-management-conversation.md
│   │   ├── state_management.md
│   │   ├── variables-conversation.md
│   │   └── workspace-management-conversation.md
│   ├── DEVELOPMENT.md
│   ├── FILTERING_SYSTEM.md
│   ├── models
│   │   ├── account.md
│   │   ├── apply.md
│   │   ├── assessment_result.md
│   │   ├── cost_estimate.md
│   │   ├── organization.md
│   │   ├── plan.md
│   │   ├── project.md
│   │   ├── run.md
│   │   ├── state_version_outputs.md
│   │   ├── state_versions.md
│   │   ├── variables.md
│   │   └── workspace.md
│   ├── README.md
│   └── tools
│       ├── account.md
│       ├── apply.md
│       ├── assessment_results.md
│       ├── cost_estimate.md
│       ├── organization.md
│       ├── plan.md
│       ├── project.md
│       ├── run.md
│       ├── state_version_outputs.md
│       ├── state_versions.md
│       ├── variables.md
│       └── workspace.md
├── env.example
├── LICENSE
├── mypy.ini
├── pyproject.toml
├── README.md
├── terraform_cloud_mcp
│   ├── __init__.py
│   ├── api
│   │   ├── __init__.py
│   │   ├── CLAUDE.md
│   │   └── client.py
│   ├── configs
│   │   ├── __init__.py
│   │   ├── CLAUDE.md
│   │   └── filter_configs.py
│   ├── models
│   │   ├── __init__.py
│   │   ├── account.py
│   │   ├── applies.py
│   │   ├── assessment_results.py
│   │   ├── base.py
│   │   ├── CLAUDE.md
│   │   ├── cost_estimates.py
│   │   ├── filters.py
│   │   ├── organizations.py
│   │   ├── plans.py
│   │   ├── projects.py
│   │   ├── runs.py
│   │   ├── state_version_outputs.py
│   │   ├── state_versions.py
│   │   ├── variables.py
│   │   └── workspaces.py
│   ├── server.py
│   ├── tools
│   │   ├── __init__.py
│   │   ├── account.py
│   │   ├── applies.py
│   │   ├── assessment_results.py
│   │   ├── CLAUDE.md
│   │   ├── cost_estimates.py
│   │   ├── organizations.py
│   │   ├── plans.py
│   │   ├── projects.py
│   │   ├── runs.py
│   │   ├── state_version_outputs.py
│   │   ├── state_versions.py
│   │   ├── variables.py
│   │   └── workspaces.py
│   └── utils
│       ├── __init__.py
│       ├── CLAUDE.md
│       ├── decorators.py
│       ├── env.py
│       ├── filters.py
│       ├── payload.py
│       └── request.py
└── uv.lock
```

# Files

--------------------------------------------------------------------------------
/.python-version:
--------------------------------------------------------------------------------

```
1 | 3.12
2 | 
```

--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------

```
  1 | # Byte-compiled / optimized / DLL files
  2 | __pycache__/
  3 | *.py[cod]
  4 | *$py.class
  5 | 
  6 | # C extensions
  7 | *.so
  8 | 
  9 | # Distribution / packaging
 10 | .Python
 11 | build/
 12 | develop-eggs/
 13 | dist/
 14 | downloads/
 15 | eggs/
 16 | .eggs/
 17 | lib/
 18 | lib64/
 19 | parts/
 20 | sdist/
 21 | var/
 22 | wheels/
 23 | share/python-wheels/
 24 | *.egg-info/
 25 | .installed.cfg
 26 | *.egg
 27 | MANIFEST
 28 | 
 29 | # PyInstaller
 30 | #  Usually these files are written by a python script from a template
 31 | #  before PyInstaller builds the exe, so as to inject date/other infos into it.
 32 | *.manifest
 33 | *.spec
 34 | 
 35 | # Installer logs
 36 | pip-log.txt
 37 | pip-delete-this-directory.txt
 38 | 
 39 | # Unit test / coverage reports
 40 | htmlcov/
 41 | .tox/
 42 | .nox/
 43 | .coverage
 44 | .coverage.*
 45 | .cache
 46 | nosetests.xml
 47 | coverage.xml
 48 | *.cover
 49 | *.py,cover
 50 | .hypothesis/
 51 | .pytest_cache/
 52 | cover/
 53 | 
 54 | # Translations
 55 | *.mo
 56 | *.pot
 57 | 
 58 | # Django stuff:
 59 | *.log
 60 | local_settings.py
 61 | db.sqlite3
 62 | db.sqlite3-journal
 63 | 
 64 | # Flask stuff:
 65 | instance/
 66 | .webassets-cache
 67 | 
 68 | # Scrapy stuff:
 69 | .scrapy
 70 | 
 71 | # Sphinx documentation
 72 | docs/_build/
 73 | 
 74 | # PyBuilder
 75 | .pybuilder/
 76 | target/
 77 | 
 78 | # Jupyter Notebook
 79 | .ipynb_checkpoints
 80 | 
 81 | # IPython
 82 | profile_default/
 83 | ipython_config.py
 84 | 
 85 | # pyenv
 86 | #   For a library or package, you might want to ignore these files since the code is
 87 | #   intended to run in multiple environments; otherwise, check them in:
 88 | # .python-version
 89 | 
 90 | # pipenv
 91 | #   According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
 92 | #   However, in case of collaboration, if having platform-specific dependencies or dependencies
 93 | #   having no cross-platform support, pipenv may install dependencies that don't work, or not
 94 | #   install all needed dependencies.
 95 | #Pipfile.lock
 96 | 
 97 | # UV
 98 | #   Similar to Pipfile.lock, it is generally recommended to include uv.lock in version control.
 99 | #   This is especially recommended for binary packages to ensure reproducibility, and is more
100 | #   commonly ignored for libraries.
101 | #uv.lock
102 | 
103 | # poetry
104 | #   Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
105 | #   This is especially recommended for binary packages to ensure reproducibility, and is more
106 | #   commonly ignored for libraries.
107 | #   https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
108 | #poetry.lock
109 | 
110 | # pdm
111 | #   Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control.
112 | #pdm.lock
113 | #   pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it
114 | #   in version control.
115 | #   https://pdm.fming.dev/latest/usage/project/#working-with-version-control
116 | .pdm.toml
117 | .pdm-python
118 | .pdm-build/
119 | 
120 | # PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm
121 | __pypackages__/
122 | 
123 | # Celery stuff
124 | celerybeat-schedule
125 | celerybeat.pid
126 | 
127 | # Process IDs
128 | *.pid
129 | 
130 | # SageMath parsed files
131 | *.sage.py
132 | 
133 | # Environments
134 | .env
135 | .venv
136 | env/
137 | venv/
138 | ENV/
139 | env.bak/
140 | venv.bak/
141 | 
142 | # Spyder project settings
143 | .spyderproject
144 | .spyproject
145 | 
146 | # Rope project settings
147 | .ropeproject
148 | 
149 | # mkdocs documentation
150 | /site
151 | 
152 | # mypy
153 | .mypy_cache/
154 | .dmypy.json
155 | dmypy.json
156 | 
157 | # Pyre type checker
158 | .pyre/
159 | 
160 | # pytype static type analyzer
161 | .pytype/
162 | 
163 | # Cython debug symbols
164 | cython_debug/
165 | 
166 | # PyCharm
167 | #  JetBrains specific template is maintained in a separate JetBrains.gitignore that can
168 | #  be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore
169 | #  and can be added to the global gitignore or merged into this file.  For a more nuclear
170 | #  option (not recommended) you can uncomment the following to ignore the entire idea folder.
171 | #.idea/
172 | 
173 | # Ruff stuff:
174 | .ruff_cache/
175 | 
176 | # PyPI configuration file
177 | .pypirc
178 | 
179 | # Others
180 | examples/
181 | ISSUES.md
182 | TASKS.md
183 | 
```

--------------------------------------------------------------------------------
/docs/README.md:
--------------------------------------------------------------------------------

```markdown
 1 | # Terraform Cloud MCP Documentation
 2 | 
 3 | This directory contains supplementary documentation for the Terraform Cloud MCP project.
 4 | 
 5 | ## Structure
 6 | 
 7 | ### Core Documentation
 8 | - `FILTERING_SYSTEM.md` - Audit-safe response filtering system (5-15% token reduction, 100% audit compliance)
 9 | - `DEVELOPMENT.md` - Comprehensive development guidelines and coding standards
10 | - `API_REFERENCES.md` - Terraform Cloud API documentation links with implementation status
11 | - `CONTRIBUTING.md` - Guidelines for contributing to the project
12 | 
13 | ### Model Documentation
14 | The `models/` directory contains documentation for each model type:
15 | - `account.md` - Account model documentation
16 | - `apply.md` - Apply model documentation
17 | - `assessment_result.md` - Assessment result model documentation
18 | - `cost_estimate.md` - Cost estimate model documentation
19 | - `organization.md` - Organization model documentation  
20 | - `plan.md` - Plan model documentation
21 | - `project.md` - Project model documentation
22 | - `run.md` - Run model documentation
23 | - `state_versions.md` - State version model documentation
24 | - `state_version_outputs.md` - State version outputs model documentation
25 | - `variables.md` - Variables and variable sets model documentation
26 | - `workspace.md` - Workspace model documentation
27 | 
28 | ### Tool Documentation
29 | The `tools/` directory contains reference documentation for each tool:
30 | - `account.md` - Account tool reference documentation
31 | - `apply.md` - Apply management tool reference documentation
32 | - `assessment_results.md` - Assessment results tool reference documentation
33 | - `cost_estimate.md` - Cost estimate tools reference documentation
34 | - `organization.md` - Organization tools reference documentation
35 | - `plan.md` - Plan management tool reference documentation
36 | - `project.md` - Project management tool reference documentation
37 | - `run.md` - Run tools reference documentation
38 | - `state_versions.md` - State version management tool reference documentation
39 | - `state_version_outputs.md` - State version outputs tool reference documentation
40 | - `variables.md` - Variables and variable sets tool reference documentation
41 | - `workspace.md` - Workspace tools reference documentation
42 | 
43 | ### Conversation Examples
44 | The `conversations/` directory contains example conversations and usage scenarios:
45 | - `account.md` - Account management conversation examples
46 | - `apply-management-conversation.md` - Apply management conversation examples
47 | - `assessment-results-conversation.md` - Assessment results conversation examples
48 | - `cost-estimate-conversation.md` - Cost estimation conversation examples
49 | - `organization-entitlements-conversation.md` - Organization entitlements conversation examples
50 | - `organizations-management-conversation.md` - Organization management conversation examples
51 | - `plan-management-conversation.md` - Plan management conversation examples
52 | - `project-management-conversation.md` - Project management conversation examples
53 | - `runs-management-conversation.md` - Run management conversation examples
54 | - `state_management.md` - State management conversation examples
55 | - `variables-conversation.md` - Variables management conversation examples
56 | - `workspace-management-conversation.md` - Workspace management conversation examples
57 | 
58 | ## Documentation Philosophy
59 | 1. Code docstrings contain essential information about purpose, fields, parameters, and return values
60 | 2. Tool documentation provides context, API references, and usage guidance
61 | 3. Model examples illustrate how to work with data structures
62 | 4. Development standards and patterns are consolidated in DEVELOPMENT.md
63 | 5. Conversation examples demonstrate practical application scenarios
64 | 6. This structure keeps the codebase clean while maintaining comprehensive documentation
```

--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------

```markdown
  1 | [![MseeP.ai Security Assessment Badge](https://mseep.net/mseep-audited.png)](https://mseep.ai/app/severity1-terraform-cloud-mcp)
  2 | 
  3 | # Terraform Cloud MCP Server
  4 | 
  5 | A Model Context Protocol (MCP) server that integrates AI assistants with the Terraform Cloud API, allowing you to manage your infrastructure through natural conversation. Built with Pydantic models and structured around domain-specific modules, this server is compatible with any MCP-supporting platform including Claude, Claude Code CLI, Claude Desktop, Cursor, Copilot Studio, and others.
  6 | 
  7 | ![Version](https://img.shields.io/badge/version-0.8.17-blue)
  8 | ![Python](https://img.shields.io/badge/python-3.12+-green)
  9 | ![Type Checking](https://img.shields.io/badge/type_checking-mypy-brightgreen)
 10 | ![Code Quality](https://img.shields.io/badge/code_quality-100%25-success)
 11 | 
 12 | ---
 13 | 
 14 | ## Features
 15 | 
 16 | - **Account Management**: Get account details for authenticated users or service accounts.
 17 | - **Workspace Management**: Create, read, update, lock/unlock workspaces, and optionally delete workspaces (with safety controls).
 18 | - **Project Management**: Create, list, update projects, and optionally delete projects; manage project tag bindings and move workspaces between projects.
 19 | - **Run Management**: Create runs, list runs, get run details, apply/discard/cancel runs.
 20 | - **Plan Management**: Retrieve plan details and JSON execution output with advanced HTTP redirect handling.
 21 | - **Apply Management**: Get apply details and recover from failed state uploads.
 22 | - **Organization Management**: List, create, update organizations, view organization entitlements, and optionally delete organizations (with safety controls).
 23 | - **Cost Estimation**: Retrieve detailed cost estimates for infrastructure changes including proposed monthly costs, prior costs, resource counts, and usage projections.
 24 | - **Assessment Results**: Retrieve health assessment details, JSON output, schema files, and logs from Terraform Cloud health assessments.
 25 | - **State Version Management**: List, retrieve, create, and download state versions; get current state for workspaces.
 26 | - **State Version Outputs**: List and retrieve specific outputs from state versions including values and sensitivity information.
 27 | - **Variables Management**: Complete workspace variable and variable set management including creation, updates, assignments, and optionally deletion (with safety controls).
 28 | 
 29 | ### Performance Features
 30 | 
 31 | - **Audit-Safe Response Filtering**: Conservative token optimization (5-15% reduction) with 100% audit compliance - preserves all user accountability, security configuration, and change tracking data for comprehensive compliance scenarios.
 32 | 
 33 | ### Safety Features
 34 | 
 35 | - **Destructive Operation Controls**: Delete operations are disabled by default and require explicit enablement via environment variable
 36 | - **Destructive Hints**: MCP clients receive proper destructive operation warnings for potentially dangerous tools
 37 | - **Environment-Based Safety**: Production and development environments can have different safety configurations
 38 | 
 39 | ---
 40 | 
 41 | ## Quick Start
 42 | 
 43 | ### Prerequisites
 44 | 
 45 | - Python 3.12+
 46 | - MCP (includes FastMCP and development tools)
 47 | - `uv` package manager (recommended) or `pip`
 48 | - Terraform Cloud API token
 49 | 
 50 | ### Environment Variables
 51 | 
 52 | - `TFC_TOKEN` - Terraform Cloud API token (required)
 53 | - `TFC_ADDRESS` - Terraform Cloud/Enterprise address (optional, defaults to https://app.terraform.io)
 54 | - `ENABLE_DELETE_TOOLS` - Enable/disable destructive operations (optional, defaults to false)
 55 | - `ENABLE_RAW_RESPONSE` - Return raw vs filtered responses (optional, defaults to false)
 56 | 
 57 | ---
 58 | 
 59 | ### Installation
 60 | 
 61 | ```bash
 62 | # Clone the repository
 63 | git clone https://github.com/severity1/terraform-cloud-mcp.git
 64 | cd terraform-cloud-mcp
 65 | 
 66 | # Create virtual environment and activate it
 67 | uv venv
 68 | source .venv/bin/activate
 69 | 
 70 | # Install package
 71 | uv pip install .
 72 | ```
 73 | 
 74 | ### Adding to Claude Environments
 75 | 
 76 | #### Adding to Claude Code CLI
 77 | 
 78 | ```bash
 79 | # Add to Claude Code with your Terraform Cloud token
 80 | claude mcp add -e TFC_TOKEN=YOUR_TF_TOKEN -e ENABLE_DELETE_TOOLS=false -s user terraform-cloud-mcp -- "terraform-cloud-mcp"
 81 | 
 82 | # To use a self-hosted Terraform Enterprise instance:
 83 | # claude mcp add -e TFC_TOKEN=YOUR_TF_TOKEN -e TFC_ADDRESS=https://terraform.example.com -s user terraform-cloud-mcp -- "terraform-cloud-mcp"
 84 | 
 85 | # To enable delete operations (use with caution):
 86 | # claude mcp add -e TFC_TOKEN=YOUR_TF_TOKEN -e ENABLE_DELETE_TOOLS=true -s user terraform-cloud-mcp -- "terraform-cloud-mcp"
 87 | ```
 88 | 
 89 | #### Adding to Claude Desktop
 90 | 
 91 | Create a `claude_desktop_config.json` configuration file:
 92 | - mac: ~/Library/Application Support/Claude/claude_desktop_config.json
 93 | - win: %APPDATA%\Claude\claude_desktop_config.json
 94 | 
 95 | ```json
 96 | {
 97 |   "mcpServers": {
 98 |     "terraform-cloud-mcp": {
 99 |       "command": "/path/to/uv", # Get this by running: `which uv`
100 |       "args": [
101 |         "--directory",
102 |         "/path/to/your/terraform-cloud-mcp", # Full path to this project
103 |         "run",
104 |         "terraform-cloud-mcp"
105 |       ],
106 |       "env": {
107 |         "TFC_TOKEN": "my token...", # replace with actual token
108 |         "TFC_ADDRESS": "https://app.terraform.io", # optional, change for self-hosted TFE
109 |         "ENABLE_DELETE_TOOLS": "false" # set to "true" to enable destructive operations
110 |       }
111 |     }
112 |   }
113 | }
114 | ```
115 | 
116 | Replace `your_terraform_cloud_token` with your actual Terraform Cloud API token.
117 | 
118 | #### Other MCP-Compatible Platforms
119 | 
120 | For other platforms (like Cursor, Copilot Studio, or Glama), follow their platform-specific instructions for adding an MCP server. Most platforms require:
121 | 1. The server path or command to start the server.
122 | 2. Environment variables for the Terraform Cloud API token (`TFC_TOKEN`).
123 | 3. Optional environment variable for self-hosted Terraform Enterprise (`TFC_ADDRESS`).
124 | 4. Optional environment variable to enable delete operations (`ENABLE_DELETE_TOOLS=true` for destructive operations).
125 | 5. Configuration to auto-start the server when needed.
126 | 
127 | ---
128 | 
129 | ## Available Tools
130 | 
131 | ### Account Tools
132 | 
133 | - `get_account_details()`: Gets account information for the authenticated user or service account.
134 | 
135 | ### Workspace Management Tools
136 | 
137 | #### List & Search
138 | - `list_workspaces(organization, page_number, page_size, search)`: List and filter workspaces.
139 | - `get_workspace_details(workspace_id, organization, workspace_name)`: Get detailed information about a specific workspace.
140 | 
141 | #### Create & Update
142 | - `create_workspace(organization, name, params)`: Create a new workspace with optional parameters.
143 | - `update_workspace(organization, workspace_name, params)`: Update an existing workspace's configuration.
144 | 
145 | #### Delete (Requires ENABLE_DELETE_TOOLS=true)
146 | - `delete_workspace(organization, workspace_name)`: Delete a workspace and all its content.
147 | - `safe_delete_workspace(organization, workspace_name)`: Delete only if the workspace isn't managing any resources.
148 | 
149 | **Note**: Delete operations are disabled by default for safety. Set `ENABLE_DELETE_TOOLS=true` to enable these destructive operations.
150 | 
151 | #### Lock & Unlock
152 | - `lock_workspace(workspace_id, reason)`: Lock a workspace to prevent runs.
153 | - `unlock_workspace(workspace_id)`: Unlock a workspace to allow runs.
154 | - `force_unlock_workspace(workspace_id)`: Force unlock a workspace locked by another user.
155 | 
156 | <!-- Future implementation: Data Retention
157 | - `set_data_retention_policy(workspace_id, days)`: Set a data retention policy.
158 | - `get_data_retention_policy(workspace_id)`: Get the current data retention policy.
159 | - `delete_data_retention_policy(workspace_id)`: Delete the data retention policy. -->
160 | 
161 | ### Run Management Tools
162 | 
163 | - `create_run(workspace_id, params)`: Create and queue a Terraform run in a workspace using its ID.
164 | - `list_runs_in_workspace(workspace_id, ...)`: List and filter runs in a specific workspace using its ID.
165 | - `list_runs_in_organization(organization, ...)`: List and filter runs across an entire organization.
166 | - `get_run_details(run_id)`: Get detailed information about a specific run.
167 | - `apply_run(run_id, comment)`: Apply a run waiting for confirmation.
168 | - `discard_run(run_id, comment)`: Discard a run waiting for confirmation.
169 | - `cancel_run(run_id, comment)`: Cancel a run currently planning or applying.
170 | - `force_cancel_run(run_id, comment)`: Forcefully cancel a run immediately.
171 | - `force_execute_run(run_id)`: Forcefully execute a pending run by canceling prior runs.
172 | 
173 | ### Plan Management Tools
174 | 
175 | - `get_plan_details(plan_id)`: Get detailed information about a specific plan.
176 | - `get_plan_json_output(plan_id)`: Retrieve the JSON execution plan for a specific plan with proper redirect handling.
177 | - `get_run_plan_json_output(run_id)`: Retrieve the JSON execution plan from a run with proper redirect handling.
178 | - `get_plan_logs(plan_id)`: Retrieve logs from a plan operation.
179 | 
180 | ### Apply Management Tools
181 | 
182 | - `get_apply_details(apply_id)`: Get detailed information about a specific apply.
183 | - `get_errored_state(apply_id)`: Retrieve the errored state from a failed apply for recovery.
184 | - `get_apply_logs(apply_id)`: Retrieve logs from an apply operation.
185 | 
186 | ### Project Management Tools
187 | 
188 | - `create_project(organization, name, params)`: Create a new project with optional parameters.
189 | - `update_project(project_id, params)`: Update an existing project's configuration.
190 | - `list_projects(organization, ...)`: List and filter projects in an organization.
191 | - `get_project_details(project_id)`: Get detailed information about a specific project.
192 | - `delete_project(project_id)`: Delete a project (fails if it contains workspaces). **Requires ENABLE_DELETE_TOOLS=true**
193 | - `list_project_tag_bindings(project_id)`: List tags bound to a project.
194 | - `add_update_project_tag_bindings(project_id, tag_bindings)`: Add or update tag bindings on a project.
195 | - `move_workspaces_to_project(project_id, workspace_ids)`: Move workspaces into a project.
196 | 
197 | ### Organization Management Tools
198 | 
199 | - `get_organization_details(organization)`: Get detailed information about a specific organization.
200 | - `get_organization_entitlements(organization)`: Show entitlement set for organization features.
201 | - `list_organizations(page_number, page_size, query, query_email, query_name)`: List and filter organizations.
202 | - `create_organization(name, email, params)`: Create a new organization with optional parameters.
203 | - `update_organization(organization, params)`: Update an existing organization's settings.
204 | - `delete_organization(organization)`: Delete an organization and all its content. **Requires ENABLE_DELETE_TOOLS=true**
205 | 
206 | ### Cost Estimation Tools
207 | 
208 | - `get_cost_estimate_details(cost_estimate_id)`: Get detailed information about a specific cost estimate, including resource counts (matched and unmatched), prior monthly cost, proposed monthly cost, and delta monthly cost estimations. Use run relationships to find cost estimate IDs for specific runs.
209 | 
210 | ### Assessment Results Tools
211 | 
212 | - `get_assessment_result_details(assessment_result_id)`: Get detailed information about a specific health assessment result.
213 | - `get_assessment_json_output(assessment_result_id)`: Retrieve the JSON execution plan from an assessment result.
214 | - `get_assessment_json_schema(assessment_result_id)`: Retrieve the JSON schema file from an assessment result.
215 | - `get_assessment_log_output(assessment_result_id)`: Retrieve logs from an assessment result operation.
216 | 
217 | ### State Version Management Tools
218 | 
219 | - `list_state_versions(organization, workspace_name, page_number, page_size, filter_status)`: List and filter state versions in a workspace.
220 | - `get_current_state_version(workspace_id)`: Get the current state version for a workspace.
221 | - `get_state_version(state_version_id)`: Get details for a specific state version.
222 | - `create_state_version(workspace_id, serial, md5, params)`: Create a new state version in a workspace.
223 | - `download_state_file(state_version_id, json_format)`: Download the raw or JSON formatted state file.
224 | 
225 | ### State Version Outputs Tools
226 | 
227 | - `list_state_version_outputs(state_version_id, page_number, page_size)`: List outputs for a specific state version.
228 | - `get_state_version_output(state_version_output_id)`: Get details for a specific state version output.
229 | 
230 | ### Variables Management Tools
231 | 
232 | #### Workspace Variables
233 | - `list_workspace_variables(workspace_id)`: List all variables (Terraform and environment) for a workspace.
234 | - `create_workspace_variable(workspace_id, key, category, params)`: Create a new variable in a workspace.
235 | - `update_workspace_variable(workspace_id, variable_id, params)`: Update an existing workspace variable.
236 | - `delete_workspace_variable(workspace_id, variable_id)`: Delete a workspace variable. **Requires ENABLE_DELETE_TOOLS=true**
237 | 
238 | #### Variable Sets
239 | - `list_variable_sets(organization, page_number, page_size)`: List variable sets in an organization.
240 | - `get_variable_set(varset_id)`: Get details for a specific variable set.
241 | - `create_variable_set(organization, name, params)`: Create a new variable set.
242 | - `update_variable_set(varset_id, params)`: Update an existing variable set.
243 | - `delete_variable_set(varset_id)`: Delete a variable set and all its variables. **Requires ENABLE_DELETE_TOOLS=true**
244 | - `assign_variable_set_to_workspaces(varset_id, workspace_ids)`: Assign a variable set to workspaces.
245 | - `unassign_variable_set_from_workspaces(varset_id, workspace_ids)`: Remove a variable set from workspaces.
246 | - `assign_variable_set_to_projects(varset_id, project_ids)`: Assign a variable set to projects.
247 | - `unassign_variable_set_from_projects(varset_id, project_ids)`: Remove a variable set from projects.
248 | 
249 | #### Variable Set Variables
250 | - `list_variables_in_variable_set(varset_id)`: List all variables in a variable set.
251 | - `create_variable_in_variable_set(varset_id, key, category, params)`: Create a variable in a variable set.
252 | - `update_variable_in_variable_set(varset_id, var_id, params)`: Update a variable in a variable set.
253 | - `delete_variable_from_variable_set(varset_id, var_id)`: Delete a variable from a variable set. **Requires ENABLE_DELETE_TOOLS=true**
254 | 
255 | **Note**: Variable management includes both Terraform input variables and environment variables. Sensitive variables have their values hidden for security. Delete operations are disabled by default and require `ENABLE_DELETE_TOOLS=true`.
256 | 
257 | ---
258 | 
259 | ## Development Guide
260 | 
261 | For detailed development guidance including code standards, Pydantic patterns, and contribution workflows, see our [Development Documentation](docs/DEVELOPMENT.md).
262 | 
263 | ### Quick Development Setup
264 | 
265 | ```bash
266 | # Clone the repository
267 | git clone https://github.com/severity1/terraform-cloud-mcp.git
268 | cd terraform-cloud-mcp
269 | 
270 | # Create virtual environment and activate it
271 | uv venv
272 | source .venv/bin/activate  # On Windows: .venv\Scripts\activate
273 | 
274 | # Install in development mode with development dependencies
275 | uv pip install -e .
276 | uv pip install black mypy pydantic ruff
277 | ```
278 | 
279 | ### Basic Development Commands
280 | 
281 | ```bash
282 | # Run the server in development mode
283 | mcp dev terraform_cloud_mcp/server.py
284 | 
285 | # Run tests and quality checks
286 | uv run -m mypy .
287 | uv run -m ruff check .
288 | uv run -m black .
289 | ```
290 | 
291 | For detailed information on code organization, architecture, development workflows, and code quality guidelines, refer to [docs/DEVELOPMENT.md](docs/DEVELOPMENT.md).
292 | 
293 | ---
294 | 
295 | ## Documentation
296 | 
297 | The codebase includes comprehensive documentation:
298 | 
299 | - **Code Comments**: Focused on explaining the "why" behind implementation decisions
300 | - **Docstrings**: All public functions and classes include detailed docstrings
301 | - **Implementation References**: Development documentation now references actual code examples rather than using code snippets
302 | - **Example Files**: The `docs/` directory contains detailed examples for each domain:
303 |   - `docs/FILTERING_SYSTEM.md`: Comprehensive guide to the audit-safe response filtering system (5-15% token reduction, 100% audit compliance)
304 |   - `docs/DEVELOPMENT.md`: Development standards and coding guidelines with references to actual code
305 |   - `docs/API_REFERENCES.md`: Terraform Cloud API documentation links with implementation status
306 |   - `docs/CONTRIBUTING.md`: Guidelines for contributing to the project
307 |   - `docs/models/`: Reference documentation for all model types
308 |   - `docs/tools/`: Detailed reference documentation for each tool
309 |   - `docs/conversations/`: Sample conversation flows with the API
310 | 
311 | ## Troubleshooting
312 | 
313 | 1. Check server logs (debug logging is enabled by default)
314 | 2. Use the MCP Inspector (http://localhost:5173) for debugging
315 | 3. Debug logging is already enabled in `server.py`:
316 |    ```python
317 |    import logging
318 |    logging.basicConfig(level=logging.DEBUG)
319 |    ```
320 | 
321 | ---
322 | 
323 | ## Contributing
324 | 
325 | Contributions are welcome! Please open an issue or pull request if you'd like to contribute to this project.
326 | 
327 | See our [Contributing Guide](docs/CONTRIBUTING.md) for detailed instructions on how to get started, code quality standards, and the pull request process.
328 | 
329 | ## Disclaimer
330 | 
331 | This project is not affiliated with, associated with, or endorsed by HashiCorp or Terraform.  
332 | "Terraform" and "Terraform Cloud" are trademarks of HashiCorp.  
333 | This project merely interacts with the Terraform Cloud public API under fair use.
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/configs/CLAUDE.md:
--------------------------------------------------------------------------------

```markdown
 1 | # CLAUDE.md for configs/
 2 | 
 3 | This file provides guidance about configuration management for the Terraform Cloud MCP implementation.
 4 | 
 5 | ## Context Activation
 6 | This guidance activates when:
 7 | - Working in `terraform_cloud_mcp/configs/` directory
 8 | - Creating/editing configuration files (*.py)
 9 | - Implementing configuration-driven functionality
10 | - Adding new resource type configurations
11 | 
12 | **Companion directories**: utils/ (for usage), models/ (for validation)
13 | 
14 | ## Configuration Architecture
15 | 
16 | The configs directory provides centralized configuration data to maintain consistency and enable easy maintenance:
17 | 
18 | ### Core Configurations
19 | - **filter_configs.py**: Response filtering configurations for token optimization
20 | 
21 | ## Filter Configuration Standards
22 | 
23 | ### Resource Type Configurations
24 | When adding new resource types, add filter configurations to `FILTER_CONFIGS`:
25 | - **always_remove**: Fields always filtered regardless of operation type
26 | - **read_remove**: Fields filtered only for READ operations (detailed views)
27 | - **list_remove**: Fields filtered only for LIST operations (pagination views)
28 | - **essential_relationships**: Relationships to preserve (optional)
29 | 
30 | ### Detection Pattern Standards
31 | Update detection patterns when adding new API endpoints:
32 | - **PATH_PATTERNS**: Add new path patterns in specificity order (most specific first)
33 | - **DATA_TYPE_MAP**: Add fallback mappings for response data type detection
34 | - **RESOURCE_TYPE_MAP**: Add string-to-enum conversions for new resource types
35 | 
36 | ### Configuration Maintenance
37 | When implementing new tools or API endpoints:
38 | - **Review API responses**: Check for verbose/unnecessary fields that impact token usage
39 | - **Test filtering effectiveness**: Ensure essential operational data is preserved
40 | - **Update configurations**: Add new resource types or modify existing filter rules
41 | - **Validate detection**: Ensure new endpoints are correctly detected and mapped
42 | 
43 | ### MCP Context Preservation Requirements
44 | As an MCP server for Terraform Cloud, filter configurations must preserve essential context:
45 | - **Never filter essential fields**: Resource IDs, names, status, operational URLs, permissions
46 | - **Preserve operational context**: Status information, timing data, progress indicators
47 | - **Maintain relationships**: Resource connections and hierarchical data
48 | - **Keep user-relevant data**: Configuration settings, decision support information
49 | - **Conservative READ filtering**: Detailed views need comprehensive context
50 | - **Selective LIST filtering**: Lists can be more aggressively filtered for identification
51 | 
52 | ## Implementation Guidelines
53 | 
54 | ### New Resource Type Process
55 | 1. **Add to models**: Define `ResourceType` enum value in `models/filters.py`
56 | 2. **Create filter config**: Add `FilterConfig` entry in `FILTER_CONFIGS` 
57 | 3. **Update detection**: Add path patterns and type mappings as needed
58 | 4. **Test filtering**: Verify correct resource detection and appropriate filtering
59 | 
60 | ### Configuration Quality Standards
61 | - **Specificity ordering**: More specific patterns before general ones in `PATH_PATTERNS`
62 | - **Conservative filtering**: Only remove fields that don't impact functionality
63 | - **Documentation**: Document reasoning for field removal decisions
64 | - **Testing**: Validate filter effectiveness after configuration changes
65 | 
66 | ### Maintenance Triggers
67 | Update configurations when:
68 | - **New API endpoints**: Add detection patterns and filter rules
69 | - **API response changes**: Review existing filter configurations
70 | - **Token usage optimization**: Identify new fields for filtering
71 | - **Performance issues**: Optimize filter configurations for better efficiency
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/api/CLAUDE.md:
--------------------------------------------------------------------------------

```markdown
  1 | # CLAUDE.md for api/
  2 | 
  3 | This file provides guidance about the Terraform Cloud API client implementation.
  4 | 
  5 | ## Context Activation
  6 | This guidance activates when:
  7 | - Working in `terraform_cloud_mcp/api/` directory
  8 | - Creating/editing API client files (*.py)
  9 | - Implementing HTTP request handling or authentication
 10 | - Adding redirect management or response processing
 11 | 
 12 | **Companion directories**: tools/ (for usage), models/ (for requests), utils/ (for helpers)
 13 | 
 14 | ## API Client Architecture
 15 | 
 16 | The API client provides core functionality for Terraform Cloud API integration:
 17 | - **Authentication**: Terraform Cloud API token management
 18 | - **Request handling**: Formatting, submission, and response processing
 19 | - **Error management**: Consistent error handling across all API calls
 20 | - **Redirect handling**: Custom handling for Terraform Cloud pre-signed URLs
 21 | 
 22 | ### Core Components
 23 | - **client.py**: `api_request()` main function and `handle_redirect()` for pre-signed URLs
 24 | 
 25 | ## Implementation Standards
 26 | 
 27 | ### Request Function Pattern
 28 | The `api_request()` function handles all API interactions with:
 29 | - **Path/Method**: API endpoint path and HTTP method (GET, POST, PATCH, DELETE)
 30 | - **Authentication**: Automatic token management via utils/env.py
 31 | - **Parameters**: Query parameters and request body handling
 32 | - **Response types**: JSON and text response processing
 33 | 
 34 | ### Custom Redirect Management
 35 | Custom redirect handling (not httpx automatic) provides:
 36 | - **Authentication preservation**: Maintains auth headers through redirects
 37 | - **Content-type processing**: Handles pre-signed URL responses appropriately
 38 | - **Terraform Cloud compatibility**: Required for API pre-signed URL patterns
 39 | 
 40 | ### Response Handling Standards
 41 | - **Success responses**: 200/201 return raw API data; 204 returns `{"status": "success", "status_code": 204}`
 42 | - **Response filtering**: Automatic filtering applied to GET requests returning JSON data
 43 | - **Error handling**: HTTP status errors, network issues, JSON parsing failures  
 44 | - **Security**: Never logs tokens/credentials, validates inputs, proper error redaction
 45 | 
 46 | ## Usage Standards
 47 | 
 48 | ### Integration Requirements
 49 | - **Error handling**: Always use with `@handle_api_errors` decorator from utils/decorators.py
 50 | - **Environment management**: Token handling via `get_tfc_token()` from utils/env.py
 51 | - **Payload creation**: Convert Pydantic models using utils/payload.py utilities
 52 | - **Content downloads**: Set `accept_text=True` for redirect-based content retrieval
 53 | 
 54 | ## Development Standards
 55 | 
 56 | ### Quality Checks
 57 | - **Format**: `ruff format .`
 58 | - **Lint**: `ruff check .`
 59 | - **Type Check**: `mypy .`
 60 | - **Test**: `pytest`
 61 | 
 62 | ### API Client Requirements
 63 | - All functions must include proper error handling and consistent response format
 64 | - Apply security guidelines for token and credential management
 65 | - Follow established patterns for request formatting and response processing
 66 | - Test with comprehensive coverage of success, error, and edge cases
 67 | 
 68 | ### Integration Guidelines
 69 | 
 70 | ### Tool Integration
 71 | When API client is used in tools:
 72 | - Always use with `@handle_api_errors` decorator
 73 | - Apply proper payload creation using utility functions
 74 | - Handle redirects appropriately for content downloads
 75 | - Use centralized token management
 76 | 
 77 | ### Model Integration
 78 | When API client works with models:
 79 | - Convert Pydantic models using payload utilities
 80 | - Apply proper request validation before API calls
 81 | - Handle model validation errors appropriately
 82 | - Ensure proper type safety throughout request pipeline
 83 | 
 84 | ### Utility Integration
 85 | When API client works with utilities:
 86 | - Use environment management for token handling
 87 | - Apply payload creation utilities for JSON:API compliance
 88 | - Use error handling decorators consistently
 89 | - Apply security practices for sensitive data
 90 | 
 91 | ## Implementation Workflow
 92 | 
 93 | ### API Client Enhancement Process
 94 | 1. **Define request patterns**: Follow established function signatures
 95 | 2. **Implement authentication**: Use centralized token management
 96 | 3. **Add error handling**: Apply consistent response formats
 97 | 4. **Handle redirects**: Use custom redirect management where needed
 98 | 5. **Test thoroughly**: Cover success, error, network, and redirect scenarios
 99 | 6. **Update documentation**: Implementation status tracking
100 | 
101 | ### Quality Validation Checklist
102 | For each API client enhancement:
103 | - [ ] Function includes proper authentication and error handling
104 | - [ ] Custom redirect handling applied where needed for TFC pre-signed URLs
105 | - [ ] Security guidelines followed for token and credential management
106 | - [ ] Quality checks passed: format, lint, type check
107 | - [ ] Tests cover all scenarios: success, error, network issues, redirects
108 | - [ ] Documentation updated: implementation status tracking
```

--------------------------------------------------------------------------------
/CLAUDE.md:
--------------------------------------------------------------------------------

```markdown
  1 | # CLAUDE.md
  2 | 
  3 | This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
  4 | 
  5 | # Terraform Cloud MCP Development Guide
  6 | 
  7 | ## Subtree Discovery System
  8 | 
  9 | This project uses Claude Code's automatic subtree discovery for context-aware guidance. Component-specific CLAUDE.md files are automatically loaded when working in their directories:
 10 | 
 11 | - **docs/** - Documentation standards and templates
 12 | - **terraform_cloud_mcp/tools/** - MCP tools implementation patterns  
 13 | - **terraform_cloud_mcp/models/** - Pydantic models and validation
 14 | - **terraform_cloud_mcp/utils/** - Utility functions and error handling
 15 | - **terraform_cloud_mcp/api/** - API client patterns
 16 | 
 17 | ## Working Directory Guidance
 18 | 
 19 | ### When Working on Tool Implementation
 20 | - **Directory**: `terraform_cloud_mcp/tools/`
 21 | - **Context**: Automatic loading of tools-specific patterns
 22 | - **Focus**: MCP function signatures, error handling, API integration
 23 | 
 24 | ### When Working on Data Models
 25 | - **Directory**: `terraform_cloud_mcp/models/`
 26 | - **Context**: Automatic loading of model validation patterns
 27 | - **Focus**: Pydantic models, validation rules, type definitions
 28 | 
 29 | ### When Working on Utilities
 30 | - **Directory**: `terraform_cloud_mcp/utils/`
 31 | - **Context**: Automatic loading of utility function patterns
 32 | - **Focus**: Error handling, API helpers, common operations
 33 | 
 34 | ### When Working on API Client
 35 | - **Directory**: `terraform_cloud_mcp/api/`
 36 | - **Context**: Automatic loading of API client patterns
 37 | - **Focus**: HTTP client, authentication, request handling
 38 | 
 39 | ### When Working on Documentation
 40 | - **Directory**: `docs/`
 41 | - **Context**: Automatic loading of documentation standards
 42 | - **Focus**: Templates, formatting, structure requirements
 43 | 
 44 | ## Development Commands
 45 | 
 46 | ### Quality Checks
 47 | - **Format**: `ruff format .`
 48 | - **Lint**: `ruff check .`
 49 | - **Type Check**: `mypy .`
 50 | - **Test**: `pytest`
 51 | 
 52 | ### Build Commands
 53 | - **Install**: `uv pip install -e .`
 54 | - **Dev Install**: `uv pip install -e .[dev]`
 55 | - **Requirements**: `uv pip compile requirements.in`
 56 | 
 57 | ## Core Principles
 58 | 
 59 | ### Decision-Making Process
 60 | 1. **Use component guidance**: Let subtree discovery load relevant context
 61 | 2. **Apply documented patterns**: Follow loaded component standards
 62 | 3. **Avoid code inference**: Use documented criteria only
 63 | 4. **Validate against patterns**: Check implementation against guidance
 64 | 
 65 | ### Task Complexity Assessment
 66 | - **Simple** (< 2 hours): Direct implementation, minimal planning
 67 | - **Medium** (2-8 hours): Use TodoWrite for 3-5 tasks
 68 | - **Complex** (> 8 hours): Use subagents (2-6) with comprehensive TodoWrite planning
 69 | 
 70 | ## Documentation Standards
 71 | 
 72 | ### Required Documentation Updates
 73 | For any new implementation, always update:
 74 | - **TASKS.md**: Move features from planned to completed status
 75 | - **docs/API_REFERENCES.md**: Mark corresponding API sections as implemented  
 76 | - **docs/DEVELOPMENT.md**: Add new patterns if applicable
 77 | - **docs/CONTRIBUTING.md**: Update contribution guidelines if new patterns introduced
 78 | 
 79 | ### Implementation Standards  
 80 | - **Use utility functions**: `create_api_payload()`, `query_params()`, `@handle_api_errors`
 81 | - **Apply response filtering**: Automatic filtering system in `utils/filters.py` handles all GET requests
 82 | - **Follow component patterns**: Apply standards from automatically loaded component CLAUDE.md files
 83 | - **Run quality checks**: Format, lint, type check before completion
 84 | - **Update relevant documentation**: Maintain consistency across project
 85 | 
 86 | ### Response Filtering Implementation Context
 87 | This MCP server implements audit-safe response filtering with the following constraints:
 88 | - **Primary use case**: Audit and compliance scenarios requiring complete data integrity
 89 | - **Filtering approach**: Conservative token optimization (5-15% reduction) to preserve audit trails
 90 | - **Critical preservation requirements**: 
 91 |   - User accountability data (`created-at`, `updated-at`, `version-id`)
 92 |   - Security configuration (permissions, auth policies)
 93 |   - Change tracking (status timestamps, source information)
 94 |   - Operational context (status, timing, progress indicators)
 95 | - **Decision principle**: Preserve fields when audit impact is uncertain
 96 | - **Implementation location**: `utils/filters.py` with configurations in `configs/filter_configs.py`
 97 | 
 98 | ## Task Management
 99 | 
100 | ### TodoWrite Usage
101 | Use TodoWrite for tasks with:
102 | - Multiple distinct steps (> 2)
103 | - Multiple file changes
104 | - Cross-component coordination
105 | - Medium to complex scope
106 | 
107 | ### Progress Standards  
108 | - Mark todos `in_progress` before starting
109 | - Mark `completed` immediately after finishing
110 | - Update status in real-time
111 | - Provide concise progress updates for major phases
112 | 
113 | ## Memory System Maintenance
114 | 
115 | ### Periodic Review Schedule
116 | - **Monthly**: Review component CLAUDE.md files for outdated patterns
117 | - **After major features**: Update decision matrices and workflow patterns
118 | - **When adding new domains**: Verify subtree discovery optimization
119 | - **Quality check failures**: Review and update development standards
120 | 
121 | ### Maintenance Triggers
122 | - **New implementation patterns**: Update relevant component guidance
123 | - **API changes**: Review model and tool implementation standards  
124 | - **Development workflow changes**: Update quality check commands
125 | - **Documentation structure changes**: Update docs/ guidance
126 | - **Filter configuration changes**: When new API fields appear, assess preservation vs. optimization trade-offs
127 | - **Compliance requirement changes**: Review filter configurations if audit use cases evolve
128 | 
129 | ### Memory Optimization Indicators
130 | - **High context usage**: Review for redundant information across files
131 | - **Frequent cross-referencing**: Consider consolidating related guidance
132 | - **Outdated patterns**: Remove deprecated implementation approaches
133 | - **Missing decision criteria**: Add decision matrices for common scenarios
```

--------------------------------------------------------------------------------
/docs/CLAUDE.md:
--------------------------------------------------------------------------------

```markdown
  1 | # CLAUDE.md for docs/
  2 | 
  3 | This file provides guidance about the documentation structure and standards in this repository.
  4 | 
  5 | ## Context Activation
  6 | This guidance activates when:
  7 | - Working in `docs/` directory
  8 | - Creating/editing documentation files (*.md)
  9 | - Implementing multi-layer documentation structure
 10 | - Adding cross-references or updating documentation standards
 11 | 
 12 | **Companion directories**: All component directories (tools/, models/, utils/, api/)
 13 | 
 14 | ## Documentation Architecture
 15 | 
 16 | ### Core Files
 17 | - **DEVELOPMENT.md**: Development standards and comprehensive build/quality guidance
 18 | - **CONTRIBUTING.md**: Contributing guidelines and PR process
 19 | - **README.md**: Documentation directory overview
 20 | - **API_REFERENCES.md**: Terraform Cloud API reference links and implementation status
 21 | 
 22 | ### Multi-Layer Structure
 23 | Documentation follows a consistent 4-layer pattern for each domain:
 24 | 
 25 | 1. **conversations/**: Real-world usage examples and interaction patterns
 26 | 2. **models/**: Pydantic model documentation with validation rules and API mappings
 27 | 3. **tools/**: API tool reference with signatures, parameters, and error scenarios
 28 | 4. **Code docstrings**: Implementation-level documentation with cross-references
 29 | 
 30 | ## Documentation Standards
 31 | 
 32 | ### Core Principles
 33 | - **Consistency**: Each domain has documentation across all 4 layers
 34 | - **Implementation-focused**: Reference actual code rather than duplicate examples
 35 | - **Cross-referenced**: All layers link to related documentation
 36 | - **API-aligned**: Include Terraform Cloud API documentation references
 37 | 
 38 | ### Quality Requirements
 39 | - Document input parameters, return types, and error handling
 40 | - Organize examples from basic to advanced
 41 | - Use consistent anchor names (#lowercase-with-hyphens)
 42 | - Maintain valid cross-references with relative paths
 43 | 
 44 | ## New Tool Documentation Workflow
 45 | 
 46 | ### Implementation Steps
 47 | 1. **Model Documentation**: Create `docs/models/{domain}.md` with validation rules and API mappings
 48 | 2. **Tool Documentation**: Create `docs/tools/{domain}.md` with function signatures and examples
 49 | 3. **Conversation Examples**: Create `docs/conversations/{domain}-conversation.md` with usage scenarios
 50 | 4. **Cross-References**: Link all layers bidirectionally
 51 | 5. **Integration**: Update `docs/README.md` and relevant CLAUDE.md files
 52 | 
 53 | ### Cross-Reference Requirements
 54 | Every new tool must maintain bidirectional links across all 4 layers:
 55 | - **Code docstrings** → docs/tools/ sections
 56 | - **docs/tools/** ↔ docs/models/ (bidirectional)
 57 | - **docs/tools/** → docs/conversations/ examples  
 58 | - **docs/models/** → tools that use the model
 59 | - **docs/conversations/** → specific tool and model sections
 60 | 
 61 | ### Validation Checklist
 62 | - [ ] All markdown links use relative paths
 63 | - [ ] Cross-references use consistent anchor names (#lowercase-with-hyphens)
 64 | - [ ] Each layer references appropriate related layers
 65 | - [ ] All links are valid and accessible
 66 | 
 67 | ## Development Standards
 68 | 
 69 | ### Quality Checks
 70 | - **Format**: `ruff format .`
 71 | - **Lint**: `ruff check .`
 72 | - **Type Check**: `mypy .`
 73 | - **Test**: `pytest`
 74 | 
 75 | ### Documentation Quality Standards
 76 | - Setup and quality check sequences
 77 | - Comprehensive validation process for all documentation layers
 78 | - KISS/DRY principles applied to documentation structure
 79 | - Error handling patterns documented consistently
 80 | 
 81 | ### AI Documentation Guidelines
 82 | - Maintain consistency with existing documentation patterns
 83 | - Reference actual code implementations rather than duplicate examples
 84 | - Ensure examples include proper error handling
 85 | - Keep examples concise but comprehensive
 86 | - Follow cross-reference requirements for all layers
 87 | 
 88 | ## Implementation Workflow
 89 | 
 90 | ### New Documentation Creation Process
 91 | 1. **Core Status Files**: Update TASKS.md and API_REFERENCES.md to reflect implementation progress
 92 | 2. **Multi-Layer Documentation**: Create docs/models/, docs/tools/, and docs/conversations/ for new domains
 93 | 3. **Cross-References**: Establish bidirectional links across all 4 layers
 94 | 4. **Integration**: Update docs/README.md with new documentation sections
 95 | 5. **Validation**: Test all links and anchor references
 96 | 
 97 | ### Documentation Quality Checklist
 98 | For each new documentation implementation:
 99 | - [ ] All 4 documentation layers created (conversations, models, tools, code docstrings)
100 | - [ ] Cross-references established bidirectionally between all layers
101 | - [ ] TASKS.md and API_REFERENCES.md updated to reflect new capabilities
102 | - [ ] All markdown links use relative paths and valid anchors
103 | - [ ] Examples include proper error handling and follow established patterns
104 | - [ ] Documentation follows consistent template structure
105 | 
106 | ---
107 | 
108 | ## Documentation Templates
109 | 
110 | ### Code Docstring Template
111 | ```python
112 | """Tool description with clear usage context.
113 | 
114 | API endpoint: METHOD /path/to/endpoint
115 | 
116 | Args:
117 |     param_name: Description with format/constraints (e.g., "ws-xxxxxxxx")
118 |     
119 | Returns:
120 |     Description of return structure and key fields
121 |     
122 | See:
123 |     docs/tools/domain.md#tool-name for usage examples
124 | """
125 | ```
126 | 
127 | ### Tool Reference Template  
128 | ```markdown
129 | ### tool_name
130 | **Function:** `tool_name(param1: str, param2: int = 0) -> APIResponse`  
131 | **Description:** What it does and when to use it
132 | **Parameters:** 
133 | - param1: Description with format requirements
134 | - param2: Description with default value
135 | **Returns:** Return structure explanation
136 | **Models:** [DomainModel](../models/domain.md#domainmodel)
137 | **Examples:** [Usage Scenario](../conversations/domain-conversation.md#scenario-name)
138 | ```
139 | 
140 | ### Model Documentation Template
141 | ```markdown
142 | ### ModelName
143 | **Purpose:** What this model validates
144 | **Used by:** [tool_name](../tools/domain.md#tool-name), [other_tool](../tools/domain.md#other-tool)
145 | **Fields:** Field descriptions and validation rules
146 | **API Mapping:** model_field -> "api-field-name"
147 | ```
148 | 
149 | ### Conversation Example Template
150 | ```markdown
151 | ## Scenario Name
152 | **Tools used:** [tool_name](../tools/domain.md#tool-name)
153 | **Models:** [ModelName](../models/domain.md#modelname)
154 | **Description:** Realistic usage scenario with expected inputs/outputs
155 | ```
```

--------------------------------------------------------------------------------
/docs/CONTRIBUTING.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Contributing to Terraform Cloud MCP
  2 | 
  3 | Thank you for your interest in contributing to the Terraform Cloud MCP project! This document provides guidelines and instructions for contributing to this project.
  4 | 
  5 | ## Getting Started
  6 | 
  7 | 1. Fork the repository on GitHub
  8 | 2. Clone your forked repository locally
  9 | 3. Set up the development environment as described in the [Development Guide](DEVELOPMENT.md)
 10 | 
 11 | ## Development Environment
 12 | 
 13 | ```bash
 14 | # Clone the repository
 15 | git clone https://github.com/severity1/terraform-cloud-mcp.git
 16 | cd terraform-cloud-mcp
 17 | 
 18 | # Create virtual environment and activate it
 19 | uv venv
 20 | source .venv/bin/activate  # On Windows: .venv\Scripts\activate
 21 | 
 22 | # Install in development mode with development dependencies
 23 | uv pip install -e .
 24 | uv pip install black mypy pydantic ruff
 25 | ```
 26 | 
 27 | ## Code Quality Standards
 28 | 
 29 | Before submitting your contribution, please ensure your code meets our quality standards:
 30 | 
 31 | 1. **Type Checking**: Use proper type hints everywhere
 32 |    ```bash
 33 |    uv run -m mypy .
 34 |    ```
 35 | 
 36 | 2. **Linting**: Ensure code follows our style guidelines
 37 |    ```bash
 38 |    uv run -m ruff check .
 39 |    ```
 40 | 
 41 | 3. **Formatting**: Format code with Black
 42 |    ```bash
 43 |    uv run -m black .
 44 |    ```
 45 | 
 46 | 4. **Tests**: Add tests for new functionality
 47 |    ```bash
 48 |    uv run -m unittest discover tests
 49 |    ```
 50 | 
 51 | ## Contribution Guidelines
 52 | 
 53 | ### Pull Request Process
 54 | 
 55 | 1. Create a feature branch for your changes
 56 | 2. Make your changes following the code style guidelines in the [Development Guide](DEVELOPMENT.md)
 57 | 3. Add or update tests to verify your changes
 58 | 4. Update documentation, including:
 59 |    - Function docstrings
 60 |    - Example files in the appropriate `docs/` subdirectory
 61 |    - README.md if adding new features or changing APIs
 62 | 5. Run all quality checks to ensure your code meets our standards
 63 | 6. Commit your changes with a clear, descriptive commit message
 64 | 7. Push your branch and create a pull request
 65 | 
 66 | ### Commit Messages
 67 | 
 68 | Write clear, descriptive commit messages that explain *why* the change was made, not just *what* changed. For example:
 69 | 
 70 | ```
 71 | Fix workspace creation validation for execution mode
 72 | 
 73 | The workspace creation API was not properly validating the execution
 74 | mode and defaulting to 'local' instead of 'remote', causing confusion
 75 | for users. This fix ensures defaults match API documentation.
 76 | ```
 77 | 
 78 | ## Extending the Server
 79 | 
 80 | To add new functionality to the MCP server:
 81 | 
 82 | 1. Add model classes in the `terraform_cloud_mcp/models` directory:
 83 |    - Define enums for constrained choices
 84 |    - Create request models inheriting from `APIRequest`
 85 |    - Create a `*Params` model for function parameters
 86 |    - For examples, see:
 87 |      - `account.py` for simple request models
 88 |      - `workspaces.py` for comprehensive models with params 
 89 |      - `cost_estimates.py` for models with enums and status tracking
 90 | 
 91 | 2. Add tool functions in the `terraform_cloud_mcp/tools` directory:
 92 |    - Accept typed `params` objects instead of `**kwargs`
 93 |    - Use the `@handle_api_errors` decorator
 94 |    - Use utility functions from `utils/payload.py` for JSON:API payloads
 95 |    - Use utility functions from `utils/request.py` for parameters
 96 |    - Return `APIResponse` type
 97 |    - For examples, see:
 98 |      - `account.py` for simple GET operations
 99 |      - `workspaces.py` for full CRUD operations
100 |      - `cost_estimates.py` for specialized retrieval operations
101 | 
102 | 3. Register new tools in `terraform_cloud_mcp/server.py`:
103 |    - Add import statements at the top
104 |    - Use `mcp.tool()(module_name.function_name)` to register each function
105 |    - Group related tools together with comments
106 | 
107 | 4. Follow the Pydantic pattern for parameter validation and error handling
108 | 
109 | 5. Ensure all functions include proper type hints and docstrings
110 | 
111 | 6. Update documentation in the appropriate places (following reference-based documentation approach):
112 |    - Add model documentation to `docs/models/` (e.g., `cost_estimate.md`) with model structure, validation rules, and references to actual implementations
113 |    - Add tool reference documentation to `docs/tools/` (e.g., `cost_estimate.md`) following the established format:
114 |      - Overview section explaining the tool's purpose
115 |      - API Reference section with links to Terraform Cloud API documentation
116 |      - Tools Reference section with function signatures, parameters, return values, and references to actual implementations
117 |      - Notes section for important usage information
118 |      - Common Error Scenarios section in table format
119 |    - Add conversation examples to `docs/conversations/` (e.g., `cost-estimate-conversation.md`) showing real-world usage patterns with the API
120 |    - Update `docs/README.md` to include new functionality
121 |    - Update `README.md` to include new functionality
122 |    - Update `docs/CONTRIBUTING.md` (this file) to reflect new patterns or processes
123 |    - Update `docs/DEVELOPMENT.md` to include new development standards or patterns
124 | 
125 | 7. Update existing integration files:
126 |    - Add exports to `models/__init__.py`
127 |    - Add imports to `tools/__init__.py`
128 | 
129 | 8. Update `CLAUDE.md` files to document new functionality:
130 |    - Update main `CLAUDE.md` if adding major new components
131 |    - Update `docs/CLAUDE.md` with changes to documentation structure or standards
132 |    - Update component-specific CLAUDE.md files as needed:
133 |      - `terraform_cloud_mcp/api/CLAUDE.md` for API client changes
134 |      - `terraform_cloud_mcp/models/CLAUDE.md` for model patterns
135 |      - `terraform_cloud_mcp/tools/CLAUDE.md` for tool implementation patterns
136 |      - `terraform_cloud_mcp/utils/CLAUDE.md` for utility function patterns
137 |    - These files should include:
138 |      - New patterns introduced
139 |      - Additional examples for AI assistance
140 |      - Component-specific guidelines
141 |    - These files are critical for AI-assisted development and should document any non-obvious patterns
142 | 
143 | ## Release Process
144 | 
145 | If you are a maintainer with release permissions, follow these steps for releasing a new version:
146 | 
147 | 1. Update version number in:
148 |    - `pyproject.toml`
149 |    - `README.md` badges
150 |    - Create release notes
151 | 
152 | 2. Run quality checks:
153 |    - `uv run -m mypy .`
154 |    - `uv run -m ruff check .`
155 |    - `uv run -m black --check .`
156 |    - `uv run -m unittest discover tests`
157 | 
158 | 3. Commit changes with clear message
159 | 
160 | 4. Tag the release with the version number:
161 |    - `git tag v0.x.y`
162 | 
163 | 5. Push changes and tags:
164 |    - `git push origin main --tags`
165 | 
166 | ## Questions?
167 | 
168 | If you have any questions or need help, please open an issue on GitHub and we'll be happy to assist you.
169 | 
170 | Thank you for contributing!
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/tools/CLAUDE.md:
--------------------------------------------------------------------------------

```markdown
  1 | # CLAUDE.md for tools/
  2 | 
  3 | This file provides guidance for MCP tool implementations that expose Terraform Cloud API functionality to AI assistants.
  4 | 
  5 | ## Context Activation
  6 | This guidance activates when:
  7 | - Working in `terraform_cloud_mcp/tools/` directory
  8 | - Reading/editing tool implementation files (*.py)
  9 | - Implementing MCP functions for Terraform Cloud API
 10 | - Adding new tool domains or expanding existing tools
 11 | 
 12 | **Companion directories**: models/ (for validation), utils/ (for utilities), api/ (for client)
 13 | 
 14 | ## Tool Architecture
 15 | 
 16 | ### Directory Structure
 17 | - **__init__.py**: Tool registration and imports
 18 | - **Domain modules**: Account, workspaces, runs, plans, applies, organizations, projects, cost estimates, assessment results
 19 | 
 20 | ### Implementation Standards
 21 | - **Consistent patterns**: All tools follow standardized implementation patterns
 22 | - **Error handling**: Use @handle_api_errors decorator for consistent error management
 23 | - **Async patterns**: All API functions are async using httpx
 24 | - **Parameter validation**: Use Pydantic models for input validation
 25 | 
 26 | ## Tool Organization
 27 | 
 28 | ### Operation Categories
 29 | - **CRUD**: create_*, get_*, update_*, delete_* operations
 30 | - **List**: list_* operations with filtering and pagination
 31 | - **Actions**: lock_*, unlock_*, apply_*, cancel_* state changes
 32 | - **Specialized**: Domain-specific operations
 33 | 
 34 | ### File Organization Rules
 35 | - **Add to existing**: Tool fits domain and file has < 15 functions
 36 | - **Create new file**: New domain OR existing file ≥ 15 functions  
 37 | - **Split file**: When file exceeds 20 functions, split by logical sub-domains
 38 | - **Domain boundaries**: Create new domain for ≥ 5 conceptually distinct tools
 39 | - **Naming**: Use singular form matching API domain (e.g., workspace.py)
 40 | 
 41 | ### Registration Classification
 42 | - **Non-destructive**: get_*, list_*, create_*, update_* (basic registration)
 43 | - **Destructive**: delete_*, force_*, *_unlock affecting running processes (conditional)
 44 | - **Potentially destructive**: cancel_*, discard_* operations (case-by-case)
 45 | 
 46 | ## Decision Matrices
 47 | 
 48 | ### When to Create New File vs Add to Existing
 49 | | Scenario | New File | Add to Existing |
 50 | |----------|----------|-----------------|
 51 | | New API domain (≥5 conceptually distinct tools) | ✅ | ❌ |
 52 | | Existing file has ≥15 functions | ✅ | ❌ |
 53 | | Tool fits existing domain + file <15 functions | ❌ | ✅ |
 54 | | Existing file will exceed 20 functions | ✅ Split by sub-domains | ❌ |
 55 | 
 56 | ### Tool Registration Decision Matrix
 57 | | Operation Type | Examples | Registration | Reason |
 58 | |----------------|----------|-------------|---------|
 59 | | Non-destructive | get_*, list_*, create_*, update_* | Basic | Safe operations |
 60 | | Destructive | delete_*, force_*, *_unlock | Conditional | Affects running processes |
 61 | | Potentially destructive | cancel_*, discard_* | Case-by-case | Context-dependent impact |
 62 | 
 63 | ### Function Signature Pattern Decision
 64 | | Parameter Count | Structure | Example |
 65 | |-----------------|-----------|---------|
 66 | | 1-2 required | Direct parameters | `get_workspace(workspace_id)` |
 67 | | 3+ required | Routing + individual + params | `create_workspace(org, name, params)` |
 68 | | 5+ optional | Use params object | `update_workspace(org, name, params)` |
 69 | | <5 optional | Direct parameters | `list_workspaces(org, search, page)` |
 70 | 
 71 | ## Implementation Requirements
 72 | 
 73 | ### Essential Patterns
 74 | 1. Use @handle_api_errors decorator for consistent error handling
 75 | 2. Create corresponding Pydantic models for validation
 76 | 3. Follow function signature pattern: (required_routing_params, optional_individual_params, optional_params_object)
 77 | 4. Use utility functions for payload creation and parameter handling:
 78 |    - `create_api_payload()` for JSON:API compliant payload creation
 79 |    - `query_params()` for transforming Pydantic models to API parameters
 80 | 5. Document thoroughly with API endpoint references
 81 | 6. Register appropriately in server.py based on destructiveness
 82 | 
 83 | ### Function Signature Patterns
 84 | 
 85 | Tool functions follow a consistent parameter structure. See `variables.py:create_workspace_variable` for the standard pattern.
 86 | 
 87 | **Parameter Order:**
 88 | 1. **Required routing parameters** (workspace_id, organization, etc.)
 89 | 2. **Required API parameters** (key, category, name, etc.)  
 90 | 3. **Optional params object** for additional configuration
 91 | 
 92 | ### Query Parameter Pattern
 93 | For list operations with filtering/pagination, use `query_params()` utility. See `workspaces.py:list_workspaces` for the standard pattern of transforming request models to API parameters.
 94 | 
 95 | ### Documentation Integration
 96 | - Reference API_REFERENCES.md for official API groupings
 97 | - Create usage examples in docs/tools/
 98 | - Link to model definitions and conversation examples
 99 | 
100 | ## Development Standards
101 | 
102 | ### Quality Checks
103 | - **Format**: `ruff format .`
104 | - **Lint**: `ruff check .`
105 | - **Type Check**: `mypy .`
106 | - **Test**: `pytest`
107 | 
108 | ### Code Style Requirements
109 | - Use @handle_api_errors decorator for all API functions
110 | - Follow (required_routing_params, optional_individual_params, optional_params_object) signature pattern
111 | - Apply async patterns with httpx for all API calls
112 | - Use Pydantic models for input validation
113 | - Apply comprehensive testing: Happy path → Edge cases → Error cases → Integration
114 | 
115 | ### Model Integration
116 | When working with models:
117 | - Create corresponding Pydantic models for all tool parameters
118 | - Use model validation for input parameters
119 | - Follow field naming conventions (snake_case for Python, kebab-case for API)
120 | - Apply proper type hints and validation rules
121 | 
122 | ### Utility Function Usage
123 | Essential utility functions for tool implementation:
124 | - `create_api_payload()`: For JSON:API compliant payload creation
125 | - `query_params()`: For transforming Pydantic models to API parameters
126 | - `@handle_api_errors`: Decorator for consistent error handling
127 | - Request helpers: Authentication, pagination, filtering
128 | 
129 | ## Implementation Workflow
130 | 
131 | ### New Tool Development Process
132 | 1. **Define function signature**: Follow parameter order pattern
133 | 2. **Create Pydantic models**: For validation and type safety
134 | 3. **Implement core logic**: Using utility functions and decorators
135 | 4. **Add error handling**: Apply @handle_api_errors decorator
136 | 5. **Register in server.py**: Based on destructiveness classification
137 | 6. **Test thoroughly**: Cover happy path, edge cases, and error conditions
138 | 7. **Update documentation**: TASKS.md, API_REFERENCES.md status updates
139 | 
140 | ### Quality Validation Checklist
141 | For each tool implementation:
142 | - [ ] Function follows Essential Patterns (decorator, models, utilities)
143 | - [ ] Pydantic models created and validated
144 | - [ ] Tool registered in server.py with appropriate classification
145 | - [ ] Quality checks passed: format, lint, type check
146 | - [ ] Documentation updated: implementation status tracking
147 | - [ ] Tests cover all scenarios: success, edge cases, errors
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/CLAUDE.md:
--------------------------------------------------------------------------------

```markdown
  1 | # CLAUDE.md for models/
  2 | 
  3 | This file provides guidance about the Pydantic data models for Terraform Cloud API request validation.
  4 | 
  5 | ## Context Activation
  6 | This guidance activates when:
  7 | - Working in `terraform_cloud_mcp/models/` directory
  8 | - Creating/editing Pydantic model files (*.py)
  9 | - Implementing request validation models
 10 | - Adding field validation or model hierarchies
 11 | 
 12 | **Companion directories**: tools/ (for usage), utils/ (for integration), api/ (for requests)
 13 | 
 14 | ## Model Architecture
 15 | 
 16 | The models directory provides request validation through Pydantic models with:
 17 | - **Input validation**: API request parameter validation and type safety
 18 | - **Field mapping**: Aliases for kebab-case to snake_case API compatibility
 19 | - **Response typing**: All responses typed as `APIResponse = Dict[str, Any]` (not validated)
 20 | 
 21 | ### Core Components
 22 | - **base.py**: `APIRequest` base class, `BaseModelConfig`, and `APIResponse` type alias
 23 | - **Domain modules**: Account, workspaces, runs, plans, applies, organizations, projects, cost estimates, assessment results
 24 | 
 25 | ### Model Categories
 26 | - **Request models**: Validate API request parameters with field aliases and direct parameter fields
 27 | - **Parameter models**: Simplified configuration objects used only for operations with complex parameter sets
 28 | - **Enums**: Constrained choices based on API documentation
 29 | 
 30 | ## Implementation Standards
 31 | 
 32 | ### Model Patterns
 33 | - **Request models**: Extend `APIRequest`, include required fields directly and optional fields as individual parameters
 34 | - **Parameter models**: Create `*Params` objects only when operations have complex parameter sets requiring separation
 35 | - **Direct parameter approach**: Most models now include optional fields directly rather than nested in `params` objects
 36 | - **Base models**: Create `Base*Request` when ≥3 operations share >50% of fields
 37 | - **Enums**: Use for fields with API-documented constrained choices
 38 | 
 39 | ### Implementation Approach
 40 | Request models include all parameters directly. See `variables.py:WorkspaceVariableCreateRequest` for the direct parameter pattern where optional fields are included in the model rather than nested in params objects.
 41 | 
 42 | ### Field Standards
 43 | - **Required**: `Field(...)` with no default (follows API documentation)
 44 | - **Optional**: `Optional[Type]` with appropriate default values
 45 | - **Aliases**: Always use `alias="kebab-case-name"` for API compatibility
 46 | - **Validation**: Apply Field constraints when API docs specify limits
 47 | 
 48 | ## Decision Criteria
 49 | 
 50 | ### Model Creation Rules
 51 | - **BaseRequest**: When ≥3 operations share >50% of fields
 52 | - **Params objects**: Use sparingly - only when parameter sets are complex and need separation from routing parameters
 53 | - **Direct parameters**: Prefer including optional fields directly in request models rather than nested params
 54 | - **Separate Create/Update**: When models differ by >2 fields or validation rules
 55 | - **Enums**: When API docs specify constrained values (not examples)
 56 | 
 57 | ## Decision Matrices
 58 | 
 59 | ### Model Structure Decision Matrix
 60 | | Scenario | Base Model | Separate Models | Direct Parameters |
 61 | |----------|------------|-----------------|-------------------|
 62 | | ≥3 operations share >50% fields | ✅ | ❌ | ❌ |
 63 | | Operations differ by >2 fields | ❌ | ✅ | ❌ |
 64 | | <5 optional parameters | ❌ | ❌ | ✅ |
 65 | | Complex parameter validation needed | ❌ | Use params object | ❌ |
 66 | 
 67 | ### Validation Strategy Decision Matrix
 68 | | Field Type | Validation Approach | Example |
 69 | |------------|---------------------|---------|
 70 | | API-documented constraints | Apply Field constraints | `maxLength=128` |
 71 | | Optional with API default | Use API default value | `default="latest"` |
 72 | | Truly optional in API | Use `None` default | `default=None` |
 73 | | Constrained choices in API docs | Create Enum | `ExecutionMode` |
 74 | 
 75 | ### Parameter Object vs Direct Fields
 76 | | Criteria | Use Params Object | Use Direct Fields |
 77 | |----------|-------------------|-------------------|
 78 | | >5 optional parameters | ✅ | ❌ |
 79 | | Complex validation rules | ✅ | ❌ |
 80 | | Reuse across operations | ✅ | ❌ |
 81 | | Simple operation-specific | ❌ | ✅ |
 82 | 
 83 | ### When to Use Params Objects vs Direct Parameters
 84 | **Use Params Objects When:**
 85 | - Tool function has >5 optional parameters requiring complex validation
 86 | - Parameters need reuse across multiple similar operations
 87 | - Separation of concerns between routing and configuration parameters is critical
 88 | 
 89 | **Use Direct Parameters When (Preferred):**
 90 | - Model has <5 optional parameters
 91 | - Parameters are operation-specific
 92 | - Simpler model structure improves maintainability
 93 | 
 94 | ### Field Validation Rules
 95 | - **Validation constraints**: Apply when API docs specify limits (length, range, format)
 96 | - **Default values**: Use API defaults; None only when field truly optional in API
 97 | - **Required vs Optional**: Follow API documentation exactly
 98 | - **Field organization**: Group by domain, clear inheritance with APIRequest
 99 | 
100 | ## Development Standards
101 | 
102 | ### Quality Checks
103 | - **Format**: `ruff format .`
104 | - **Lint**: `ruff check .`
105 | - **Type Check**: `mypy .`
106 | - **Test**: `pytest`
107 | 
108 | ### Model-Specific Requirements
109 | - All fields must have proper type hints and API-based validation
110 | - Use `BaseModelConfig` and `APIRequest` for consistency
111 | - Document all field aliases and constraint reasoning
112 | - Apply comprehensive testing for validation rules
113 | 
114 | ### Development Workflow
115 | 1. **Pattern implementation**: Follow model patterns and base classes
116 | 2. **API validation**: Ensure field alignment with API documentation
117 | 3. **Quality checks**: Format, lint, type check validation
118 | 4. **Alias mapping**: Verify kebab-case API compatibility
119 | 
120 | ## Tool Integration
121 | 
122 | ### Using Models in Tools
123 | - Import models for parameter validation in tool functions
124 | - Apply model validation to ensure type safety
125 | - Use model instances for payload creation
126 | - Leverage field aliases for API compatibility
127 | 
128 | ### Payload Creation Integration
129 | When working with utilities:
130 | - Use `create_api_payload()` with model instances
131 | - Apply `query_params()` for transforming model data to API parameters
132 | - Handle model validation errors appropriately
133 | - Ensure proper error handling for invalid inputs
134 | 
135 | ### API Client Integration
136 | When working with API client:
137 | - Use models for request parameter validation
138 | - Apply model serialization for API requests
139 | - Handle validation errors before API calls
140 | - Ensure proper type safety throughout request pipeline
141 | 
142 | ## Implementation Workflow
143 | 
144 | ### New Model Development Process
145 | 1. **Define model structure**: Extend `APIRequest` base class
146 | 2. **Add field validation**: Follow API documentation requirements
147 | 3. **Apply aliases**: Use kebab-case aliases for API compatibility
148 | 4. **Create enums**: For API-documented constrained choices
149 | 5. **Test validation**: Cover valid inputs, invalid inputs, edge cases
150 | 6. **Update documentation**: Implementation status tracking
151 | 
152 | ### Quality Validation Checklist
153 | For each model implementation:
154 | - [ ] Model extends `APIRequest` base class with appropriate field aliases
155 | - [ ] Field validation follows API documentation requirements exactly
156 | - [ ] Parameter models created when needed for complex operations
157 | - [ ] Enums defined for API-documented constrained choices
158 | - [ ] Quality checks passed: format, lint, type check
159 | - [ ] Documentation updated: implementation status tracking
160 | - [ ] Tests cover validation scenarios: valid, invalid, edge cases
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/utils/CLAUDE.md:
--------------------------------------------------------------------------------

```markdown
  1 | # CLAUDE.md for utils/
  2 | 
  3 | This file provides guidance about shared utility functions for consistent operations across the Terraform Cloud MCP implementation.
  4 | 
  5 | ## Context Activation
  6 | This guidance activates when:
  7 | - Working in `terraform_cloud_mcp/utils/` directory
  8 | - Creating/editing utility functions (*.py)
  9 | - Implementing shared functionality (decorators, helpers, formatters)
 10 | - Adding error handling or payload creation utilities
 11 | 
 12 | **Companion directories**: tools/ (for usage), models/ (for integration), api/ (for requests)
 13 | 
 14 | ## Utility Architecture
 15 | 
 16 | The utils directory provides common functionality to maintain consistency and reduce code duplication:
 17 | 
 18 | ### Core Utilities
 19 | - **decorators.py**: `handle_api_errors` decorator for consistent error handling
 20 | - **env.py**: Centralized environment variable management (tokens, feature flags)
 21 | - **payload.py**: JSON:API payload creation and relationship management
 22 | - **request.py**: Query parameter transformation for API requests
 23 | - **filters.py**: Response filtering system for token optimization
 24 | 
 25 | ## Implementation Standards
 26 | 
 27 | ### Error Handling Pattern
 28 | - **@handle_api_errors decorator**: Apply to all API functions for consistent error formatting
 29 | - **Error format**: `{"error": "message"}` (never expose sensitive data)
 30 | - **Success preservation**: Decorator preserves successful responses without modification
 31 | 
 32 | ### Environment Management
 33 | - **get_tfc_token()**: Centralized TFC_TOKEN access (never use direct os.getenv)
 34 | - **should_enable_delete_tools()**: Safety control for destructive operations
 35 | - **Centralized access**: All environment variables managed through utils/env.py
 36 | 
 37 | ### Payload Creation
 38 | - **create_api_payload()**: JSON:API compliant payload creation from Pydantic models
 39 | - **add_relationship()**: Standardized relationship management for JSON:API
 40 | - **query_params()**: Pydantic model to API parameter transformation for list/filter operations
 41 | 
 42 | ### Query Parameter Transformation
 43 | The `query_params()` function transforms Pydantic model fields to API parameters using consistent naming conventions:
 44 | - **Pagination**: `page_number` → `page[number]`, `page_size` → `page[size]`
 45 | - **Filters**: `filter_name` → `filter[name]`, `filter_permissions_update` → `filter[permissions][update]`
 46 | - **Search**: `search_term` → `search[term]`, `search_user` → `search[user]`
 47 | - **Query**: `query_email` → `q[email]`, `query_name` → `q[name]`
 48 | - **Direct params**: `q`, `search`, `sort` mapped directly
 49 | 
 50 | Usage pattern for all list operations: See `../tools/workspaces.py:list_workspaces` for the standard query parameter transformation approach.
 51 | 
 52 | ### Parameter Model Integration
 53 | 
 54 | Functions use direct parameters with optional params objects. See `../tools/variables.py:create_workspace_variable` for the pattern of combining direct and optional parameters with request models.
 55 | 
 56 | ## Usage Standards
 57 | 
 58 | ### Core Requirements
 59 | - **Error handling**: Always use `@handle_api_errors` for API functions (never duplicate logic)
 60 | - **Environment access**: Use utility functions instead of direct `os.getenv()` calls
 61 | - **Payload creation**: Use `create_api_payload()` and `add_relationship()` for JSON:API operations
 62 | - **Parameter handling**: Use `query_params()` for all list/filter operations
 63 | - **Response filtering**: Review filter configurations when implementing new tools - check for new fields to filter
 64 | 
 65 | ### Validated Audit-Safe Filtering System
 66 | **✅ FULLY TESTED AND VERIFIED**: All 7 tool categories validated for 100% audit compliance:
 67 | - **User accountability**: `created-at`, `updated-at`, `version-id` always preserved
 68 | - **Security configuration**: All permission and auth fields preserved  
 69 | - **Change tracking**: Status timestamps, source tracking, version data preserved
 70 | - **Operational context**: Status, timing, progress data for monitoring tools
 71 | - **Decision context**: Cost data, assessments, diagnostics for analysis tools
 72 | - **Conservative 5-15% token reduction**: Balanced optimization vs. complete audit capability
 73 | - **Audit-first principle**: When in doubt, preserve the field rather than filter it
 74 | 
 75 | ### Development Guidelines
 76 | - **New utilities**: Place in appropriate module, document with type hints and examples
 77 | - **Consistency**: Maintain established patterns, consistent return types and error formats
 78 | - **Reusability**: Write utilities to be domain-agnostic and broadly applicable
 79 | 
 80 | ## Error Handling Decision Matrix
 81 | 
 82 | ### When to Use Decorator Only
 83 | - Standard CRUD operations with predictable API responses (200, 201, 204, 4xx, 5xx)
 84 | - Most list and get operations without complex parameter validation
 85 | - Tools that don't require business logic validation before API calls
 86 | 
 87 | ### When to Add Custom Logic (WITH Decorator)
 88 | - Parameter validation requiring specific error messages beyond Pydantic
 89 | - API responses needing special status code interpretation
 90 | - Multi-step operations with intermediate error handling needs
 91 | - File operations requiring size/format validation
 92 | 
 93 | ### Error Response Standards
 94 | - **Format**: `{"error": "descriptive message"}` (never expose sensitive data)
 95 | - **Success**: 200/201 return raw API response; 204 returns `{"status": "success", "status_code": 204}`
 96 | - **Consistency**: Always preserve @handle_api_errors decorator even with custom logic
 97 | 
 98 | ## Development Standards
 99 | 
100 | ### Quality Checks
101 | - **Format**: `ruff format .`
102 | - **Lint**: `ruff check .`
103 | - **Type Check**: `mypy .`
104 | - **Test**: `pytest`
105 | 
106 | ### Utility-Specific Requirements
107 | - All functions must include proper error handling and consistent response format
108 | - Apply security guidelines for sensitive data redaction
109 | - Follow established patterns for error decoration and type safety
110 | - Test with comprehensive quality check sequence after utility changes
111 | 
112 | ### Code Style Requirements
113 | - Type hints required for all parameters and return values
114 | - Apply async patterns where appropriate
115 | - Follow security practices for sensitive data handling
116 | - Maintain consistent naming conventions
117 | 
118 | ## Integration Guidelines
119 | 
120 | ### Tool Integration
121 | When utilities are used in tools:
122 | - Apply `@handle_api_errors` decorator to all API functions
123 | - Use `create_api_payload()` for JSON:API compliant requests
124 | - Apply `query_params()` for all list/filter operations
125 | - Use centralized environment variable access
126 | 
127 | ### Model Integration
128 | When utilities work with models:
129 | - Use `create_api_payload()` with Pydantic model instances
130 | - Apply `query_params()` for transforming model data to API parameters
131 | - Handle model validation errors appropriately
132 | - Ensure proper type safety throughout
133 | 
134 | ### API Client Integration
135 | When utilities work with API client:
136 | - Use utilities for consistent request formatting
137 | - Apply error handling decorators
138 | - Use centralized token management
139 | - Ensure proper response handling
140 | 
141 | ## Implementation Workflow
142 | 
143 | ### New Utility Development Process
144 | 1. **Define function signature**: Include proper type hints
145 | 2. **Implement core logic**: Follow established patterns
146 | 3. **Add error handling**: Apply consistent response formats
147 | 4. **Test thoroughly**: Cover success, error, and edge cases
148 | 5. **Document function**: Include usage examples and cross-references
149 | 6. **Update status**: Implementation tracking
150 | 
151 | ### Quality Validation Checklist
152 | For each utility implementation:
153 | - [ ] Function includes proper error handling and consistent response format
154 | - [ ] Type hints provided for all parameters and return values
155 | - [ ] Documentation includes usage examples and patterns
156 | - [ ] Security guidelines followed for sensitive data handling
157 | - [ ] Quality checks passed: format, lint, type check
158 | - [ ] Tests cover all scenarios: success, error, edge cases
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/api/__init__.py:
--------------------------------------------------------------------------------

```python
1 | """API client module for Terraform Cloud MCP"""
2 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/configs/__init__.py:
--------------------------------------------------------------------------------

```python
1 | """Configuration modules for Terraform Cloud MCP."""
2 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/__init__.py:
--------------------------------------------------------------------------------

```python
1 | """Terraform Cloud MCP - A MCP server for Terraform Cloud"""
2 | 
3 | from .server import main
4 | import importlib.metadata
5 | 
6 | __version__ = importlib.metadata.version("terraform-cloud-mcp")
7 | 
8 | __all__ = ["main"]
9 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/utils/__init__.py:
--------------------------------------------------------------------------------

```python
1 | """Utility functions for Terraform Cloud MCP"""
2 | 
3 | from .payload import create_api_payload, add_relationship
4 | from .request import query_params
5 | 
6 | __all__ = ["create_api_payload", "add_relationship", "query_params"]
7 | 
```

--------------------------------------------------------------------------------
/mypy.ini:
--------------------------------------------------------------------------------

```
 1 | [mypy]
 2 | #disable_error_code = no-any-return
 3 | python_version = 3.12
 4 | warn_return_any = True
 5 | warn_unused_configs = True
 6 | ignore_missing_imports = True
 7 | namespace_packages = True
 8 | explicit_package_bases = True
 9 | 
10 | # These modules will be strictly typed
11 | [mypy.api.*]
12 | disallow_untyped_defs = True
13 | 
14 | [mypy.models.*]
15 | disallow_untyped_defs = True
16 | 
17 | [mypy.tools.*]
18 | disallow_untyped_defs = True
19 | 
20 | [mypy.utils.*]
21 | disallow_untyped_defs = True
22 | 
23 | [mypy.server]
24 | disallow_untyped_defs = True
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/tools/__init__.py:
--------------------------------------------------------------------------------

```python
 1 | """MCP tools for Terraform Cloud"""
 2 | 
 3 | # Import tools for easier access
 4 | from . import account
 5 | from . import applies
 6 | from . import assessment_results
 7 | from . import cost_estimates
 8 | from . import organizations
 9 | from . import plans
10 | from . import projects
11 | from . import runs
12 | from . import state_versions
13 | from . import state_version_outputs
14 | from . import variables
15 | from . import workspaces
16 | 
17 | __all__ = [
18 |     "account",
19 |     "applies",
20 |     "assessment_results",
21 |     "cost_estimates",
22 |     "organizations",
23 |     "plans",
24 |     "projects",
25 |     "runs",
26 |     "state_versions",
27 |     "state_version_outputs",
28 |     "variables",
29 |     "workspaces",
30 | ]
31 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/utils/decorators.py:
--------------------------------------------------------------------------------

```python
 1 | """Decorators and utility functions for Terraform Cloud MCP"""
 2 | 
 3 | from functools import wraps
 4 | from typing import Callable, Any, Dict, Awaitable, cast
 5 | 
 6 | 
 7 | def handle_api_errors(
 8 |     func: Callable[..., Awaitable[Dict[str, Any]]],
 9 | ) -> Callable[..., Awaitable[Dict[str, Any]]]:
10 |     """Decorator to handle API errors consistently."""
11 | 
12 |     @wraps(func)
13 |     async def wrapper(*args, **kwargs) -> Dict[str, Any]:
14 |         try:
15 |             result = await func(*args, **kwargs)
16 |             # Cast ensures type safety when func might return subclass of Dict
17 |             return cast(Dict[str, Any], result)
18 |         except ValueError as e:
19 |             return {"error": str(e)}
20 | 
21 |     return wrapper
22 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/account.py:
--------------------------------------------------------------------------------

```python
 1 | """Account models for Terraform Cloud API
 2 | 
 3 | This module contains models for Terraform Cloud account-related requests.
 4 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/account
 5 | """
 6 | 
 7 | from .base import APIRequest
 8 | 
 9 | 
10 | class AccountDetailsRequest(APIRequest):
11 |     """Request model for getting account details.
12 | 
13 |     This model is used for the GET /account/details endpoint which requires no parameters.
14 |     The endpoint returns information about the currently authenticated user or service account.
15 | 
16 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/account#show-account-details
17 | 
18 |     Note:
19 |         For team and organization tokens, this endpoint returns information about
20 |         a synthetic "service user" account associated with the token.
21 | 
22 |     See:
23 |         docs/models/account.md for reference
24 |     """
25 | 
26 |     pass  # No parameters needed for this endpoint
27 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/utils/env.py:
--------------------------------------------------------------------------------

```python
 1 | """Environment variable management for Terraform Cloud MCP"""
 2 | 
 3 | import os
 4 | from typing import Optional
 5 | 
 6 | 
 7 | def get_tfc_token() -> Optional[str]:
 8 |     """Get Terraform Cloud API token from environment."""
 9 |     return os.getenv("TFC_TOKEN")
10 | 
11 | 
12 | def get_tfc_address() -> str:
13 |     """Get Terraform Cloud/Enterprise address from environment, with default of app.terraform.io."""
14 |     return os.getenv("TFC_ADDRESS", "https://app.terraform.io")
15 | 
16 | 
17 | def should_enable_delete_tools() -> bool:
18 |     """Check if delete tools should be enabled."""
19 |     env_value = os.getenv("ENABLE_DELETE_TOOLS", "false").lower().strip()
20 |     return env_value in ("true", "1", "yes", "on")
21 | 
22 | 
23 | def should_return_raw_response() -> bool:
24 |     """Check if raw API responses should be returned instead of filtered responses."""
25 |     env_value = os.getenv("ENABLE_RAW_RESPONSE", "false").lower().strip()
26 |     return env_value in ("true", "1", "yes", "on")
27 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/utils/payload.py:
--------------------------------------------------------------------------------

```python
 1 | """JSON:API payload utilities for Terraform Cloud MCP."""
 2 | 
 3 | from typing import Dict, Optional, Set, Any
 4 | from pydantic import BaseModel
 5 | 
 6 | 
 7 | def create_api_payload(
 8 |     resource_type: str,
 9 |     model: BaseModel,
10 |     exclude_fields: Optional[Set[str]] = None,
11 | ) -> Dict[str, Any]:
12 |     """Creates a JSON:API compliant payload from a Pydantic model."""
13 |     attributes = model.model_dump(
14 |         by_alias=True,
15 |         exclude=exclude_fields or set(),
16 |         exclude_none=True,
17 |     )
18 | 
19 |     return {"data": {"type": resource_type, "attributes": attributes}}
20 | 
21 | 
22 | def add_relationship(
23 |     payload: Dict[str, Any], relation_name: str, resource_type: str, resource_id: str
24 | ) -> Dict[str, Any]:
25 |     """Adds a relationship to a JSON:API payload."""
26 |     if "relationships" not in payload["data"]:
27 |         payload["data"]["relationships"] = {}
28 | 
29 |     payload["data"]["relationships"][relation_name] = {
30 |         "data": {"type": resource_type, "id": resource_id}
31 |     }
32 | 
33 |     return payload
34 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/tools/account.py:
--------------------------------------------------------------------------------

```python
 1 | """Account management tools for Terraform Cloud API
 2 | 
 3 | This module implements the /account endpoints of the Terraform Cloud API.
 4 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/account
 5 | """
 6 | 
 7 | from ..api.client import api_request
 8 | from ..utils.decorators import handle_api_errors
 9 | from ..models.base import APIResponse
10 | 
11 | 
12 | @handle_api_errors
13 | async def get_account_details() -> APIResponse:
14 |     """Get account details for a Terraform Cloud API token
15 | 
16 |     This endpoint shows information about the currently authenticated user or service account,
17 |     useful for verifying identity, retrieving email address, and checking authentication status.
18 |     It returns the same type of object as the Users API, but also includes an email address,
19 |     which is hidden when viewing info about other users.
20 | 
21 |     API endpoint: GET /account/details
22 | 
23 |     Returns:
24 |         Raw API response with account information from Terraform Cloud
25 |         including user ID, username, email address, and authentication status
26 | 
27 |     See:
28 |         docs/tools/account.md for reference documentation
29 |     """
30 |     return await api_request("account/details")
31 | 
```

--------------------------------------------------------------------------------
/pyproject.toml:
--------------------------------------------------------------------------------

```toml
 1 | [build-system]
 2 | requires = ["hatchling"]
 3 | build-backend = "hatchling.build"
 4 | 
 5 | [project]
 6 | name = "terraform-cloud-mcp"
 7 | version = "0.8.17"
 8 | description = "A Model Context Protocol (MCP) server that integrates Claude with the Terraform Cloud API, allowing Claude to manage your Terraform infrastructure through natural conversation."
 9 | readme = "README.md"
10 | requires-python = ">=3.12"
11 | dependencies = [
12 |     "dotenv>=0.9.9",
13 |     "httpx>=0.28.1",
14 |     "fastmcp>=2.9.1",
15 | ]
16 | packages = ["terraform_cloud_mcp", "api", "models", "tools", "utils"]
17 | 
18 | [project.scripts]
19 | terraform-cloud-mcp = "terraform_cloud_mcp.server:main"
20 | 
21 | [tool.hatch.metadata]
22 | allow-direct-references = true
23 | 
24 | [tool.mypy]
25 | python_version = "3.12"
26 | warn_return_any = true
27 | warn_unused_configs = true
28 | disallow_untyped_defs = true
29 | disallow_incomplete_defs = true
30 | check_untyped_defs = true
31 | disallow_untyped_decorators = true
32 | no_implicit_optional = true
33 | strict_optional = true
34 | namespace_packages = true
35 | explicit_package_bases = true
36 | ignore_missing_imports = true
37 | 
38 | # Focus only on individual modules
39 | [[tool.mypy.overrides]]
40 | module = ["api.*", "models.*", "tools.*", "utils.*"]
41 | disallow_untyped_defs = true
42 | 
43 | [[tool.mypy.overrides]]
44 | module = ["server"]
45 | disallow_untyped_defs = true
46 | 
47 | [[tool.mypy.overrides]]
48 | module = ["mcp.*", "dotenv.*", "httpx.*"]
49 | ignore_missing_imports = true
50 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/tools/cost_estimates.py:
--------------------------------------------------------------------------------

```python
 1 | """Terraform Cloud cost estimates management tools.
 2 | 
 3 | This module provides tools for working with cost estimates in Terraform Cloud.
 4 | It includes functions to retrieve cost estimate details.
 5 | 
 6 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/cost-estimates
 7 | """
 8 | 
 9 | from ..api.client import api_request
10 | from ..models.base import APIResponse
11 | from ..models.cost_estimates import CostEstimateRequest
12 | from ..utils.decorators import handle_api_errors
13 | 
14 | 
15 | @handle_api_errors
16 | async def get_cost_estimate_details(cost_estimate_id: str) -> APIResponse:
17 |     """Get details for a specific cost estimate.
18 | 
19 |     Retrieves comprehensive information about a cost estimate including its current status,
20 |     resource counts, monthly cost estimations, and relationship to other resources.
21 | 
22 |     API endpoint: GET /cost-estimates/{cost_estimate_id}
23 | 
24 |     Args:
25 |         cost_estimate_id: The ID of the cost estimate to retrieve details for (format: "ce-xxxxxxxx")
26 | 
27 |     Returns:
28 |         Cost estimate details including status, timestamps, resource counts,
29 |         and monthly cost estimations
30 | 
31 |     Note:
32 |         There is no endpoint to list cost estimates. You can find the ID for a cost estimate
33 |         in the `relationships.cost-estimate` property of a run object.
34 | 
35 |     See:
36 |         docs/tools/cost_estimate.md for reference documentation
37 |     """
38 |     # Validate parameters
39 |     params = CostEstimateRequest(cost_estimate_id=cost_estimate_id)
40 | 
41 |     # Make API request
42 |     return await api_request(f"cost-estimates/{params.cost_estimate_id}")
43 | 
```

--------------------------------------------------------------------------------
/docs/tools/account.md:
--------------------------------------------------------------------------------

```markdown
 1 | # Account Tools
 2 | 
 3 | This module provides tools for retrieving information about the currently authenticated Terraform Cloud account.
 4 | 
 5 | ## Overview
 6 | 
 7 | Account tools allow you to access details about the currently authenticated user or service account. This is useful for retrieving account information, verifying authentication status, and checking permissions.
 8 | 
 9 | ## API Reference
10 | 
11 | These tools interact with the Terraform Cloud Account API:
12 | - [Account API Documentation](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/account)
13 | 
14 | ## Tools Reference
15 | 
16 | ### get_account_details
17 | 
18 | **Function:** `get_account_details() -> Dict[str, Any]`
19 | 
20 | **Description:** Retrieves information about the currently authenticated user or service account.
21 | 
22 | **Parameters:** None - uses the authentication from the API token environment variable.
23 | 
24 | **Returns:** JSON response containing comprehensive account details including:
25 | - User ID and username
26 | - Email address
27 | - Two-factor authentication status
28 | - Service account status
29 | - User permissions and attributes
30 | 
31 | **Notes:**
32 | - This endpoint returns additional information (email address) beyond what is returned by the standard Users API
33 | - Useful for determining if you're authenticated as a user or a service account
34 | - Can be used to verify 2FA compliance and permissions
35 | - Returns the same type of object as the Users API, but with additional information
36 | 
37 | **Common Error Scenarios:**
38 | 
39 | | Error | Cause | Solution |
40 | |-------|-------|----------|
41 | | 401 | Invalid or expired API token | Generate a new API token in Terraform Cloud settings |
42 | | 403 | Token lacks sufficient permissions | Ensure the token has proper access rights |
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/state_version_outputs.py:
--------------------------------------------------------------------------------

```python
 1 | """State version output models for Terraform Cloud API
 2 | 
 3 | This module contains models for Terraform Cloud state version output-related requests.
 4 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/state-version-outputs
 5 | """
 6 | 
 7 | from typing import Optional
 8 | 
 9 | from pydantic import Field
10 | 
11 | from .base import APIRequest
12 | 
13 | 
14 | class StateVersionOutputListRequest(APIRequest):
15 |     """Request parameters for listing state version outputs.
16 | 
17 |     Defines the parameters for the state version outputs listing API including pagination.
18 | 
19 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/state-version-outputs#list-state-version-outputs
20 | 
21 |     See:
22 |         docs/models/state_version_outputs.md for reference
23 |     """
24 | 
25 |     state_version_id: str = Field(
26 |         ...,
27 |         description="The ID of the state version to list outputs for",
28 |         pattern=r"^sv-[a-zA-Z0-9]{16}$",  # Standard state version ID pattern
29 |     )
30 |     page_number: Optional[int] = Field(
31 |         1,
32 |         ge=1,
33 |         description="Page number to fetch",
34 |     )
35 |     page_size: Optional[int] = Field(
36 |         20,
37 |         ge=1,
38 |         le=100,
39 |         description="Number of results per page",
40 |     )
41 | 
42 | 
43 | class StateVersionOutputRequest(APIRequest):
44 |     """Request model for retrieving a specific state version output.
45 | 
46 |     Used to validate the state version output ID parameter for API requests.
47 | 
48 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/state-version-outputs#show-a-state-version-output
49 | 
50 |     See:
51 |         docs/models/state_version_outputs.md for reference
52 |     """
53 | 
54 |     state_version_output_id: str = Field(
55 |         ...,
56 |         description="The ID of the state version output to retrieve",
57 |         pattern=r"^wsout-[a-zA-Z0-9]{16}$",  # Standard state version output ID pattern
58 |     )
59 | 
60 | 
61 | # Response handling is implemented through raw dictionaries
62 | 
```

--------------------------------------------------------------------------------
/docs/tools/cost_estimate.md:
--------------------------------------------------------------------------------

```markdown
 1 | # Cost Estimate Tools
 2 | 
 3 | The cost estimate tools module provides functions for working with cost estimates in Terraform Cloud.
 4 | 
 5 | ## Overview
 6 | 
 7 | Cost estimates provide insights into the financial impact of infrastructure changes, allowing you to understand the cost implications of your Terraform changes before applying them. These tools allow you to retrieve and analyze cost estimate details.
 8 | 
 9 | ## API Reference
10 | 
11 | These tools interact with the Terraform Cloud Cost Estimation API:
12 | - [Cost Estimation API Documentation](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/cost-estimates)
13 | - [Cost Estimation Concepts](https://developer.hashicorp.com/terraform/cloud-docs/cost-estimation)
14 | 
15 | ## Tools Reference
16 | 
17 | ### get_cost_estimate_details
18 | 
19 | **Function:** `get_cost_estimate_details(cost_estimate_id: str) -> Dict[str, Any]`
20 | 
21 | **Description:** Retrieves detailed information about a specific cost estimate by ID.
22 | 
23 | **Parameters:**
24 | - `cost_estimate_id` (str): The ID of the cost estimate (format: "ce-xxxxxxxx")
25 | 
26 | **Returns:** JSON response containing comprehensive cost estimate details including:
27 | - Status (pending, queued, running, errored, canceled, finished, unreachable)
28 | - Cost projections (prior monthly cost, proposed monthly cost, delta monthly cost)
29 | - Resource counts (total, matched, unmatched resources)
30 | - Execution timestamps
31 | - Related workspaces and runs
32 | 
33 | **Notes:**
34 | - There is no endpoint to list cost estimates directly
35 | - Cost estimate IDs are typically found in the `relationships.cost-estimate` property of run objects
36 | - Requires "read" permission for the associated workspace
37 | - You can extract the cost estimate ID from a run by accessing:
38 |   ```
39 |   relationships = run_result.get("data", {}).get("relationships", {})
40 |   cost_estimate_data = relationships.get("cost-estimate", {}).get("data", {})
41 |   cost_estimate_id = cost_estimate_data.get("id")
42 |   ```
43 | 
44 | **Common Error Scenarios:**
45 | 
46 | | Error | Cause | Solution |
47 | |-------|-------|----------|
48 | | 404 | Cost estimate not found | Verify the ID exists and you have proper permissions |
49 | | 422 | Invalid cost estimate ID format | Ensure the ID matches pattern "ce-xxxxxxxx" |
50 | | 403 | Insufficient permissions | Verify your API token has proper access |
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/assessment_results.py:
--------------------------------------------------------------------------------

```python
 1 | """Assessment result models for Terraform Cloud API.
 2 | 
 3 | This module contains models for Terraform Cloud assessment result-related requests.
 4 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/assessment-results
 5 | """
 6 | 
 7 | from enum import Enum
 8 | 
 9 | from pydantic import Field
10 | 
11 | from .base import APIRequest
12 | 
13 | 
14 | class AssessmentResultStatus(str, Enum):
15 |     """Status options for assessment results in Terraform Cloud.
16 | 
17 |     Defines the various states an assessment result can be in during its lifecycle:
18 |     - PENDING: Assessment has not yet started
19 |     - QUEUED: Assessment is queued for execution
20 |     - RUNNING: Assessment is currently running
21 |     - ERRORED: Assessment has encountered an error
22 |     - CANCELED: Assessment was canceled
23 |     - FINISHED: Assessment has completed successfully
24 | 
25 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/assessment-results
26 | 
27 |     See:
28 |         docs/models/assessment_result.md for reference
29 |     """
30 | 
31 |     PENDING = "pending"
32 |     QUEUED = "queued"
33 |     RUNNING = "running"
34 |     ERRORED = "errored"
35 |     CANCELED = "canceled"
36 |     FINISHED = "finished"
37 | 
38 | 
39 | class AssessmentResultRequest(APIRequest):
40 |     """Request model for retrieving assessment result details.
41 | 
42 |     Used to validate the assessment result ID parameter for API requests.
43 | 
44 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/assessment-results#show-assessment-result
45 | 
46 |     See:
47 |         docs/models/assessment_result.md for reference
48 |     """
49 | 
50 |     assessment_result_id: str = Field(
51 |         ...,
52 |         # No alias needed as field name matches API parameter
53 |         description="The ID of the assessment result to retrieve",
54 |         pattern=r"^asmtres-[a-zA-Z0-9]{8,}$",  # Standard assessment result ID pattern
55 |     )
56 | 
57 | 
58 | class AssessmentOutputRequest(AssessmentResultRequest):
59 |     """Request model for retrieving assessment result outputs.
60 | 
61 |     Extends the base AssessmentResultRequest for specialized outputs like
62 |     JSON plan, schema, and log output.
63 | 
64 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/assessment-results#retrieve-the-json-output-from-the-assessment-execution
65 | 
66 |     See:
67 |         docs/models/assessment_result.md for reference
68 |     """
69 | 
70 |     pass  # Uses the same validation as the parent class
71 | 
72 | 
73 | # Response handling is implemented through raw dictionaries
74 | 
```

--------------------------------------------------------------------------------
/docs/conversations/account.md:
--------------------------------------------------------------------------------

```markdown
 1 | # Terraform Cloud Account Management Conversation Examples
 2 | 
 3 | This document shows example conversations between a user and Claude when using the account management tools.
 4 | 
 5 | ## Getting Account Details
 6 | 
 7 | ```
 8 | User: What's my account information in Terraform Cloud?
 9 | 
10 | Claude: I'll check your account details in Terraform Cloud.
11 | 
12 | [Claude uses get_account_details tool]
13 | 
14 | Based on your Terraform Cloud account details:
15 | 
16 | Your username is "jsmith"
17 | Your email is "[email protected]"
18 | You have a "regular" user account (not a service account)
19 | Your account was created on February 12, 2023
20 | You have two-factor authentication enabled
21 | You're associated with the "acme-corp" organization
22 | 
23 | Would you like to see more specific information about your account?
24 | ```
25 | 
26 | ## Diagnosing Authentication Issues
27 | 
28 | ```
29 | User: I can't seem to access any workspaces. What's wrong?
30 | 
31 | Claude: Let me check your account details to see if there might be an authentication issue.
32 | 
33 | [Claude uses get_account_details tool]
34 | 
35 | I've checked your Terraform Cloud account, and it looks like your token doesn't have access to any workspaces. This could be due to one of these issues:
36 | 
37 | 1. Your token has limited permissions - it may be scoped only to certain resources
38 | 2. You might not be a member of any organizations or teams that have workspace access
39 | 3. Your token might have expired or been revoked
40 | 
41 | Your token identifies as belonging to a service account, not a regular user account. Service accounts often have more restricted permissions.
42 | 
43 | Would you like me to help you:
44 | 1. Check which organizations you have access to?
45 | 2. Verify if your token has the correct permissions?
46 | 3. Get instructions for creating a new token with broader access?
47 | ```
48 | 
49 | ## Features and Enterprise Plan Information
50 | 
51 | ```
52 | User: What features does my Terraform Cloud account have?
53 | 
54 | Claude: I'll check what features your Terraform Cloud account has access to.
55 | 
56 | [Claude uses get_account_details tool]
57 | 
58 | Based on your Terraform Cloud account information:
59 | 
60 | You're on the Business tier plan with the following features:
61 | - Private module registry
62 | - Team management
63 | - Sentinel policy enforcement 
64 | - Run tasks
65 | - Agents for private infrastructure
66 | - Cost estimation
67 | - SSO with SAML
68 | 
69 | Your organization ("hashicorp-demo") has the following limits:
70 | - Up to 500 users
71 | - Unlimited private modules
72 | - Unlimited workspaces
73 | - Up to 50 concurrent runs
74 | 
75 | Is there a specific feature you're interested in learning more about?
76 | ```
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/cost_estimates.py:
--------------------------------------------------------------------------------

```python
 1 | """Cost estimate models for Terraform Cloud API
 2 | 
 3 | This module contains models for Terraform Cloud cost estimate-related requests.
 4 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/cost-estimates
 5 | """
 6 | 
 7 | from enum import Enum
 8 | from typing import Optional
 9 | 
10 | from pydantic import Field
11 | 
12 | from .base import APIRequest
13 | 
14 | 
15 | class CostEstimateStatus(str, Enum):
16 |     """Status options for cost estimates in Terraform Cloud.
17 | 
18 |     Defines the various states a cost estimate can be in during its lifecycle:
19 |     - PENDING: Cost estimate has not yet started
20 |     - QUEUED: Cost estimate is queued for execution
21 |     - RUNNING: Cost estimate is currently running
22 |     - ERRORED: Cost estimate has encountered an error
23 |     - CANCELED: Cost estimate was canceled
24 |     - FINISHED: Cost estimate has completed successfully
25 |     - UNREACHABLE: Cost estimate is in an unreachable state
26 | 
27 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/cost-estimates
28 | 
29 |     See:
30 |         docs/models/cost_estimate.md for reference
31 |     """
32 | 
33 |     PENDING = "pending"
34 |     QUEUED = "queued"
35 |     RUNNING = "running"
36 |     ERRORED = "errored"
37 |     CANCELED = "canceled"
38 |     FINISHED = "finished"
39 |     UNREACHABLE = "unreachable"
40 | 
41 | 
42 | class StatusTimestamps(APIRequest):
43 |     """Model for cost estimate execution timestamps.
44 | 
45 |     Captures the timestamps for various stages in a cost estimate's lifecycle.
46 | 
47 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/cost-estimates
48 | 
49 |     See:
50 |         docs/models/cost_estimate.md for reference
51 |     """
52 | 
53 |     queued_at: Optional[str] = Field(
54 |         None,
55 |         alias="queued-at",
56 |         description="When the cost estimate was queued",
57 |     )
58 |     finished_at: Optional[str] = Field(
59 |         None,
60 |         alias="finished-at",
61 |         description="When the cost estimate execution completed",
62 |     )
63 | 
64 | 
65 | class CostEstimateRequest(APIRequest):
66 |     """Request model for retrieving a cost estimate.
67 | 
68 |     Used to validate the cost estimate ID parameter for API requests.
69 | 
70 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/cost-estimates#show-a-cost-estimate
71 | 
72 |     See:
73 |         docs/models/cost_estimate.md for reference
74 |     """
75 | 
76 |     cost_estimate_id: str = Field(
77 |         ...,
78 |         # No alias needed as field name matches API parameter
79 |         description="The ID of the cost estimate to retrieve",
80 |         pattern=r"^ce-[a-zA-Z0-9]{16}$",  # Standard cost estimate ID pattern
81 |     )
82 | 
83 | 
84 | # Response handling is implemented through raw dictionaries
85 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/utils/request.py:
--------------------------------------------------------------------------------

```python
 1 | """Request utilities for Terraform Cloud MCP."""
 2 | 
 3 | from typing import Dict, Any
 4 | from pydantic import BaseModel
 5 | 
 6 | 
 7 | def query_params(model: BaseModel) -> Dict[str, Any]:
 8 |     """Transform Pydantic model fields to API parameters using naming conventions."""
 9 |     params = {}
10 |     routing_fields = {
11 |         "organization",
12 |         "workspace_name",
13 |         "workspace_id",
14 |         "run_id",
15 |         "plan_id",
16 |         "apply_id",
17 |         "project_id",
18 |     }
19 | 
20 |     # Use model_dump for reliable field access
21 |     model_dict = model.model_dump(exclude_none=True)
22 | 
23 |     for name, value in model_dict.items():
24 |         # Skip routing fields that aren't query parameters
25 |         if name in routing_fields:
26 |             continue
27 | 
28 |         # Pagination parameters
29 |         if name.startswith("page_"):
30 |             field_name = name.replace("page_", "")
31 |             params[f"page[{field_name}]"] = str(value)
32 | 
33 |         # Filter parameters
34 |         elif name.startswith("filter_"):
35 |             # Skip empty string filters
36 |             if value == "":
37 |                 continue
38 | 
39 |             # Handle nested filters (workspace and organization for state versions)
40 |             if name == "filter_workspace_name":
41 |                 params["filter[workspace][name]"] = str(value)
42 |             elif name == "filter_organization_name":
43 |                 params["filter[organization][name]"] = str(value)
44 |             # Handle two-level filters (permissions)
45 |             elif "_permissions_" in name:
46 |                 parts = name.replace("filter_permissions_", "").split("_")
47 |                 field_name = "-".join(parts)
48 |                 params[f"filter[permissions][{field_name}]"] = (
49 |                     "true" if value is True else str(value)
50 |                 )
51 |             else:
52 |                 field_name = name.replace("filter_", "").replace("_", "-")
53 |                 params[f"filter[{field_name}]"] = (
54 |                     "true" if value is True else str(value)
55 |                 )
56 | 
57 |         # Search parameters
58 |         elif name.startswith("search_"):
59 |             if value not in ("", None):
60 |                 field_name = name.replace("search_", "")
61 |                 params[f"search[{field_name}]"] = str(value)
62 | 
63 |         # Organization query parameters
64 |         elif name.startswith("query_"):
65 |             if value not in ("", None):
66 |                 field_name = name.replace("query_", "")
67 |                 params[f"q[{field_name}]"] = str(value)
68 | 
69 |         # Direct parameters
70 |         elif name in ("q", "search", "sort"):
71 |             # Only add non-empty string parameters
72 |             if value not in ("", None):
73 |                 params[name] = str(value)
74 | 
75 |     return params
76 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/tools/state_version_outputs.py:
--------------------------------------------------------------------------------

```python
 1 | """Terraform Cloud state version outputs management tools.
 2 | 
 3 | This module provides tools for working with state version outputs in Terraform Cloud.
 4 | It includes functions to retrieve and list state version outputs.
 5 | 
 6 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/state-version-outputs
 7 | """
 8 | 
 9 | from ..api.client import api_request
10 | from ..models.base import APIResponse
11 | from ..models.state_version_outputs import (
12 |     StateVersionOutputListRequest,
13 |     StateVersionOutputRequest,
14 | )
15 | from ..utils.decorators import handle_api_errors
16 | from ..utils.request import query_params
17 | 
18 | 
19 | @handle_api_errors
20 | async def list_state_version_outputs(
21 |     state_version_id: str, page_number: int = 1, page_size: int = 20
22 | ) -> APIResponse:
23 |     """List outputs for a state version.
24 | 
25 |     Retrieves a paginated list of all outputs for a specific state version.
26 |     These outputs include name, value, and sensitivity information.
27 | 
28 |     API endpoint: GET /state-versions/:state_version_id/outputs
29 | 
30 |     Args:
31 |         state_version_id: The ID of the state version (format: "sv-xxxxxxxx")
32 |         page_number: The page number to return (default: 1)
33 |         page_size: The number of items per page (default: 20, max: 100)
34 | 
35 |     Returns:
36 |         Paginated list of state version outputs with name, value, and sensitivity information
37 | 
38 |     See:
39 |         docs/tools/state_version_outputs.md for reference documentation
40 |     """
41 |     # Validate parameters
42 |     params = StateVersionOutputListRequest(
43 |         state_version_id=state_version_id,
44 |         page_number=page_number,
45 |         page_size=page_size,
46 |     )
47 | 
48 |     # Build query parameters using utility function
49 |     query = query_params(params)
50 | 
51 |     # Make API request
52 |     return await api_request(
53 |         f"state-versions/{params.state_version_id}/outputs", params=query
54 |     )
55 | 
56 | 
57 | @handle_api_errors
58 | async def get_state_version_output(state_version_output_id: str) -> APIResponse:
59 |     """Get details for a specific state version output.
60 | 
61 |     Retrieves comprehensive information about a state version output including
62 |     its name, value, type, and sensitivity information.
63 | 
64 |     API endpoint: GET /state-version-outputs/:state_version_output_id
65 | 
66 |     Args:
67 |         state_version_output_id: The ID of the state version output (format: "wsout-xxxxxxxx")
68 | 
69 |     Returns:
70 |         State version output details including name, value, type, and sensitivity information
71 | 
72 |     See:
73 |         docs/tools/state_version_outputs.md for reference documentation
74 |     """
75 |     # Validate parameters
76 |     params = StateVersionOutputRequest(state_version_output_id=state_version_output_id)
77 | 
78 |     # Make API request
79 |     return await api_request(f"state-version-outputs/{params.state_version_output_id}")
80 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/base.py:
--------------------------------------------------------------------------------

```python
 1 | """Base models for Terraform Cloud MCP.
 2 | 
 3 | This module defines base models for Terraform Cloud API requests.
 4 | We validate requests using Pydantic models but do not validate responses.
 5 | Response structures are documented in comments for reference only.
 6 | 
 7 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs
 8 | """
 9 | 
10 | from enum import Enum
11 | from typing import Any, Dict, TypeVar
12 | from pydantic import BaseModel, ConfigDict
13 | 
14 | 
15 | class BaseModelConfig(BaseModel):
16 |     """Base model configuration for all models in the project.
17 | 
18 |     Provides common configuration settings for Pydantic models including:
19 |     - populate_by_name: Allow populating models by alias name or field name
20 |     - use_enum_values: Use string values from enums instead of enum objects
21 |     - extra: Ignore extra fields in input data
22 | 
23 |     See:
24 |         docs/models/base.md for reference
25 |     """
26 | 
27 |     model_config = ConfigDict(
28 |         populate_by_name=True,
29 |         use_enum_values=True,
30 |         extra="ignore",
31 |     )
32 | 
33 | 
34 | class APIRequest(BaseModelConfig):
35 |     """Base model for API requests.
36 | 
37 |     All API request models should inherit from this class to ensure
38 |     consistent configuration and behavior. It inherits settings from
39 |     BaseModelConfig.
40 | 
41 |     Note:
42 |         This class provides the foundation for all API requests and inherits
43 |         model configuration from BaseModelConfig.
44 | 
45 |     See:
46 |         docs/models/base.md for reference
47 |     """
48 | 
49 |     pass
50 | 
51 | 
52 | # Common enums used across multiple modules
53 | class ExecutionMode(str, Enum):
54 |     """Execution mode options for workspaces and organizations.
55 | 
56 |     Defines how Terraform operations are executed:
57 |     - REMOTE: Terraform runs on Terraform Cloud's infrastructure
58 |     - LOCAL: Terraform runs on your local machine
59 |     - AGENT: Terraform runs on your own infrastructure using an agent
60 | 
61 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/workspaces/settings#execution-mode
62 | 
63 |     See:
64 |         docs/models/workspace.md for reference
65 |     """
66 | 
67 |     REMOTE = "remote"
68 |     LOCAL = "local"
69 |     AGENT = "agent"
70 | 
71 | 
72 | class CollaboratorAuthPolicy(str, Enum):
73 |     """Authentication policy options for organization collaborators.
74 | 
75 |     Defines the authentication requirements for organization members:
76 |     - PASSWORD: Password-only authentication is allowed
77 |     - TWO_FACTOR_MANDATORY: Two-factor authentication is required for all users
78 | 
79 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/users-teams-organizations/organizations#authentication
80 | 
81 |     See:
82 |         docs/models/organization.md for reference
83 |     """
84 | 
85 |     PASSWORD = "password"
86 |     TWO_FACTOR_MANDATORY = "two_factor_mandatory"
87 | 
88 | 
89 | # Response type for all API calls - just a dictionary with no validation
90 | APIResponse = Dict[str, Any]
91 | 
92 | 
93 | # Type variable for API requests to use with generics
94 | ReqT = TypeVar("ReqT", bound=APIRequest)
95 | 
```

--------------------------------------------------------------------------------
/docs/models/state_version_outputs.md:
--------------------------------------------------------------------------------

```markdown
 1 | # State Version Outputs Models
 2 | 
 3 | This document describes the data models used for state version outputs operations in Terraform Cloud.
 4 | 
 5 | ## Overview
 6 | 
 7 | State version outputs models provide structure and validation for interacting with the Terraform Cloud State Version Outputs API. These models handle the output values from Terraform state files, including name, value, type, and sensitivity information.
 8 | 
 9 | ## Models Reference
10 | 
11 | ### StateVersionOutputListRequest
12 | 
13 | **Type:** Request Validation Model
14 | 
15 | **Description:** Used to validate parameters for listing outputs for a specific state version.
16 | 
17 | **Fields:**
18 | - `state_version_id` (string, required): The ID of the state version to list outputs for
19 |   - Format: Must match pattern "sv-[a-zA-Z0-9]{16}"
20 |   - Example: "sv-BPvFFrYCqRV6qVBK"
21 | - `page_number` (integer, optional): Page number to fetch (default: 1, minimum: 1)
22 | - `page_size` (integer, optional): Number of results per page (default: 20, max: 100)
23 | 
24 | **Validation Rules:**
25 | - State version ID must start with "sv-" prefix
26 | - Must contain exactly 16 alphanumeric characters after the prefix
27 | - Page number must be positive integer
28 | - Page size must be between 1 and 100
29 | 
30 | ### StateVersionOutputRequest
31 | 
32 | **Type:** Request Validation Model
33 | 
34 | **Description:** Used to validate state version output ID parameters in API requests.
35 | 
36 | **Fields:**
37 | - `state_version_output_id` (string, required): The ID of the state version output to retrieve
38 |   - Format: Must match pattern "wsout-[a-zA-Z0-9]{16}"
39 |   - Example: "wsout-BPvFFrYCqRV6qVBK"
40 | 
41 | **Validation Rules:**
42 | - State version output ID must start with "wsout-" prefix
43 | - Must contain exactly 16 alphanumeric characters after the prefix
44 | 
45 | **Used by:**
46 | - `get_state_version_output` tool function to validate the output ID format before making API requests
47 | 
48 | ## API Response Structure
49 | 
50 | While models validate requests, responses are returned as raw JSON. A typical state version output response has this structure:
51 | 
52 | ```json
53 | {
54 |   "data": {
55 |     "id": "wsout-BPvFFrYCqRV6qVBK",
56 |     "type": "state-version-outputs",
57 |     "attributes": {
58 |       "name": "vpc_id",
59 |       "sensitive": false,
60 |       "type": "string",
61 |       "value": "vpc-1234567890abcdef",
62 |       "detailed-type": "string"
63 |     },
64 |     "relationships": {
65 |       "configurable": {
66 |         "data": {
67 |           "id": "sv-BPvFFrYCqRV6qVBK",
68 |           "type": "state-versions"
69 |         }
70 |       }
71 |     }
72 |   }
73 | }
74 | ```
75 | 
76 | **Key Attributes:**
77 | - `name`: The name of the output as defined in Terraform configuration
78 | - `sensitive`: Boolean indicating if the output contains sensitive information
79 | - `type`: Simplified data type (string, number, bool, etc.)
80 | - `value`: The actual output value (hidden for sensitive outputs)
81 | - `detailed-type`: More specific type information for complex structures
82 | 
83 | ## Related Resources
84 | 
85 | - [State Version Outputs Tools](../tools/state_version_outputs.md)
86 | - [State Version Models](./state_versions.md)
87 | - [Terraform Cloud API - State Version Outputs](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/state-version-outputs)
```

--------------------------------------------------------------------------------
/docs/tools/state_version_outputs.md:
--------------------------------------------------------------------------------

```markdown
 1 | # State Version Outputs Tools
 2 | 
 3 | The state version outputs tools module provides functions for working with state version outputs in Terraform Cloud.
 4 | 
 5 | ## Overview
 6 | 
 7 | State version outputs represent the output values from Terraform state files, including their names, values, types, and sensitivity information. These tools allow you to retrieve and inspect the outputs generated by your Terraform configurations.
 8 | 
 9 | ## API Reference
10 | 
11 | These tools interact with the Terraform Cloud State Version Outputs API:
12 | - [State Version Outputs API Documentation](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/state-version-outputs)
13 | - [State Versions Concepts](https://developer.hashicorp.com/terraform/cloud-docs/workspaces/state)
14 | 
15 | ## Tools Reference
16 | 
17 | ### list_state_version_outputs
18 | 
19 | **Function:** `list_state_version_outputs(state_version_id: str, page_number: int = 1, page_size: int = 20) -> Dict[str, Any]`
20 | 
21 | **Description:** Retrieves a paginated list of all outputs for a specific state version.
22 | 
23 | **Parameters:**
24 | - `state_version_id` (str): The ID of the state version (format: "sv-xxxxxxxx")
25 | - `page_number` (int): Page number to fetch (default: 1)
26 | - `page_size` (int): Number of results per page (default: 20, max: 100)
27 | 
28 | **Returns:** JSON response containing paginated state version outputs with name, value, type, and sensitivity information.
29 | 
30 | **Notes:**
31 | - Outputs are populated asynchronously after state version upload
32 | - Check the `resources-processed` property on the state version to confirm processing is complete
33 | - Requires "read" permission for the associated workspace
34 | - Sensitive outputs will show `sensitive: true` but hide the actual value
35 | 
36 | ### get_state_version_output
37 | 
38 | **Function:** `get_state_version_output(state_version_output_id: str) -> Dict[str, Any]`
39 | 
40 | **Description:** Retrieves detailed information about a specific state version output by ID.
41 | 
42 | **Parameters:**
43 | - `state_version_output_id` (str): The ID of the state version output (format: "wsout-xxxxxxxx")
44 | 
45 | **Returns:** JSON response containing comprehensive output details including name, value, type, and detailed type information.
46 | 
47 | **Notes:**
48 | - Provides both simplified and detailed type information
49 | - Sensitive outputs will not expose their values in the response
50 | - Requires "read" permission for the associated workspace
51 | - Output IDs are typically obtained from listing outputs first
52 | 
53 | **Common Error Scenarios:**
54 | 
55 | | Error | Cause | Solution |
56 | |-------|-------|----------|
57 | | 404 | Output not found | Verify the ID exists and you have proper permissions |
58 | | 422 | Invalid output ID format | Ensure the ID matches pattern "wsout-xxxxxxxx" |
59 | | 403 | Insufficient permissions | Verify your API token has proper workspace access |
60 | | 202 | Processing incomplete | Wait for state version processing to complete |
61 | 
62 | ## Related Resources
63 | 
64 | - [State Version Outputs Models](../models/state_version_outputs.md)
65 | - [State Version Tools](./state_versions.md)
66 | - [Terraform Cloud API - State Version Outputs](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/state-version-outputs)
```

--------------------------------------------------------------------------------
/docs/models/account.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Account Models
  2 | 
  3 | This document describes the data models used for account operations in Terraform Cloud.
  4 | 
  5 | ## Overview
  6 | 
  7 | Account models provide structure for working with Terraform Cloud account information. These models help with accessing and validating account data retrieved from the Terraform Cloud API.
  8 | 
  9 | ## Models Reference
 10 | 
 11 | ### AccountDetailsRequest
 12 | 
 13 | **Type:** Request Validation Model
 14 | 
 15 | **Description:** Used to validate parameters for retrieving account details.
 16 | 
 17 | **Fields:** None - This model simply enforces the validation pattern for the account details endpoint.
 18 | 
 19 | **Usage Context:**
 20 | Used by the `get_account_details` function to validate request parameters (which are none in this case).
 21 | 
 22 | ### AccountDetails
 23 | 
 24 | **Type:** Response Model
 25 | 
 26 | **Description:** Represents the account information of the current user or service account.
 27 | 
 28 | **Fields:**
 29 | - `id` (string): The ID of the account (e.g., "user-12345abcd")
 30 | - `username` (string): The username of the account
 31 | - `email` (string): The email address associated with the account
 32 | - `is_service_account` (boolean): Whether this is a service account (true) or user account (false)
 33 | - `avatar_url` (string, optional): URL to the user's avatar image
 34 | - `two_factor` (TwoFactorInfo, optional): Information about two-factor authentication status
 35 |   - `enabled` (boolean): Whether 2FA is enabled
 36 |   - `verified` (boolean): Whether 2FA has been verified
 37 | 
 38 | **JSON representation:**
 39 | ```json
 40 | {
 41 |   "data": {
 42 |     "id": "user-12345abcd",
 43 |     "type": "users",
 44 |     "attributes": {
 45 |       "username": "admin-user",
 46 |       "email": "[email protected]",
 47 |       "is-service-account": false,
 48 |       "avatar-url": "https://example.com/avatar.png",
 49 |       "two-factor": {
 50 |         "enabled": true,
 51 |         "verified": true
 52 |       }
 53 |     }
 54 |   }
 55 | }
 56 | ```
 57 | 
 58 | **Notes:**
 59 | - Field names in JSON responses use kebab-case format (e.g., "is-service-account")
 60 | - Field names in the model use snake_case format (e.g., is_service_account)
 61 | - The `from_api_response` static method helps parse API responses into this model
 62 | - Email is only returned for the authenticated user's own account
 63 | 
 64 | **Usage Examples:**
 65 | ```python
 66 | # Parse account details from API response
 67 | account = AccountDetails.from_api_response(api_response)
 68 | 
 69 | # Check if account has two-factor authentication enabled
 70 | if account.two_factor and account.two_factor.enabled:
 71 |     print(f"2FA is enabled for {account.username}")
 72 | 
 73 | # Check if the account is a service account
 74 | if account.is_service_account:
 75 |     print(f"{account.username} is a service account")
 76 | ```
 77 | 
 78 | ## API Response Structure
 79 | 
 80 | When retrieving account details, the Terraform Cloud API returns a response with this structure:
 81 | 
 82 | ```json
 83 | {
 84 |   "data": {
 85 |     "id": "user-12345abcd",
 86 |     "type": "users",
 87 |     "attributes": {
 88 |       "username": "admin-user",
 89 |       "email": "[email protected]",
 90 |       "is-service-account": false,
 91 |       "avatar-url": "https://example.com/avatar.png",
 92 |       "two-factor": {
 93 |         "enabled": true,
 94 |         "verified": true
 95 |       }
 96 |     }
 97 |   }
 98 | }
 99 | ```
100 | 
101 | ## Related Resources
102 | 
103 | - [Account Tools](../tools/account.md)
104 | - [Terraform Cloud API - Account](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/account)
```

--------------------------------------------------------------------------------
/docs/models/cost_estimate.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Cost Estimate Models
  2 | 
  3 | This document describes the data models used for cost estimation in Terraform Cloud.
  4 | 
  5 | ## Overview
  6 | 
  7 | Cost estimate models provide structure and validation for interacting with the Terraform Cloud Cost Estimation API. These models define the format of cost estimate data, status values, and request validation.
  8 | 
  9 | ## Models Reference
 10 | 
 11 | ### CostEstimateStatus
 12 | 
 13 | **Type:** Enum (string)
 14 | 
 15 | **Description:** Represents the possible states a cost estimate can be in during its lifecycle.
 16 | 
 17 | **Values:**
 18 | - `pending`: Cost estimate has not yet started
 19 | - `queued`: Cost estimate is queued for execution
 20 | - `running`: Cost estimate is currently running
 21 | - `errored`: Cost estimate has encountered an error
 22 | - `canceled`: Cost estimate was canceled
 23 | - `finished`: Cost estimate has completed successfully
 24 | - `unreachable`: Cost estimate is in an unreachable state
 25 | 
 26 | **Usage Context:**
 27 | Used to determine the current state of a cost estimate operation and whether it has completed successfully.
 28 | 
 29 | ### StatusTimestamps
 30 | 
 31 | **Type:** Object
 32 | 
 33 | **Description:** Captures timing information for various stages in a cost estimate's lifecycle.
 34 | 
 35 | **Fields:**
 36 | - `queued_at` (string, optional): ISO8601 timestamp when the cost estimate was queued
 37 | - `finished_at` (string, optional): ISO8601 timestamp when the cost estimate execution completed
 38 | 
 39 | **JSON representation:**
 40 | ```json
 41 | {
 42 |   "queued-at": "2023-05-01T12:34:56Z",
 43 |   "finished-at": "2023-05-01T12:35:30Z"
 44 | }
 45 | ```
 46 | 
 47 | **Notes:**
 48 | - Field names in JSON responses use kebab-case format (e.g., "queued-at")
 49 | - Field names in the model use snake_case format (e.g., queued_at)
 50 | - All timestamp fields follow ISO8601 format
 51 | 
 52 | ### CostEstimateRequest
 53 | 
 54 | **Type:** Request Validation Model
 55 | 
 56 | **Description:** Used to validate cost estimate ID parameters in API requests.
 57 | 
 58 | **Fields:**
 59 | - `cost_estimate_id` (string, required): The ID of the cost estimate to retrieve
 60 |   - Format: Must match pattern "ce-[a-zA-Z0-9]{16}"
 61 |   - Example: "ce-BPvFFrYCqRV6qVBK"
 62 | 
 63 | **Validation Rules:**
 64 | - Cost estimate ID must start with "ce-" prefix
 65 | - Must contain exactly 16 alphanumeric characters after the prefix
 66 | 
 67 | **Used by:**
 68 | - `get_cost_estimate_details` tool function to validate the cost estimate ID format before making API requests
 69 | 
 70 | ## API Response Structure
 71 | 
 72 | While models validate requests, responses are returned as raw JSON. A typical cost estimate response has this structure:
 73 | 
 74 | ```json
 75 | {
 76 |   "data": [
 77 |     {
 78 |       "id": "ce-BPvFFrYCqRV6qVBK",
 79 |       "type": "cost-estimates",
 80 |       "attributes": {
 81 |         "error-message": null,
 82 |         "status": "finished",
 83 |         "status-timestamps": {
 84 |           "queued-at": "2023-05-01T12:34:56Z",
 85 |           "finished-at": "2023-05-01T12:35:30Z"
 86 |         },
 87 |         "resources-count": 4,
 88 |         "matched-resources-count": 3,
 89 |         "unmatched-resources-count": 1,
 90 |         "prior-monthly-cost": "0.0",
 91 |         "proposed-monthly-cost": "25.488",
 92 |         "delta-monthly-cost": "25.488"
 93 |       },
 94 |       "links": {
 95 |         "self": "/api/v2/cost-estimate/ce-BPvFFrYCqRV6qVBK"
 96 |       }
 97 |     }
 98 |   ]
 99 | }
100 | ```
101 | 
102 | ## Related Resources
103 | 
104 | - [Cost Estimate Tools](../tools/cost_estimate.md)
105 | - [Terraform Cloud API - Cost Estimates](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/cost-estimates)
```

--------------------------------------------------------------------------------
/docs/tools/apply.md:
--------------------------------------------------------------------------------

```markdown
 1 | # Apply Management Tools
 2 | 
 3 | This module provides tools for managing applies in Terraform Cloud.
 4 | 
 5 | ## Overview
 6 | 
 7 | Applies in Terraform Cloud represent the execution phase of a Terraform run after the plan has been approved. These tools allow retrieving information about applies and recovering from failed state uploads.
 8 | 
 9 | ## API Reference
10 | 
11 | These tools interact with the Terraform Cloud Apply API:
12 | - [Apply API Documentation](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies)
13 | - [Run Lifecycle](https://developer.hashicorp.com/terraform/cloud-docs/run/states)
14 | 
15 | ## Tools Reference
16 | 
17 | ### get_apply_details
18 | 
19 | **Function:** `get_apply_details(apply_id: str) -> Dict[str, Any]`
20 | 
21 | **Description:** Retrieves comprehensive information about an apply operation including its status, resource counts, and timestamps.
22 | 
23 | **Parameters:**
24 | - `apply_id` (str): The ID of the apply to retrieve details for (format: "apply-xxxxxxxx")
25 | 
26 | **Returns:** JSON response containing apply details including:
27 | - Status (queued, running, errored, canceled, finished)
28 | - Status timestamps (queued-at, started-at, finished-at)
29 | - Resource statistics (additions, changes, destructions)
30 | - Log read URL
31 | - Relationships to state versions and runs
32 | 
33 | **Notes:**
34 | - Apply IDs can be found in the relationships of a run object
35 | - Successful applies have a status of "finished"
36 | - The log-read-url is a pre-signed URL to access the full apply logs
37 | - Resource counts help track infrastructure changes
38 | 
39 | ### get_apply_logs
40 | 
41 | **Function:** `get_apply_logs(apply_id: str) -> Dict[str, Any]`
42 | 
43 | **Description:** Retrieves the raw log output from a specific apply operation.
44 | 
45 | **Parameters:**
46 | - `apply_id` (str): The ID of the apply to retrieve logs for (format: "apply-xxxxxxxx")
47 | 
48 | **Returns:** Text content of the apply logs including:
49 | - Terraform output during apply
50 | - Resource creation/modification details
51 | - Error messages (if any occurred)
52 | - Complete execution trace
53 | 
54 | **Notes:**
55 | - Handles HTTP redirects automatically
56 | - Useful for debugging failed applies
57 | - Contains detailed information about each resource change
58 | - Can be large for complex infrastructures
59 | 
60 | ### get_errored_state
61 | 
62 | **Function:** `get_errored_state(apply_id: str) -> Dict[str, Any]`
63 | 
64 | **Description:** Retrieves information about a state file that failed to upload during an apply, enabling state recovery.
65 | 
66 | **Parameters:**
67 | - `apply_id` (str): The ID of the apply with a failed state upload (format: "apply-xxxxxxxx")
68 | 
69 | **Returns:** Terraform state data that was not successfully uploaded, including:
70 | - Complete state representation
71 | - Resource definitions and attributes
72 | - Terraform version information
73 | - State metadata (serial, lineage)
74 | 
75 | **Notes:**
76 | - Critical for recovering from failed state uploads
77 | - Only available when a state upload has failed
78 | - Allows administrators to manually recover state information
79 | - Handles HTTP redirects automatically to retrieve the state data
80 | 
81 | **Common Error Scenarios:**
82 | 
83 | | Error | Cause | Solution |
84 | |-------|-------|----------|
85 | | 404 | Apply not found or no errored state | Verify the apply ID is correct and that it has a failed state |
86 | | 403 | Insufficient permissions | Ensure your token has admin or state access permissions |
87 | | 422 | Invalid apply ID format | Ensure the ID follows the format "apply-xxxxxxxx" |
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/tools/applies.py:
--------------------------------------------------------------------------------

```python
  1 | """Terraform Cloud apply management tools.
  2 | 
  3 | This module provides tools for working with applies in Terraform Cloud.
  4 | It includes functions to retrieve apply details, logs, and errored state information.
  5 | 
  6 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies
  7 | """
  8 | 
  9 | from ..api.client import api_request
 10 | from ..models.base import APIResponse
 11 | from ..models.applies import (
 12 |     ApplyRequest,
 13 |     ApplyErroredStateRequest,
 14 | )
 15 | from ..utils.decorators import handle_api_errors
 16 | 
 17 | 
 18 | @handle_api_errors
 19 | async def get_apply_details(apply_id: str) -> APIResponse:
 20 |     """Get details for a specific apply.
 21 | 
 22 |     Retrieves comprehensive information about an apply including its current status,
 23 |     logs, resource counts, and relationship to other resources.
 24 | 
 25 |     API endpoint: GET /applies/{apply_id}
 26 | 
 27 |     Args:
 28 |         apply_id: The ID of the apply to retrieve details for (format: "apply-xxxxxxxx")
 29 | 
 30 |     Returns:
 31 |         Apply details including status, timestamps, and resource change counts
 32 | 
 33 |     See:
 34 |         docs/tools/apply.md for reference documentation
 35 |     """
 36 |     # Validate parameters
 37 |     params = ApplyRequest(apply_id=apply_id)
 38 | 
 39 |     # Make API request
 40 |     return await api_request(f"applies/{params.apply_id}")
 41 | 
 42 | 
 43 | @handle_api_errors
 44 | async def get_errored_state(apply_id: str) -> APIResponse:
 45 |     """Retrieve the errored state from a failed apply.
 46 | 
 47 |     Gets information about a state file that failed to upload during an apply,
 48 |     providing access to the state data for recovery purposes.
 49 | 
 50 |     API endpoint: GET /applies/{apply_id}/errored-state
 51 | 
 52 |     Args:
 53 |         apply_id: The ID of the apply with a failed state upload (format: "apply-xxxxxxxx")
 54 | 
 55 |     Returns:
 56 |         Information about the errored state including access details.
 57 |         The redirect to the state file is automatically followed.
 58 | 
 59 |     See:
 60 |         docs/tools/apply.md for reference documentation
 61 |     """
 62 |     # Validate parameters
 63 |     params = ApplyErroredStateRequest(apply_id=apply_id)
 64 | 
 65 |     # Make API request - redirect handling happens automatically in the API client
 66 |     return await api_request(f"applies/{params.apply_id}/errored-state")
 67 | 
 68 | 
 69 | @handle_api_errors
 70 | async def get_apply_logs(apply_id: str) -> APIResponse:
 71 |     """Retrieve logs from an apply.
 72 | 
 73 |     Gets the raw log output from a Terraform Cloud apply operation,
 74 |     providing detailed information about resource changes and any errors.
 75 | 
 76 |     API endpoint: Uses the log-read-url from GET /applies/{apply_id}
 77 | 
 78 |     Args:
 79 |         apply_id: The ID of the apply to retrieve logs for (format: "apply-xxxxxxxx")
 80 | 
 81 |     Returns:
 82 |         The raw logs from the apply operation. The redirect to the log file
 83 |         is automatically followed.
 84 | 
 85 |     See:
 86 |         docs/tools/apply.md for reference documentation
 87 |     """
 88 |     # Validate parameters using existing model
 89 |     params = ApplyRequest(apply_id=apply_id)
 90 | 
 91 |     # First get apply details to get the log URL
 92 |     apply_details = await api_request(f"applies/{params.apply_id}")
 93 | 
 94 |     # Extract log read URL
 95 |     log_read_url = (
 96 |         apply_details.get("data", {}).get("attributes", {}).get("log-read-url")
 97 |     )
 98 |     if not log_read_url:
 99 |         return {"error": "No log URL available for this apply"}
100 | 
101 |     # Use the enhanced api_request to fetch logs from the external URL
102 |     return await api_request(log_read_url, external_url=True, accept_text=True)
103 | 
```

--------------------------------------------------------------------------------
/docs/models/assessment_result.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Assessment Results Models
  2 | 
  3 | This document describes the Pydantic models used for validating input to the Assessment Results API.
  4 | 
  5 | ## Overview
  6 | 
  7 | Assessment Results models provide validation for requests to Terraform Cloud's health assessment API endpoints. Health assessments automatically check whether deployed infrastructure matches the requirements defined in Terraform configurations.
  8 | 
  9 | ## Models
 10 | 
 11 | ### AssessmentResultStatus
 12 | 
 13 | ```python
 14 | class AssessmentResultStatus(str, Enum):
 15 |     """Status options for assessment results in Terraform Cloud."""
 16 |     PENDING = "pending"
 17 |     QUEUED = "queued"
 18 |     RUNNING = "running"
 19 |     ERRORED = "errored"
 20 |     CANCELED = "canceled"
 21 |     FINISHED = "finished"
 22 | ```
 23 | 
 24 | This enum defines the various states an assessment result can be in during its lifecycle:
 25 | 
 26 | - `PENDING`: Assessment has not yet started
 27 | - `QUEUED`: Assessment is queued for execution
 28 | - `RUNNING`: Assessment is currently running
 29 | - `ERRORED`: Assessment has encountered an error
 30 | - `CANCELED`: Assessment was canceled
 31 | - `FINISHED`: Assessment has completed successfully
 32 | 
 33 | ### AssessmentResultRequest
 34 | 
 35 | ```python
 36 | class AssessmentResultRequest(APIRequest):
 37 |     """Request model for retrieving assessment result details."""
 38 |     assessment_result_id: str = Field(
 39 |         ...,
 40 |         description="The ID of the assessment result to retrieve",
 41 |         pattern=r"^asmtres-[a-zA-Z0-9]{8,}$",
 42 |     )
 43 | ```
 44 | 
 45 | This model validates the assessment result ID parameter for basic API requests:
 46 | 
 47 | - `assessment_result_id`: The ID of the assessment result to retrieve (format: "asmtres-xxxxxxxx")
 48 |   - Required field (no default value)
 49 |   - Must match the pattern of Terraform Cloud assessment result IDs
 50 |   - No alias needed as the field name matches the API parameter name
 51 | 
 52 | ### AssessmentOutputRequest
 53 | 
 54 | ```python
 55 | class AssessmentOutputRequest(AssessmentResultRequest):
 56 |     """Request model for retrieving assessment result outputs."""
 57 |     pass  # Uses the same validation as the parent class
 58 | ```
 59 | 
 60 | This model extends `AssessmentResultRequest` to validate requests for specialized outputs:
 61 | 
 62 | - Used for JSON plan output requests
 63 | - Used for provider schema requests 
 64 | - Used for log output requests
 65 | 
 66 | ## API Response Structure
 67 | 
 68 | While the responses are not validated with Pydantic models, they typically follow this structure:
 69 | 
 70 | ```json
 71 | {
 72 |   "id": "asmtres-UG5rE9L1373hMYMA",
 73 |   "type": "assessment-results",
 74 |   "data": {
 75 |     "attributes": {
 76 |       "drifted": true,
 77 |       "succeeded": true,
 78 |       "error-msg": null,
 79 |       "created-at": "2022-07-02T22:29:58+00:00"
 80 |     },
 81 |     "links": {
 82 |       "self": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/",
 83 |       "json-output": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/json-output",
 84 |       "json-schema": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/json-schema",
 85 |       "log-output": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/log-output"
 86 |     }
 87 |   }
 88 | }
 89 | ```
 90 | 
 91 | For specialized endpoint responses like JSON output, JSON schema, and log output, the response is provided in "content" field as raw text:
 92 | 
 93 | ```json
 94 | {
 95 |   "content": "Raw output content here..."
 96 | }
 97 | ```
 98 | 
 99 | ## Reference 
100 | 
101 | For more detailed information, see:
102 | - [Terraform Cloud API Documentation](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/assessment-results)
103 | - Tools implementation in `terraform_cloud_mcp/tools/assessment_results.py`
```

--------------------------------------------------------------------------------
/docs/tools/assessment_results.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Assessment Results API Tools
  2 | 
  3 | This document describes the tools for interacting with Terraform Cloud Health Assessment Results.
  4 | Health assessments automatically verify that real infrastructure matches the requirements defined in Terraform configurations.
  5 | 
  6 | ## Overview
  7 | 
  8 | Health assessments provide automated drift detection and continuous validation for Terraform Cloud workspaces.
  9 | The assessment results API allows you to retrieve assessment details, plans, schemas, and logs.
 10 | 
 11 | > **Note**: Health assessments are a premium feature available in HCP Terraform Plus and Premium editions.
 12 | 
 13 | ## Available Tools
 14 | 
 15 | | Tool Name | Description |
 16 | |-----------|-------------|
 17 | | `get_assessment_result_details` | Retrieve basic information about an assessment result |
 18 | | `get_assessment_json_output` | Get the JSON plan from an assessment |
 19 | | `get_assessment_json_schema` | Get the provider schema from an assessment |
 20 | | `get_assessment_log_output` | Get logs from an assessment run |
 21 | 
 22 | ## Tool Usage
 23 | 
 24 | ### Get Assessment Result Details
 25 | 
 26 | Retrieves information about a specific health assessment result, including status and drift detection.
 27 | 
 28 | ```python
 29 | get_assessment_result_details(assessment_result_id="asmtres-XXXXXXXXXX")
 30 | ```
 31 | 
 32 | #### Parameters
 33 | 
 34 | - `assessment_result_id`: The ID of the assessment result (format: "asmtres-XXXXXXXXXX")
 35 | 
 36 | #### Response Example
 37 | 
 38 | ```json
 39 | {
 40 |   "id": "asmtres-UG5rE9L1373hMYMA",
 41 |   "type": "assessment-results",
 42 |   "data": {
 43 |     "attributes": {
 44 |       "drifted": true,
 45 |       "succeeded": true,
 46 |       "error-msg": null,
 47 |       "created-at": "2022-07-02T22:29:58+00:00",
 48 |     },
 49 |     "links": {
 50 |       "self": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/",
 51 |       "json-output": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/json-output",
 52 |       "json-schema": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/json-schema",
 53 |       "log-output": "/api/v2/assessment-results/asmtres-UG5rE9L1373hMYMA/log-output"
 54 |     }
 55 |   }
 56 | }
 57 | ```
 58 | 
 59 | ### Get Assessment JSON Output
 60 | 
 61 | Retrieves the JSON plan output from an assessment result.
 62 | 
 63 | ```python
 64 | get_assessment_json_output(assessment_result_id="asmtres-XXXXXXXXXX")
 65 | ```
 66 | 
 67 | #### Parameters
 68 | 
 69 | - `assessment_result_id`: The ID of the assessment result (format: "asmtres-XXXXXXXXXX")
 70 | 
 71 | #### Response Example
 72 | 
 73 | ```json
 74 | {
 75 |   "content": "{\n  \"format_version\": \"1.0\",\n  \"terraform_version\": \"1.3.0\",\n  \"planned_values\": { ... },\n  \"resource_changes\": [ ... ],\n  \"configuration\": { ... }\n}"
 76 | }
 77 | ```
 78 | 
 79 | ### Get Assessment JSON Schema
 80 | 
 81 | Retrieves the provider schema from an assessment result.
 82 | 
 83 | ```python
 84 | get_assessment_json_schema(assessment_result_id="asmtres-XXXXXXXXXX")
 85 | ```
 86 | 
 87 | #### Parameters
 88 | 
 89 | - `assessment_result_id`: The ID of the assessment result (format: "asmtres-XXXXXXXXXX")
 90 | 
 91 | #### Response Example
 92 | 
 93 | ```json
 94 | {
 95 |   "content": "{\n  \"format_version\": \"1.0\",\n  \"provider_schemas\": { ... }\n}"
 96 | }
 97 | ```
 98 | 
 99 | ### Get Assessment Log Output
100 | 
101 | Retrieves the logs from an assessment run.
102 | 
103 | ```python
104 | get_assessment_log_output(assessment_result_id="asmtres-XXXXXXXXXX")
105 | ```
106 | 
107 | #### Parameters
108 | 
109 | - `assessment_result_id`: The ID of the assessment result (format: "asmtres-XXXXXXXXXX")
110 | 
111 | #### Response Example
112 | 
113 | ```json
114 | {
115 |   "content": "Terraform initiated...\nGathering resources...\nDetecting drift...\n"
116 | }
117 | ```
118 | 
119 | ## Authentication Requirements
120 | 
121 | The assessment results endpoints have specific authentication requirements:
122 | 
123 | - `get_assessment_result_details`: Accessible to users with read access to a workspace
124 | - All other endpoints (`json-output`, `json-schema`, `log-output`): Require admin level access and cannot be accessed with organization tokens. You must use a user token or team token with admin access.
125 | 
126 | ## Reference
127 | 
128 | For more detailed information, see the [official Terraform Cloud API documentation](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/assessment-results).
```

--------------------------------------------------------------------------------
/docs/tools/plan.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Plan Management Tools
  2 | 
  3 | This module provides tools for retrieving information about Terraform plans.
  4 | 
  5 | ## Overview
  6 | 
  7 | A plan in Terraform Cloud contains information about the changes Terraform will make to your infrastructure, including resources to add, change, or delete. Plans represent the execution plan that Terraform generates during a run before any changes are applied.
  8 | 
  9 | ## API Reference
 10 | 
 11 | These tools interact with the Terraform Cloud Plan API:
 12 | - [Plan API Documentation](https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans)
 13 | - [Run Workflow](https://developer.hashicorp.com/terraform/cloud-docs/run/states)
 14 | 
 15 | ## Tools Reference
 16 | 
 17 | ### get_plan_details
 18 | 
 19 | **Function:** `get_plan_details(plan_id: str) -> Dict[str, Any]`
 20 | 
 21 | **Description:** Retrieves comprehensive information about a specific plan including its status, resource counts, and timestamps.
 22 | 
 23 | **Parameters:**
 24 | - `plan_id` (str): The ID of the plan to retrieve details for (format: "plan-xxxxxxxx")
 25 | 
 26 | **Returns:** JSON response containing plan details including:
 27 | - Status (queued, running, errored, canceled, finished)
 28 | - Status timestamps (queued-at, started-at, finished-at)
 29 | - Resource statistics (additions, changes, destructions)
 30 | - Log read URL
 31 | - Relationships to runs and configuration versions
 32 | 
 33 | **Notes:**
 34 | - Plan IDs can be found in the relationships of a run object
 35 | - Successful plans have a status of "finished"
 36 | - The log-read-url is a pre-signed URL to access the full plan logs
 37 | - Resource counts are useful for understanding the impact of changes
 38 | 
 39 | ### get_plan_json_output
 40 | 
 41 | **Function:** `get_plan_json_output(plan_id: str) -> Dict[str, Any]`
 42 | 
 43 | **Description:** Retrieves the JSON representation of a plan's execution details.
 44 | 
 45 | **Parameters:**
 46 | - `plan_id` (str): The ID of the plan to retrieve JSON output for (format: "plan-xxxxxxxx")
 47 | 
 48 | **Returns:** Machine-readable JSON format of the plan containing:
 49 | - Detailed resource changes
 50 | - Provider configurations
 51 | - Output changes
 52 | - Variables values used
 53 | - Complete planned actions in structured format
 54 | 
 55 | **Notes:**
 56 | - Automatically follows HTTP redirects to retrieve the plan JSON content
 57 | - Ideal for programmatic analysis of infrastructure changes
 58 | - Contains much more detailed information than the summary in plan details
 59 | - Useful for custom validation or visualization of changes
 60 | 
 61 | ### get_run_plan_json_output
 62 | 
 63 | **Function:** `get_run_plan_json_output(run_id: str) -> Dict[str, Any]`
 64 | 
 65 | **Description:** Retrieves the JSON representation of a run's current plan execution details.
 66 | 
 67 | **Parameters:**
 68 | - `run_id` (str): The ID of the run to retrieve plan JSON output for (format: "run-xxxxxxxx")
 69 | 
 70 | **Returns:** Same JSON plan format as get_plan_json_output but referenced by run ID.
 71 | 
 72 | **Notes:**
 73 | - Provides the same JSON plan data as get_plan_json_output
 74 | - Useful when you only have the run ID and not the plan ID
 75 | - Automatically follows HTTP redirects to retrieve the content
 76 | - Returns the current plan for the run
 77 | 
 78 | ### get_plan_logs
 79 | 
 80 | **Function:** `get_plan_logs(plan_id: str) -> Dict[str, Any]`
 81 | 
 82 | **Description:** Retrieves the raw log output from a Terraform plan operation.
 83 | 
 84 | **Parameters:**
 85 | - `plan_id` (str): The ID of the plan to retrieve logs for (format: "plan-xxxxxxxx")
 86 | 
 87 | **Returns:** Text content of the plan logs including:
 88 | - Terraform output during planning
 89 | - Resource change details in human-readable format
 90 | - Warnings and errors that occurred during planning
 91 | 
 92 | **Notes:**
 93 | - Handles HTTP redirects automatically to retrieve the log content
 94 | - Useful for troubleshooting plan failures
 95 | - Contains the same output as displayed in Terraform Cloud UI
 96 | - May include sensitive information depending on your code
 97 | 
 98 | **Common Error Scenarios:**
 99 | 
100 | | Error | Cause | Solution |
101 | |-------|-------|----------|
102 | | 404 | Plan not found | Verify the plan ID is correct |
103 | | 403 | Insufficient permissions | Ensure your token has read access to the workspace |
104 | | 422 | Invalid plan ID format | Ensure the ID follows the format "plan-xxxxxxxx" |
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/tools/plans.py:
--------------------------------------------------------------------------------

```python
  1 | """Terraform Cloud plan management tools.
  2 | 
  3 | This module provides tools for working with plans in Terraform Cloud.
  4 | It includes functions to retrieve plan details and JSON output.
  5 | 
  6 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans
  7 | """
  8 | 
  9 | from ..api.client import api_request
 10 | from ..models.base import APIResponse
 11 | from ..models.plans import (
 12 |     PlanJsonOutputRequest,
 13 |     PlanRequest,
 14 |     RunPlanJsonOutputRequest,
 15 | )
 16 | from ..utils.decorators import handle_api_errors
 17 | 
 18 | 
 19 | @handle_api_errors
 20 | async def get_plan_details(plan_id: str) -> APIResponse:
 21 |     """Get details for a specific plan.
 22 | 
 23 |     Retrieves comprehensive information about a plan including its current status,
 24 |     logs, resource counts, and relationship to other resources.
 25 | 
 26 |     API endpoint: GET /plans/{plan_id}
 27 | 
 28 |     Args:
 29 |         plan_id: The ID of the plan to retrieve details for (format: "plan-xxxxxxxx")
 30 | 
 31 |     Returns:
 32 |         Plan details including status, timestamps, and resource change counts
 33 | 
 34 |     See:
 35 |         docs/tools/plan.md for reference documentation
 36 |     """
 37 |     # Validate parameters
 38 |     params = PlanRequest(plan_id=plan_id)
 39 | 
 40 |     # Make API request
 41 |     return await api_request(f"plans/{params.plan_id}")
 42 | 
 43 | 
 44 | @handle_api_errors
 45 | async def get_plan_json_output(plan_id: str) -> APIResponse:
 46 |     """Retrieve the JSON execution plan.
 47 | 
 48 |     Gets the JSON representation of a plan's execution details, providing a
 49 |     machine-readable format of the planned resource changes.
 50 | 
 51 |     API endpoint: GET /plans/{plan_id}/json-output
 52 | 
 53 |     Args:
 54 |         plan_id: The ID of the plan to retrieve JSON output for (format: "plan-xxxxxxxx")
 55 | 
 56 |     Returns:
 57 |         The complete JSON formatted plan with resource changes, metadata,
 58 |         and planned actions. The redirect is automatically followed.
 59 | 
 60 |     See:
 61 |         docs/tools/plan.md for reference documentation
 62 |     """
 63 |     # Validate parameters
 64 |     params = PlanJsonOutputRequest(plan_id=plan_id)
 65 | 
 66 |     # Make API request
 67 |     return await api_request(f"plans/{params.plan_id}/json-output")
 68 | 
 69 | 
 70 | @handle_api_errors
 71 | async def get_run_plan_json_output(run_id: str) -> APIResponse:
 72 |     """Retrieve the JSON execution plan from a run.
 73 | 
 74 |     Gets the JSON representation of a run's current plan execution details,
 75 |     providing a machine-readable format of the planned resource changes.
 76 | 
 77 |     API endpoint: GET /runs/{run_id}/plan/json-output
 78 | 
 79 |     Args:
 80 |         run_id: The ID of the run to retrieve plan JSON output for (format: "run-xxxxxxxx")
 81 | 
 82 |     Returns:
 83 |         The complete JSON formatted plan with resource changes, metadata,
 84 |         and planned actions. The redirect is automatically followed.
 85 | 
 86 |     See:
 87 |         docs/tools/plan.md for reference documentation
 88 |     """
 89 |     # Validate parameters
 90 |     params = RunPlanJsonOutputRequest(run_id=run_id)
 91 | 
 92 |     # Make API request
 93 |     return await api_request(f"runs/{params.run_id}/plan/json-output")
 94 | 
 95 | 
 96 | @handle_api_errors
 97 | async def get_plan_logs(plan_id: str) -> APIResponse:
 98 |     """Retrieve logs from a plan.
 99 | 
100 |     Gets the raw log output from a Terraform Cloud plan operation,
101 |     providing detailed information about the execution plan.
102 | 
103 |     API endpoint: Uses the log-read-url from GET /plans/{plan_id}
104 | 
105 |     Args:
106 |         plan_id: The ID of the plan to retrieve logs for (format: "plan-xxxxxxxx")
107 | 
108 |     Returns:
109 |         The raw logs from the plan operation. The redirect to the log file
110 |         is automatically followed.
111 | 
112 |     See:
113 |         docs/tools/plan.md for reference documentation
114 |     """
115 |     # Validate parameters using existing model
116 |     params = PlanRequest(plan_id=plan_id)
117 | 
118 |     # First get plan details to get the log URL
119 |     plan_details = await api_request(f"plans/{params.plan_id}")
120 | 
121 |     # Extract log read URL
122 |     log_read_url = (
123 |         plan_details.get("data", {}).get("attributes", {}).get("log-read-url")
124 |     )
125 |     if not log_read_url:
126 |         return {"error": "No log URL available for this plan"}
127 | 
128 |     # Use the enhanced api_request to fetch logs from the external URL
129 |     return await api_request(log_read_url, external_url=True, accept_text=True)
130 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/applies.py:
--------------------------------------------------------------------------------

```python
  1 | """Apply models for Terraform Cloud API
  2 | 
  3 | This module contains models for Terraform Cloud apply-related requests.
  4 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies
  5 | """
  6 | 
  7 | from enum import Enum
  8 | from typing import Optional
  9 | 
 10 | from pydantic import Field
 11 | 
 12 | from .base import APIRequest
 13 | 
 14 | 
 15 | class ApplyStatus(str, Enum):
 16 |     """Status options for applies in Terraform Cloud.
 17 | 
 18 |     Defines the various states an apply can be in during its lifecycle:
 19 |     - PENDING: Apply has not yet started
 20 |     - MANAGED_QUEUED/QUEUED: Apply is queued for execution
 21 |     - RUNNING: Apply is currently running
 22 |     - ERRORED: Apply has encountered an error
 23 |     - CANCELED: Apply was canceled
 24 |     - FINISHED: Apply has completed successfully
 25 |     - UNREACHABLE: Apply is in an unreachable state
 26 | 
 27 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies
 28 | 
 29 |     See:
 30 |         docs/models/apply.md for reference
 31 |     """
 32 | 
 33 |     PENDING = "pending"
 34 |     MANAGED_QUEUED = "managed_queued"
 35 |     QUEUED = "queued"
 36 |     RUNNING = "running"
 37 |     ERRORED = "errored"
 38 |     CANCELED = "canceled"
 39 |     FINISHED = "finished"
 40 |     UNREACHABLE = "unreachable"
 41 | 
 42 | 
 43 | class ExecutionDetails(APIRequest):
 44 |     """Model for apply execution details.
 45 | 
 46 |     Represents execution mode specific details for an apply, including agent
 47 |     information when running in agent execution mode.
 48 | 
 49 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies
 50 | 
 51 |     See:
 52 |         docs/models/apply.md for reference
 53 |     """
 54 | 
 55 |     agent_id: Optional[str] = Field(
 56 |         None,
 57 |         alias="agent-id",
 58 |         description="ID of the agent that ran the apply",
 59 |     )
 60 |     agent_name: Optional[str] = Field(
 61 |         None,
 62 |         alias="agent-name",
 63 |         description="Name of the agent that ran the apply",
 64 |     )
 65 |     agent_pool_id: Optional[str] = Field(
 66 |         None,
 67 |         alias="agent-pool-id",
 68 |         description="ID of the agent pool the apply ran in",
 69 |     )
 70 |     agent_pool_name: Optional[str] = Field(
 71 |         None,
 72 |         alias="agent-pool-name",
 73 |         description="Name of the agent pool the apply ran in",
 74 |     )
 75 |     # Additional execution mode details can be added here
 76 | 
 77 | 
 78 | class StatusTimestamps(APIRequest):
 79 |     """Model for apply execution timestamps.
 80 | 
 81 |     Captures the timestamps for various stages in an apply's lifecycle.
 82 | 
 83 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies
 84 | 
 85 |     See:
 86 |         docs/models/apply.md for reference
 87 |     """
 88 | 
 89 |     queued_at: Optional[str] = Field(
 90 |         None,
 91 |         alias="queued-at",
 92 |         description="When the apply was queued",
 93 |     )
 94 |     pending_at: Optional[str] = Field(
 95 |         None,
 96 |         alias="pending-at",
 97 |         description="When the apply entered pending state",
 98 |     )
 99 |     started_at: Optional[str] = Field(
100 |         None,
101 |         alias="started-at",
102 |         description="When the apply execution started",
103 |     )
104 |     finished_at: Optional[str] = Field(
105 |         None,
106 |         alias="finished-at",
107 |         description="When the apply execution completed",
108 |     )
109 | 
110 | 
111 | class ApplyRequest(APIRequest):
112 |     """Request model for retrieving an apply.
113 | 
114 |     Used to validate the apply ID parameter for API requests.
115 | 
116 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies#show-an-apply
117 | 
118 |     See:
119 |         docs/models/apply.md for reference
120 |     """
121 | 
122 |     apply_id: str = Field(
123 |         ...,
124 |         # No alias needed as field name matches API parameter
125 |         description="The ID of the apply to retrieve",
126 |         pattern=r"^apply-[a-zA-Z0-9]{16}$",  # Standard apply ID pattern
127 |     )
128 | 
129 | 
130 | class ApplyErroredStateRequest(APIRequest):
131 |     """Request model for retrieving an apply's errored state.
132 | 
133 |     Used to validate the apply ID parameter for errored state API requests.
134 | 
135 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/applies#recover-a-failed-state-upload-after-applying
136 | 
137 |     See:
138 |         docs/models/apply.md for reference
139 |     """
140 | 
141 |     apply_id: str = Field(
142 |         ...,
143 |         # No alias needed as field name matches API parameter
144 |         description="The ID of the apply with a failed state upload",
145 |         pattern=r"^apply-[a-zA-Z0-9]{16}$",  # Standard apply ID pattern
146 |     )
147 | 
148 | 
149 | # Response handling is implemented through raw dictionaries
150 | 
```

--------------------------------------------------------------------------------
/docs/conversations/assessment-results-conversation.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Assessment Results Conversation Example
  2 | 
  3 | This document demonstrates how to use the assessment results tools in a conversation with Claude.
  4 | 
  5 | ## Retrieving Assessment Results
  6 | 
  7 | ```
  8 | ### User
  9 | 
 10 | I need to check if there's been any drift in my infrastructure based on the latest health assessment. The assessment result ID is asmtres-UG5rE9L1373hMYMA.
 11 | 
 12 | ### Claude
 13 | 
 14 | I'll help you check for drift in your infrastructure by retrieving the latest health assessment results. Let me fetch that information for you.
 15 | 
 16 | [Claude uses get_assessment_result_details tool]
 17 | 
 18 | Here's what I found:
 19 | 
 20 | - The assessment was completed successfully
 21 | - Drift was detected in your infrastructure
 22 | - The assessment was created on July 2, 2022
 23 | - There are no error messages
 24 | 
 25 | Would you like me to retrieve the detailed JSON output to see exactly what resources have drifted?
 26 | ```
 27 | 
 28 | ```
 29 | ### User
 30 | 
 31 | Yes, please show me the JSON output so I can see what resources have drifted.
 32 | 
 33 | ### Claude
 34 | 
 35 | I'll get the detailed JSON output that shows exactly which resources have drifted.
 36 | 
 37 | [Claude uses get_assessment_json_output tool]
 38 | 
 39 | Here's a summary of the drift detected:
 40 | 
 41 | 1. **EC2 Instance (aws_instance.web_server)**
 42 |    - Current tags don't match configuration
 43 |    - Security group attachments have changed
 44 |    
 45 | 2. **S3 Bucket (aws_s3_bucket.logs)**
 46 |    - Versioning configuration has changed from enabled to disabled
 47 | 
 48 | 3. **IAM Role (aws_iam_role.lambda_execution)**
 49 |    - An additional policy has been attached that wasn't in the Terraform configuration
 50 | 
 51 | Would you like me to help you understand how to address this drift?
 52 | ```
 53 | 
 54 | ```
 55 | ### User
 56 | 
 57 | Yes, what are my options for addressing this drift?
 58 | 
 59 | ### Claude
 60 | 
 61 | You have several options for addressing the infrastructure drift:
 62 | 
 63 | 1. **Update Your Terraform Configuration**:
 64 |    - Modify your Terraform code to match the current state
 65 |    - This approach "accepts" the current state as the new desired state
 66 |    - Use terraform plan to verify changes before applying
 67 | 
 68 | 2. **Apply Your Existing Configuration**:
 69 |    - Run terraform apply to revert infrastructure back to the state defined in your configuration
 70 |    - This will undo manual changes and enforce your existing code
 71 |    - Good for cases where the drift was accidental or unauthorized
 72 | 
 73 | 3. **Selective Updates**:
 74 |    - Import some real-world changes into your configuration and revert others
 75 |    - For example, keep the new IAM policies but revert the S3 bucket versioning change
 76 | 
 77 | 4. **Investigate Before Deciding**:
 78 |    - Review the logs to understand when and possibly why these changes occurred
 79 |    - Let me fetch the assessment logs for more context:
 80 | 
 81 | [Claude uses get_assessment_log_output tool]
 82 | 
 83 | Based on what I'm seeing in the logs, I recommend first updating your Terraform configuration to document the security group changes on the EC2 instance as those appear to be intentional, but reverting the S3 bucket versioning change as that appears to be accidental and could affect your compliance requirements.
 84 | 
 85 | Would you like me to help you draft the Terraform code updates needed to address this drift?
 86 | ```
 87 | 
 88 | ## Investigating Provider Schema
 89 | 
 90 | ```
 91 | ### User
 92 | 
 93 | Before updating the code, I want to check the provider schema to make sure I understand all available attributes for the S3 bucket resource.
 94 | 
 95 | ### Claude
 96 | 
 97 | Good idea! Let me retrieve the provider schema from the assessment result to show you all available attributes for the S3 bucket resource.
 98 | 
 99 | [Claude uses get_assessment_json_schema tool]
100 | 
101 | Here are the key attributes for the AWS S3 bucket resource based on the provider schema:
102 | 
103 | **aws_s3_bucket Attributes:**
104 | 
105 | **Required:**
106 | - bucket - Name of the bucket
107 | 
108 | **Optional:**
109 | - acl - Canned ACL to apply
110 | - bucket_prefix - Creates a unique bucket name with this prefix
111 | - force_destroy - Allow deletion even if bucket not empty
112 | - versioning - Configuration for versioning
113 |   - enabled - Whether versioning is enabled
114 |   - mfa_delete - Whether MFA is required for deletion
115 | - website - Website configuration
116 | - cors_rule - CORS configuration
117 | - lifecycle_rule - Lifecycle rules
118 | - replication_configuration - Replication configuration
119 | - server_side_encryption_configuration - Server-side encryption
120 | - tags - Key-value map of tags
121 | 
122 | For your issue with versioning, you'll want to focus on the versioning block. The schema confirms you need to set enabled = true to maintain versioning on your bucket.
123 | 
124 | Would you like me to help you draft the necessary Terraform code to restore the versioning configuration?
125 | ```
```

--------------------------------------------------------------------------------
/docs/conversations/apply-management-conversation.md:
--------------------------------------------------------------------------------

```markdown
  1 | # Apply Management Conversation Examples
  2 | 
  3 | This document provides example conversations demonstrating how to use the apply management tools in the Terraform Cloud MCP.
  4 | 
  5 | ## Getting Apply Details
  6 | 
  7 | ```
  8 | **User:** I'd like to check on the status of an apply in my Terraform Cloud workspace. The apply ID is apply-gH2Ns7VBP9a2QMcr
  9 | 
 10 | **Claude:** I'll retrieve the details for that apply for you.
 11 | 
 12 | [Claude uses get_apply_details tool]
 13 | 
 14 | Here are the details for apply-gH2Ns7VBP9a2QMcr:
 15 | 
 16 | Status: finished
 17 | Resources added: 3
 18 | Resources changed: 1  
 19 | Resources destroyed: 0
 20 | 
 21 | The apply was queued at 2023-11-15T14:31:05Z, started at 2023-11-15T14:32:18Z, and finished at 2023-11-15T14:35:42Z.
 22 | 
 23 | The operation took about 3 minutes and 24 seconds to complete.
 24 | ```
 25 | 
 26 | ## Retrieving Apply Logs
 27 | 
 28 | ```
 29 | **User:** Can you show me the logs for apply-gH2Ns7VBP9a2QMcr? I want to see what changes were made.
 30 | 
 31 | **Claude:** I'll retrieve the logs for that apply.
 32 | 
 33 | [Claude uses get_apply_logs tool]
 34 | 
 35 | Here are the logs from the apply:
 36 | 
 37 | The apply used Terraform v1.4.6 on linux and successfully completed the following actions:
 38 | 
 39 | - Created an AWS security group (sg-0a1b2c3d4e5f6g7h8) in 3 seconds
 40 | - Created an AWS instance for the web server (i-0a1b2c3d4e5f6g7h8) which took 30 seconds
 41 | - Created an S3 bucket for logs (my-example-logs-bucket) in 5 seconds
 42 | - Modified a security group rule to allow HTTPS traffic in 2 seconds
 43 | 
 44 | The apply completed successfully with 3 resources added and 1 resource changed, taking about 40 seconds total.
 45 | 
 46 | Would you like me to explain any specific part of the apply process?
 47 | ```
 48 | 
 49 | ## Working with Errored States
 50 | 
 51 | ```
 52 | **User:** I found an apply with an error: apply-rT5Kp2VsMx3zNPqf. Can you check if there's a failed state to recover?
 53 | 
 54 | **Claude:** I'll check if there's an errored state for that apply that we can recover.
 55 | 
 56 | [Claude uses get_errored_state tool]
 57 | 
 58 | I found the failed state upload for apply-rT5Kp2VsMx3zNPqf. It contains state data for 12 resources.
 59 | 
 60 | The state version is 4, and it includes resources like:
 61 | - aws_vpc.main (vpc-0a1b2c3d)
 62 | - aws_subnet.public (2 instances)
 63 | - aws_subnet.private (2 instances)
 64 | - aws_route_table.public
 65 | - aws_route_table.private
 66 | - aws_internet_gateway.main
 67 | - aws_security_group.web
 68 | - aws_instance.app_server (2 instances)
 69 | - aws_s3_bucket.logs
 70 | 
 71 | This state can be recovered to prevent drift between what Terraform Cloud knows about your infrastructure and what actually exists. Would you like me to help with the recovery process?
 72 | ```
 73 | 
 74 | ## Understanding Apply Failures
 75 | 
 76 | ```
 77 | **User:** Can you check the details of apply-xYz123AbCd and tell me why it failed?
 78 | 
 79 | **Claude:** I'll examine what went wrong with that apply.
 80 | 
 81 | [Claude uses get_apply_details tool]
 82 | [Claude uses get_apply_logs tool]
 83 | 
 84 | I've analyzed the failed apply. Here's what happened:
 85 | 
 86 | The apply failed during resource creation with error code 403 (Forbidden).
 87 | 
 88 | The specific error occurred while creating an AWS IAM role:
 89 | - Resource: aws_iam_role.lambda_execution_role
 90 | - Error: "AccessDenied: User is not authorized to perform iam:CreateRole"
 91 | 
 92 | The Terraform credentials being used don't have sufficient permissions to create IAM roles. The apply attempted to create 3 resources but failed after creating the first 2 (an S3 bucket and Lambda function), failing on the IAM role creation.
 93 | 
 94 | To resolve this, you'll need to either:
 95 | 1. Add IAM permissions to the credentials being used
 96 | 2. Have someone with appropriate permissions create the IAM role separately
 97 | 3. Use a different approach that doesn't require creating new IAM roles
 98 | ```
 99 | 
100 | ## Comparing Multiple Applies
101 | 
102 | ```
103 | **User:** Can you compare the details of two different applies for me? apply-8HqpY2tKnGbR5xVz and apply-cJm3L7sWvZ4dNfQk
104 | 
105 | **Claude:** I'll retrieve and compare the details of both applies.
106 | 
107 | [Claude uses get_apply_details tool]
108 | [Claude uses get_apply_details tool]
109 | 
110 | Here's a comparison of the two applies:
111 | 
112 | Apply 1 (apply-8HqpY2tKnGbR5xVz):
113 | - Status: finished
114 | - Duration: 4m 12s
115 | - Resources Added: 8
116 | - Resources Changed: 3
117 | - Resources Destroyed: 0
118 | - Total Actions: 11
119 | - Started: 2025-03-10T15:22:18Z
120 | 
121 | Apply 2 (apply-cJm3L7sWvZ4dNfQk):
122 | - Status: finished
123 | - Duration: 2m 38s
124 | - Resources Added: 2
125 | - Resources Changed: 5
126 | - Resources Destroyed: 4
127 | - Total Actions: 11
128 | - Started: 2025-03-15T09:45:32Z
129 | 
130 | Key differences:
131 | - Apply 2 completed faster (2m 38s vs 4m 12s)
132 | - Apply 1 created more resources (8 vs 2)
133 | - Apply 2 destroyed resources (4) while Apply 1 had none
134 | - Both applies had the same total number of resource actions (11)
135 | 
136 | Would you like me to analyze any specific aspect of these applies in more detail?
137 | ```
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/__init__.py:
--------------------------------------------------------------------------------

```python
  1 | """Data models for Terraform Cloud MCP"""
  2 | 
  3 | # Re-export the base models for easier access
  4 | from .base import (  # noqa: F401
  5 |     BaseModelConfig,
  6 |     APIRequest,
  7 |     APIResponse,
  8 |     ReqT,
  9 |     ExecutionMode,
 10 |     CollaboratorAuthPolicy,
 11 | )
 12 | 
 13 | # Import specific models
 14 | from .account import AccountDetailsRequest  # noqa: F401
 15 | from .applies import (  # noqa: F401
 16 |     ApplyStatus,
 17 |     ExecutionDetails as ApplyExecutionDetails,
 18 |     StatusTimestamps as ApplyStatusTimestamps,
 19 |     ApplyRequest,
 20 |     ApplyErroredStateRequest,
 21 | )
 22 | from .cost_estimates import (  # noqa: F401
 23 |     CostEstimateStatus,
 24 |     StatusTimestamps as CostEstimateStatusTimestamps,
 25 |     CostEstimateRequest,
 26 | )
 27 | from .organizations import (  # noqa: F401
 28 |     OrganizationDetailsRequest,
 29 |     OrganizationEntitlementsRequest,
 30 |     OrganizationDeleteRequest,
 31 |     OrganizationListRequest,
 32 |     OrganizationCreateRequest,
 33 |     OrganizationUpdateRequest,
 34 |     OrganizationParams,
 35 | )
 36 | from .plans import (  # noqa: F401
 37 |     PlanStatus,
 38 |     ExecutionDetails,
 39 |     StatusTimestamps,
 40 |     PlanRequest,
 41 |     PlanJsonOutputRequest,
 42 |     RunPlanJsonOutputRequest,
 43 | )
 44 | from .projects import (  # noqa: F401
 45 |     TagBinding,
 46 |     ProjectListRequest,
 47 |     BaseProjectRequest,
 48 |     ProjectCreateRequest,
 49 |     ProjectUpdateRequest,
 50 |     ProjectParams,
 51 |     ProjectTagBindingRequest,
 52 |     WorkspaceMoveRequest,
 53 | )
 54 | from .state_versions import (  # noqa: F401
 55 |     StateVersionStatus,
 56 |     StateVersionListRequest,
 57 |     StateVersionRequest,
 58 |     CurrentStateVersionRequest,
 59 |     StateVersionCreateRequest,
 60 |     StateVersionParams,
 61 | )
 62 | from .state_version_outputs import (  # noqa: F401
 63 |     StateVersionOutputListRequest,
 64 |     StateVersionOutputRequest,
 65 | )
 66 | from .variables import (  # noqa: F401
 67 |     VariableCategory,
 68 |     WorkspaceVariable,
 69 |     WorkspaceVariableParams,
 70 |     WorkspaceVariableCreateRequest,
 71 |     WorkspaceVariableUpdateRequest,
 72 |     VariableSet,
 73 |     VariableSetParams,
 74 |     VariableSetCreateRequest,
 75 |     VariableSetUpdateRequest,
 76 |     VariableSetVariable,
 77 |     VariableSetAssignmentRequest,
 78 |     VariableSetVariableParams,
 79 | )
 80 | from .runs import (  # noqa: F401
 81 |     RunOperation,
 82 |     RunStatus,
 83 |     RunSource,
 84 |     RunStatusGroup,
 85 |     RunVariable,
 86 |     RunListInWorkspaceRequest,
 87 |     RunListInOrganizationRequest,
 88 |     RunCreateRequest,
 89 |     RunActionRequest,
 90 |     RunParams,
 91 | )
 92 | from .workspaces import (  # noqa: F401
 93 |     VcsRepoConfig,
 94 |     WorkspaceListRequest,
 95 |     WorkspaceCreateRequest,
 96 |     WorkspaceUpdateRequest,
 97 |     WorkspaceParams,
 98 | )
 99 | 
100 | # Define __all__ to control what's imported with wildcard imports
101 | __all__ = [
102 |     # Base models
103 |     "BaseModelConfig",
104 |     "APIRequest",
105 |     "APIResponse",
106 |     "ReqT",
107 |     # Common enums
108 |     "CollaboratorAuthPolicy",
109 |     "ExecutionMode",
110 |     # Account models
111 |     "AccountDetailsRequest",
112 |     # Apply models
113 |     "ApplyStatus",
114 |     "ApplyExecutionDetails",
115 |     "ApplyStatusTimestamps",
116 |     "ApplyRequest",
117 |     "ApplyErroredStateRequest",
118 |     # Cost estimate models
119 |     "CostEstimateStatus",
120 |     "CostEstimateStatusTimestamps",
121 |     "CostEstimateRequest",
122 |     # Organization models
123 |     "OrganizationDetailsRequest",
124 |     "OrganizationEntitlementsRequest",
125 |     "OrganizationDeleteRequest",
126 |     "OrganizationListRequest",
127 |     "OrganizationCreateRequest",
128 |     "OrganizationUpdateRequest",
129 |     "OrganizationParams",
130 |     # Plan models
131 |     "PlanStatus",
132 |     "ExecutionDetails",
133 |     "StatusTimestamps",
134 |     "PlanRequest",
135 |     "PlanJsonOutputRequest",
136 |     "RunPlanJsonOutputRequest",
137 |     # Project models
138 |     "TagBinding",
139 |     "ProjectListRequest",
140 |     "BaseProjectRequest",
141 |     "ProjectCreateRequest",
142 |     "ProjectUpdateRequest",
143 |     "ProjectParams",
144 |     "ProjectTagBindingRequest",
145 |     "WorkspaceMoveRequest",
146 |     # Run models
147 |     "RunOperation",
148 |     "RunStatus",
149 |     "RunSource",
150 |     "RunStatusGroup",
151 |     "RunVariable",
152 |     "RunListInWorkspaceRequest",
153 |     "RunListInOrganizationRequest",
154 |     "RunCreateRequest",
155 |     "RunActionRequest",
156 |     "RunParams",
157 |     # State Version models
158 |     "StateVersionStatus",
159 |     "StateVersionListRequest",
160 |     "StateVersionRequest",
161 |     "CurrentStateVersionRequest",
162 |     "StateVersionCreateRequest",
163 |     "StateVersionParams",
164 |     # State Version Output models
165 |     "StateVersionOutputListRequest",
166 |     "StateVersionOutputRequest",
167 |     # Variable models
168 |     "VariableCategory",
169 |     "WorkspaceVariable",
170 |     "WorkspaceVariableParams",
171 |     "WorkspaceVariableCreateRequest",
172 |     "WorkspaceVariableUpdateRequest",
173 |     "VariableSet",
174 |     "VariableSetParams",
175 |     "VariableSetCreateRequest",
176 |     "VariableSetUpdateRequest",
177 |     "VariableSetVariable",
178 |     "VariableSetAssignmentRequest",
179 |     "VariableSetVariableParams",
180 |     # Workspace models
181 |     "VcsRepoConfig",
182 |     "WorkspaceListRequest",
183 |     "WorkspaceCreateRequest",
184 |     "WorkspaceUpdateRequest",
185 |     "WorkspaceParams",
186 | ]
187 | 
```

--------------------------------------------------------------------------------
/terraform_cloud_mcp/models/plans.py:
--------------------------------------------------------------------------------

```python
  1 | """Plan models for Terraform Cloud API
  2 | 
  3 | This module contains models for Terraform Cloud plan-related requests.
  4 | Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans
  5 | """
  6 | 
  7 | from enum import Enum
  8 | from typing import Optional
  9 | 
 10 | from pydantic import Field
 11 | 
 12 | from .base import APIRequest
 13 | 
 14 | 
 15 | class PlanStatus(str, Enum):
 16 |     """Status options for plans in Terraform Cloud.
 17 | 
 18 |     Defines the various states a plan can be in during its lifecycle:
 19 |     - PENDING: Plan has not yet started
 20 |     - MANAGED_QUEUED/QUEUED: Plan is queued for execution
 21 |     - RUNNING: Plan is currently running
 22 |     - ERRORED: Plan has encountered an error
 23 |     - CANCELED: Plan was canceled
 24 |     - FINISHED: Plan has completed successfully
 25 |     - UNREACHABLE: Plan is in an unreachable state
 26 | 
 27 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans
 28 | 
 29 |     See:
 30 |         docs/models/plan.md for reference
 31 |     """
 32 | 
 33 |     PENDING = "pending"
 34 |     MANAGED_QUEUED = "managed_queued"
 35 |     QUEUED = "queued"
 36 |     RUNNING = "running"
 37 |     ERRORED = "errored"
 38 |     CANCELED = "canceled"
 39 |     FINISHED = "finished"
 40 |     UNREACHABLE = "unreachable"
 41 | 
 42 | 
 43 | class ExecutionDetails(APIRequest):
 44 |     """Model for plan execution details.
 45 | 
 46 |     Represents execution mode specific details for a plan, including agent
 47 |     information when running in agent execution mode.
 48 | 
 49 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans
 50 | 
 51 |     See:
 52 |         docs/models/plan.md for reference
 53 |     """
 54 | 
 55 |     agent_id: Optional[str] = Field(
 56 |         None,
 57 |         alias="agent-id",
 58 |         description="ID of the agent that ran the plan",
 59 |     )
 60 |     agent_name: Optional[str] = Field(
 61 |         None,
 62 |         alias="agent-name",
 63 |         description="Name of the agent that ran the plan",
 64 |     )
 65 |     agent_pool_id: Optional[str] = Field(
 66 |         None,
 67 |         alias="agent-pool-id",
 68 |         description="ID of the agent pool the plan ran in",
 69 |     )
 70 |     agent_pool_name: Optional[str] = Field(
 71 |         None,
 72 |         alias="agent-pool-name",
 73 |         description="Name of the agent pool the plan ran in",
 74 |     )
 75 |     # Additional execution mode details can be added here
 76 | 
 77 | 
 78 | class StatusTimestamps(APIRequest):
 79 |     """Model for plan execution timestamps.
 80 | 
 81 |     Captures the timestamps for various stages in a plan's lifecycle.
 82 | 
 83 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans
 84 | 
 85 |     See:
 86 |         docs/models/plan.md for reference
 87 |     """
 88 | 
 89 |     queued_at: Optional[str] = Field(
 90 |         None,
 91 |         alias="queued-at",
 92 |         description="When the plan was queued",
 93 |     )
 94 |     pending_at: Optional[str] = Field(
 95 |         None,
 96 |         alias="pending-at",
 97 |         description="When the plan entered pending state",
 98 |     )
 99 |     started_at: Optional[str] = Field(
100 |         None,
101 |         alias="started-at",
102 |         description="When the plan execution started",
103 |     )
104 |     finished_at: Optional[str] = Field(
105 |         None,
106 |         alias="finished-at",
107 |         description="When the plan execution completed",
108 |     )
109 | 
110 | 
111 | class PlanRequest(APIRequest):
112 |     """Request model for retrieving a plan.
113 | 
114 |     Used to validate the plan ID parameter for API requests.
115 | 
116 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans#show-a-plan
117 | 
118 |     See:
119 |         docs/models/plan.md for reference
120 |     """
121 | 
122 |     plan_id: str = Field(
123 |         ...,
124 |         # No alias needed as field name matches API parameter
125 |         description="The ID of the plan to retrieve",
126 |         pattern=r"^plan-[a-zA-Z0-9]{16}$",  # Standard plan ID pattern
127 |     )
128 | 
129 | 
130 | class PlanJsonOutputRequest(APIRequest):
131 |     """Request model for retrieving a plan's JSON output.
132 | 
133 |     Used to validate the plan ID parameter for JSON output API requests.
134 | 
135 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans#retrieve-the-json-execution-plan
136 | 
137 |     See:
138 |         docs/models/plan.md for reference
139 |     """
140 | 
141 |     plan_id: str = Field(
142 |         ...,
143 |         # No alias needed as field name matches API parameter
144 |         description="The ID of the plan to retrieve JSON output for",
145 |         pattern=r"^plan-[a-zA-Z0-9]{16}$",  # Standard plan ID pattern
146 |     )
147 | 
148 | 
149 | class RunPlanJsonOutputRequest(APIRequest):
150 |     """Request model for retrieving a run's plan JSON output.
151 | 
152 |     Used to validate the run ID parameter for JSON output API requests.
153 | 
154 |     Reference: https://developer.hashicorp.com/terraform/cloud-docs/api-docs/plans#retrieve-the-json-execution-plan-from-a-run
155 | 
156 |     See:
157 |         docs/models/plan.md for reference
158 |     """
159 | 
160 |     run_id: str = Field(
161 |         ...,
162 |         # No alias needed as field name matches API parameter
163 |         description="The ID of the run to retrieve plan JSON output for",
164 |         pattern=r"^run-[a-zA-Z0-9]{16}$",  # Standard run ID pattern
165 |     )
166 | 
167 | 
168 | # Response handling is implemented through raw dictionaries
169 | 
```
Page 1/4FirstPrevNextLast