25 Commits

Author SHA1 Message Date
ebbf2c297c docs: add Docker Compose setup for OAuth multi-user mode
- Update Dockerfile to default to streamable-http transport
- Add docker-compose.oauth-standalone.yml for existing OIDC providers
- Add .env.oauth.example template with all required settings
- Update README_DOCKER.md with OAuth deployment instructions

OAuth mode requires streamable-http transport (not stdio) since
authentication happens via browser redirect flow.
2026-01-12 14:40:50 -07:00
1d9fcf73af release: v0.2.2 - OAuth claims extraction fix
- Fix OAuth user/group extraction using FastMCP's get_access_token()
- Update README with correct RBAC group names (vsphere-readers, not viewers)
- Add missing vsphere-host-admins group to documentation
v0.2.2
2025-12-28 12:50:57 -07:00
79d2caef45 fix: use FastMCP get_access_token() for OAuth claims extraction
The previous implementation tried to access OAuth token claims via
context.request_context.access_token.claims, which doesn't exist in
FastMCP's context structure.

FastMCP stores access tokens in Python's ContextVars, accessible via
the get_access_token() dependency function. This fix updates both
extract_user_from_context() and RBACMiddleware._extract_user_from_context()
to use this correct approach.

Before: Users appeared as "anonymous" with no groups (RBAC denied all)
After: User identity and groups correctly extracted from OAuth claims
2025-12-28 11:15:28 -07:00
ab83c70c31 docs: update OAuth/RBAC architecture documentation
Rewrites the architecture doc from design proposal to implementation
reference. Documents the complete RBAC system including:

- 5 permission levels (READ_ONLY → FULL_ADMIN)
- 5 OAuth groups with permission mappings
- RBACMiddleware implementation details
- Audit log format with user identity
- Configuration environment variables
- OIDC provider setup (Authentik example)
- Troubleshooting guide for common issues

Updates implementation checklist to reflect completed status.
2025-12-27 08:22:02 -07:00
00857b1840 fix: enforce strict RBAC - deny access for users without groups
Security fix: Previously users with no OAuth groups or unrecognized
groups would default to READ_ONLY access. Now:
- Empty groups = no permissions (denied access to all tools)
- Unrecognized groups = no permissions (denied access)

Also adds missing restart_service mapping to FULL_ADMIN permission.
2025-12-27 08:10:01 -07:00
6159098963 feat: implement RBAC middleware for OAuth group-based permissions
Add RBACMiddleware that integrates with FastMCP's middleware system to
enforce role-based access control on all tool calls:

- Intercepts every tool call via on_call_tool() hook
- Extracts user groups from OAuth token claims
- Checks permissions using existing permissions.py mappings
- Logs all tool invocations with user identity via audit.py
- Denies access with clear PermissionDeniedError when unauthorized

Permission levels (from permissions.py):
- READ_ONLY: view operations (vsphere-readers)
- POWER_OPS: power/snapshot ops (vsphere-operators)
- VM_LIFECYCLE: create/delete VMs (vsphere-admins)
- HOST_ADMIN: ESXi host management (vsphere-host-admins)
- FULL_ADMIN: guest ops, services (vsphere-super-admins)

Middleware only enabled when OAuth is active (OAUTH_ENABLED=true).
STDIO mode continues to work without permission checking.
2025-12-27 07:37:26 -07:00
0e29fea857 docs: add OAuth multi-user mode to README
- Add Multi-User / OAuth Mode section with quick setup
- Document permission groups for RBAC
- Update transport option to streamable-http
- Link to OAUTH-ARCHITECTURE.md for details
2025-12-27 06:03:59 -07:00
4890950e19 Merge branch 'feature/oauth-authentication'
OAuth 2.1 + PKCE authentication for mcvsphere MCP server.

Features:
- OIDC integration via FastMCP's OIDCProxy
- Authentik identity provider support
- Dynamic Client Registration for MCP clients
- PKCE flow for secure authorization
- Permission groups mapped from Authentik groups
- Audit logging with user identity

Tested end-to-end with Claude Code CLI.
2025-12-27 05:54:57 -07:00
64ba7a69de fix OAuth token validation for Authentik opaque tokens
- Remove required_scopes validation (Authentik doesn't embed scopes in JWT)
- Add oauth_base_url config for proper HTTPS callback URLs
- Add docker-compose.dev.yml for host proxy via Caddy
- Update docker-compose.oauth.yml with unique domain label

Authentik uses opaque access tokens that don't include scope claims.
Authentication is enforced at the IdP level, so scope validation in
the token is unnecessary and was causing 401 errors.
2025-12-27 05:27:21 -07:00
cda49f2912 implement OAuth authentication with Authentik support
Core OAuth infrastructure:
- permissions.py: 5-level permission model (read_only → full_admin)
  Maps all 94 tools to permission levels
  Maps OAuth groups to permission sets
- audit.py: Centralized logging with OAuth user identity
- auth.py: OIDCProxy configuration for Authentik/OIDC providers
- middleware.py: Permission checking decorator and tool wrapper

Server integration:
- config.py: Add OAuth settings (oauth_enabled, oauth_issuer_url, etc.)
  Validate OAuth config completeness, require HTTP transport
- server.py: Integrate auth provider, add HTTP transport support
  Show OAuth status in startup banner

Deployment:
- docker-compose.oauth.yml: Authentik stack (server, worker, postgres, redis)
- .env.example: Document all OAuth and Authentik environment variables

Permission model:
- vsphere-readers: READ_ONLY (32 tools)
- vsphere-operators: + POWER_OPS (14 tools)
- vsphere-admins: + VM_LIFECYCLE (33 tools)
- vsphere-host-admins: + HOST_ADMIN (6 tools)
- vsphere-super-admins: + FULL_ADMIN (9 tools)
2025-12-27 01:12:58 -07:00
f843a8a161 add OAuth architecture design document
- Service Account + OAuth Audit model for vCenter integration
- Authentik as OIDC provider with JWT validation
- Permission escalation based on OAuth groups
- Credential broker pattern for user mapping
- Implementation checklist and environment variables
2025-12-27 00:53:24 -07:00
d0aa37e9c3 bump version to 0.2.1 for PyPI README update 2025-12-26 21:04:28 -07:00
7843adede1 rewrite README for PyPI with confident, direct style
- Bold opening: 94 tools, full VMware control
- Clear install instructions upfront
- Organized tool documentation with tables
- Real-world usage examples
- Streamlined configuration reference
2025-12-26 21:03:51 -07:00
eb59cd5e9a rename project: esxi-mcp-server → mcvsphere
mcvsphere = Model Control for vSphere

Updates:
- Package renamed from esxi_mcp_server to mcvsphere
- CLI entry point: mcvsphere (was esxi-mcp-server)
- All imports and references updated
- Docker configs updated
- Test suites updated
2025-12-26 20:58:48 -07:00
c65f91c571 add extended test suite for 22 additional tools
New test_extended.py covers:
- Console tools: vm_screenshot, wait_for_vm_tools, get_vm_tools_status
- Serial port: setup, get, connect, clear, remove
- Guest operations: run_command, list/create/delete directory, read/write/delete file
- Power control: reboot_guest, reset_vm, shutdown_guest
- Snapshots: revert_to_current, delete_all
- VM hardware: change_nic_network, set_nic_mac, clone_vm

Test coverage improved from 61% to 79% (75/94 tools)
2025-12-26 19:13:19 -07:00
8e28b84e59 add console and serial port mixins, expand to 94 tools
New features:
- ConsoleMixin: vm_screenshot, wait_for_vm_tools, get_vm_tools_status
- SerialPortMixin: setup_serial_port, get_serial_port, connect_serial_port,
  clear_serial_port, remove_serial_port

Enables:
- VM console screenshots via vSphere HTTP API
- VMware Tools status monitoring and wait utilities
- Network serial ports for headless VMs and network appliances

README rewritten with comprehensive documentation of all 94 tools.
2025-12-26 18:44:09 -07:00
d771db2e1d fix list_guest_directory for varying guest OS attributes
FileInfo attributes (owner, modificationTime, size, type) vary across
guest OS types. Use getattr with defaults to prevent AttributeError
when these optional fields are missing.
2025-12-26 18:26:55 -07:00
7918a78bfa add comprehensive test suites and fix VM creation
- Fix create_vm: add required files property to ConfigSpec
- Fix disk backing: use fileName instead of datastore reference
- test_client.py: comprehensive read-only test suite (86 tools, 6 resources)
- test_destructive.py: destructive test suite covering 29 operations:
  - VM lifecycle (create, info, rename, reconfigure)
  - Power operations (on, suspend, off)
  - Disk management (add, list, extend, remove)
  - NIC management (add, list, connect, remove)
  - Snapshots (create, list, rename, revert, delete)
  - Folder operations (create, move VM)
  - Datastore operations (create folder, delete)
  - vCenter advanced (storage_vmotion, convert_to_template,
    deploy_from_template, convert_to_vm)
2025-12-26 08:52:33 -07:00
b9c411fdf9 add idempotentHint to safe-to-retry vCenter tools
Mark tools that handle already-in-target-state gracefully:
- storage_vmotion: returns "no_migration_needed" if already on target
- convert_to_template: returns "already_template" if already converted
- convert_to_vm: returns "already_vm" if already a VM

This signals to LLM clients that these operations are safe to retry.
2025-12-26 06:23:35 -07:00
359167ec6a add vCenter-specific operations mixin
VCenterOpsMixin provides tools that require vCenter Server:

Storage vMotion:
- storage_vmotion: Move VM disks to different datastore
- move_vm_disk: Move specific disk to different datastore

Template Management:
- convert_to_template: Convert VM to template
- convert_to_vm: Convert template back to VM
- deploy_from_template: Deploy new VM from template

Folder Organization:
- list_folders: List VM folders in datacenter
- create_folder: Create new VM folder
- move_vm_to_folder: Move VM to different folder

Tasks & Events:
- list_recent_tasks: List recent vCenter tasks
- list_recent_events: List recent vCenter events

Cluster Operations:
- list_clusters: List clusters with DRS/HA status
- get_drs_recommendations: Get DRS recommendations for cluster

Also fixes empty-list serialization issue in FastMCP by returning
informative messages when results are empty.

Total: 86 tools, 6 resources
2025-12-26 06:03:19 -07:00
9e39c1c678 Refactor to modular mixin architecture with 74 tools
Major refactoring from monolithic server.py to modular MCPMixin pattern:

Architecture:
- src/esxi_mcp_server/ package with proper src-layout
- FastMCP MCPMixin pattern for tool organization
- Separate mixins for each functional area
- Shared VMwareConnection class with lazy datastore/network lookup

New Mixins Added:
- DiskManagementMixin: add_disk, remove_disk, extend_disk, list_disks,
  attach_iso, detach_iso
- NICManagementMixin: add_nic, remove_nic, change_nic_network,
  connect_nic, set_nic_mac, list_nics
- HostManagementMixin: get_host_info, enter/exit_maintenance_mode,
  list_services, start/stop_service, set_service_policy,
  get/configure_ntp, reboot_host, shutdown_host, get_host_hardware,
  get_host_networking
- OVFManagementMixin: deploy_ovf, export_vm_ovf, list_ovf_networks
- ResourcesMixin: Added move_datastore_file, copy_datastore_file

Streaming Support:
- Generator-based streaming for datastore downloads
- Memory-efficient large file handling with save_to parameter
- Chunked uploads from disk

Testing:
- test_client.py: MCP SDK-based test client
- Validates all 74 tools against real ESXi host

Build System:
- pyproject.toml with uv, ruff configuration
- Docker dev/prod modes with hot-reload
- Updated Makefile for uv-based workflow
2025-12-26 05:53:51 -07:00
bright8192
a2f4c709c5 add docker support 2025-07-01 17:22:45 +08:00
bright8192
7b12024005 typo fix 2025-03-13 17:22:21 +08:00
bright8192
694d221a30 v0.0.1 2025-03-13 17:13:21 +08:00
Bright8192
ba0e03495b
Initial commit 2025-03-13 17:10:34 +08:00