Skip to content

Commit d1331bc

Browse files
committed
'openstack floating *' CLI 기능 모두 구현
1 parent 294486d commit d1331bc

File tree

5 files changed

+657
-38
lines changed

5 files changed

+657
-38
lines changed

README.md

Lines changed: 25 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@
1919
-**OpenStack SDK Integration**: Direct integration with OpenStack SDK for real-time cluster operations.
2020
-**Production-Safe Operations**: Built-in safety controls with `ALLOW_MODIFY_OPERATIONS` environment variable to prevent modification operations in production environments.
2121
-**Comprehensive Monitoring**: Enhanced cluster status reports with hypervisor health, resource utilization, and health scoring.
22-
-**Complete Service Coverage**: 65+ comprehensive tools covering Identity, Compute, Network, Storage, Image, Orchestration, Load Balancer, and Monitoring services.
22+
-**Complete Service Coverage**: 90+ comprehensive tools covering Identity, Compute, Network, Storage, Image, Orchestration, Load Balancer, and Monitoring services.
2323
-**Advanced Instance Management**: Enhanced server lifecycle operations with backup, migration, rescue, and administrative functions.
2424
-**Server Event Tracking**: Detailed server event history and lifecycle monitoring with comprehensive logging.
2525
-**Hypervisor Monitoring**: Real-time hypervisor resource statistics with utilization tracking and cluster totals.
@@ -54,7 +54,7 @@
5454

5555
**Detailed Mapping by Category**
5656

57-
### 1. 🖥️ **Compute (Nova) - 95% Implementation**
57+
### 1. 🖥️ **Compute (Nova)**
5858

5959
| OpenStack CLI Command | MCP Tool | Status | Notes |
6060
|---------------------|---------|------|------|
@@ -106,19 +106,31 @@
106106
| `openstack hypervisor list` | `get_hypervisor_details` || Hypervisor querying |
107107
| `openstack availability zone list` | `get_availability_zones` || Availability zone listing |
108108

109-
### 2. 🌐 **Network (Neutron) - 80% Implementation**
109+
### 2. 🌐 **Network (Neutron)**
110110

111111
| OpenStack CLI Command | MCP Tool | Status | Notes |
112112
|---------------------|---------|------|------|
113113
| `openstack network list` | `get_network_details` || Detailed network information |
114114
| `openstack network show` | `get_network_details` (name param) || Specific network query |
115-
| `openstack network create/delete` | (Not yet implemented) | 🚧 | Network creation/deletion |
115+
| `openstack network create` | `set_networks` (action="create") || Network creation |
116+
| `openstack network delete` | `set_networks` (action="delete") || Network deletion |
117+
| `openstack network set` | `set_networks` (action="update") || Network property updates |
116118
| `openstack subnet list` | `get_network_details` (includes subnets) || Subnet information included |
117119
| `openstack subnet create/delete` | `set_subnets` || Subnet management |
118120
| `openstack router list` | `get_routers` || Router listing |
119121
| `openstack router create/delete` | (Not yet implemented) | 🚧 | Router management |
120122
| `openstack floating ip list` | `get_floating_ips` || Floating IP listing |
121-
| `openstack floating ip create/delete` | `set_floating_ip` || Floating IP management |
123+
| `openstack floating ip create` | `set_floating_ip` (action="create") || Floating IP creation |
124+
| `openstack floating ip delete` | `set_floating_ip` (action="delete") || Floating IP deletion |
125+
| `openstack floating ip set` | `set_floating_ip` (action="set") || Floating IP property setting |
126+
| `openstack floating ip show` | `set_floating_ip` (action="show") || Floating IP details |
127+
| `openstack floating ip unset` | `set_floating_ip` (action="unset") || Floating IP property clearing |
128+
| `openstack floating ip pool list` | `get_floating_ip_pools` || Floating IP pool listing |
129+
| `openstack floating ip port forwarding create` | `set_floating_ip_port_forwarding` (action="create") || Port forwarding creation |
130+
| `openstack floating ip port forwarding delete` | `set_floating_ip_port_forwarding` (action="delete") || Port forwarding deletion |
131+
| `openstack floating ip port forwarding list` | `set_floating_ip_port_forwarding` (action="list") || Port forwarding listing |
132+
| `openstack floating ip port forwarding set` | `set_floating_ip_port_forwarding` (action="set") || Port forwarding updates |
133+
| `openstack floating ip port forwarding show` | `set_floating_ip_port_forwarding` (action="show") || Port forwarding details |
122134
| `openstack security group list` | `get_security_groups` || Security group listing |
123135
| `openstack security group create/delete` | (Not yet implemented) | 🚧 | Security group management |
124136
| `openstack port list` | `get_network_details` (includes ports) || Port information included |
@@ -128,7 +140,7 @@
128140
| `openstack network agent list` | `get_service_status` (includes agents) || Network agents |
129141
| `openstack network agent set` | `set_network_agents` || Network agent management |
130142

131-
### 3. 💾 **Storage (Cinder) - 90% Implementation**
143+
### 3. 💾 **Storage (Cinder)**
132144

133145
| OpenStack CLI Command | MCP Tool | Status | Notes |
134146
|---------------------|---------|------|------|
@@ -150,13 +162,13 @@
150162
| `openstack volume qos list` | (Not yet implemented) | 🚧 | QoS listing |
151163
| `openstack volume qos create` | `set_volume_qos` || QoS management |
152164

153-
### 4. 🖼️ **Image (Glance) - 75% Implementation**
165+
### 4. 🖼️ **Image (Glance)**
154166

155167
| OpenStack CLI Command | MCP Tool | Status | Notes |
156168
|---------------------|---------|------|------|
157169
| `openstack image list` | `get_image_detail_list` || Image listing |
158170
| `openstack image show` | `get_image_detail_list` (filtering) || Specific image query |
159-
| `openstack image create` | `set_image` (action="create") || Image creation |
171+
| `openstack image create` | `set_image` (action="create") || Enhanced image creation with min_disk, min_ram, properties |
160172
| `openstack image delete` | `set_image` (action="delete") || Image deletion |
161173
| `openstack image set` | `set_image` (action="update") || Image property modification |
162174
| `openstack image save` | `set_image` (action="save") || Image download |
@@ -166,7 +178,7 @@
166178
| `openstack image set --property` | `set_image_metadata` || Image metadata |
167179
| `openstack image set --public/private` | `set_image_visibility` || Image visibility setting |
168180

169-
### 5. 👥 **Identity (Keystone) - 70% Implementation**
181+
### 5. 👥 **Identity (Keystone)**
170182

171183
| OpenStack CLI Command | MCP Tool | Status | Notes |
172184
|---------------------|---------|------|------|
@@ -187,7 +199,7 @@
187199
| `openstack service create/delete` | `set_services` || Service management |
188200
| `openstack endpoint list` | `get_service_status` (includes endpoints) || Endpoint information |
189201

190-
### 6. 🔥 **Orchestration (Heat) - 40% Implementation**
202+
### 6. 🔥 **Orchestration (Heat)**
191203

192204
| OpenStack CLI Command | MCP Tool | Status | Notes |
193205
|---------------------|---------|------|------|
@@ -202,9 +214,7 @@
202214
| `openstack stack template show` | (Not yet implemented) | 🚧 | Template query |
203215
| `openstack stack output list` | (Not yet implemented) | 🚧 | Stack output listing |
204216

205-
### 7. ⚖️ **Load Balancer (Octavia) - 96% Implementation**
206-
207-
**🎉 Major Update: Comprehensive LoadBalancer implementation now covers 79/82 CLI commands (96% coverage)**
217+
### 7. ⚖️ **Load Balancer (Octavia)**
208218

209219
| OpenStack CLI Command | MCP Tool | Status | Notes |
210220
|---------------------|---------|------|------|
@@ -298,7 +308,7 @@
298308
| `openstack loadbalancer quota set` | `set_load_balancer_quota` (action="set") || Quota setting |
299309
| `openstack loadbalancer quota reset` | `set_load_balancer_quota` (action="reset") || Quota reset |
300310

301-
### 8. 📊 **Monitoring & Logging - 60% Implementation**
311+
### 8. 📊 **Monitoring & Logging**
302312

303313
| OpenStack CLI Command | MCP Tool | Status | Notes |
304314
|---------------------|---------|------|------|
@@ -311,7 +321,7 @@
311321
| Compute agents | `set_compute_agents` || Compute agent management |
312322
| Usage statistics | `get_usage_statistics` || Usage statistics |
313323

314-
### 9. 📏 **Usage & Quota - 80% Implementation**
324+
### 9. 📏 **Usage & Quota**
315325

316326
| OpenStack CLI Command | MCP Tool | Status | Notes |
317327
|---------------------|---------|------|------|

src/mcp_openstack_ops/functions.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -927,7 +927,9 @@ def set_compute_agents(
927927
get_network_details,
928928
get_security_groups,
929929
get_floating_ips,
930+
get_floating_ip_pools,
930931
set_floating_ip,
932+
set_floating_ip_port_forwarding,
931933
get_routers,
932934
set_networks,
933935
set_network_ports,

src/mcp_openstack_ops/mcp_main.py

Lines changed: 150 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,8 @@
5656
set_network_ports as _set_network_ports,
5757
set_networks as _set_networks,
5858
set_subnets as _set_subnets,
59+
get_floating_ip_pools as _get_floating_ip_pools,
60+
set_floating_ip_port_forwarding as _set_floating_ip_port_forwarding,
5961
set_network_qos_policies as _set_network_qos_policies,
6062
set_network_agents as _set_network_agents,
6163
# Load Balancer (Octavia) functions
@@ -1741,39 +1743,59 @@ async def get_floating_ips() -> str:
17411743

17421744

17431745
@conditional_tool
1744-
async def set_floating_ip(action: str, floating_network_id: str = "", port_id: str = "", floating_ip_id: str = "") -> str:
1746+
async def set_floating_ip(action: str, floating_network_id: str = "", port_id: str = "", floating_ip_id: str = "",
1747+
floating_ip_address: str = "", description: str = "") -> str:
17451748
"""
1746-
Manage floating IPs (create, delete, associate, disassociate).
1749+
Manage floating IPs (create, delete, associate, disassociate, set, show, unset, list).
17471750
17481751
Functions:
1749-
- Create new floating IPs from external networks
1750-
- Delete existing floating IPs
1752+
- Create new floating IPs from external networks (allocate)
1753+
- Delete existing floating IPs (release)
17511754
- Associate floating IPs with instance ports
17521755
- Disassociate floating IPs from instances
1756+
- Set floating IP properties (description, fixed IP)
1757+
- Show detailed floating IP information
1758+
- Unset floating IP properties (clear description)
1759+
- List all floating IPs
17531760
17541761
Use when user requests floating IP management, external connectivity setup, or IP allocation tasks.
17551762
17561763
Args:
1757-
action: Action to perform (create, delete, associate, disassociate)
1758-
floating_network_id: ID of external network for create action (optional)
1759-
port_id: Port ID for association operations (optional)
1760-
floating_ip_id: Floating IP ID for delete/associate/disassociate actions (optional)
1764+
action: Action to perform (create/allocate, delete/release, associate, disassociate, set, show, unset, list)
1765+
floating_network_id: ID of external network for create action
1766+
port_id: Port ID for association operations
1767+
floating_ip_id: Floating IP ID for operations
1768+
floating_ip_address: Floating IP address (alternative to floating_ip_id)
1769+
description: Description for the floating IP (for set action)
17611770
17621771
Returns:
17631772
Result of floating IP management operation in JSON format.
17641773
"""
17651774
try:
17661775
logger.info(f"Managing floating IP with action '{action}'")
17671776

1777+
# Map CLI-style actions to internal actions
1778+
action_map = {
1779+
'create': 'allocate',
1780+
'delete': 'release',
1781+
'allocate': 'allocate',
1782+
'release': 'release'
1783+
}
1784+
internal_action = action_map.get(action.lower(), action.lower())
1785+
17681786
kwargs = {}
17691787
if floating_network_id.strip():
17701788
kwargs['floating_network_id'] = floating_network_id.strip()
17711789
if port_id.strip():
17721790
kwargs['port_id'] = port_id.strip()
17731791
if floating_ip_id.strip():
17741792
kwargs['floating_ip_id'] = floating_ip_id.strip()
1793+
if floating_ip_address.strip():
1794+
kwargs['floating_ip_address'] = floating_ip_address.strip()
1795+
if description.strip():
1796+
kwargs['description'] = description.strip()
17751797

1776-
result_data = _set_floating_ip(action, **kwargs)
1798+
result_data = _set_floating_ip(internal_action, **kwargs)
17771799

17781800
result = {
17791801
"timestamp": datetime.now().isoformat(),
@@ -1790,6 +1812,125 @@ async def set_floating_ip(action: str, floating_network_id: str = "", port_id: s
17901812
return error_msg
17911813

17921814

1815+
@mcp.tool()
1816+
async def get_floating_ip_pools() -> str:
1817+
"""
1818+
Get list of floating IP pools (external networks).
1819+
1820+
Functions:
1821+
- List all external networks that can provide floating IPs
1822+
- Show available and used IP counts for each pool
1823+
- Display network configuration for floating IP allocation
1824+
- Provide pool capacity and utilization information
1825+
1826+
Use when user requests:
1827+
- "Show floating IP pools"
1828+
- "List available floating IP networks"
1829+
- "Check floating IP capacity"
1830+
- "What external networks are available?"
1831+
1832+
Returns:
1833+
List of floating IP pools with capacity information in JSON format.
1834+
"""
1835+
try:
1836+
result_data = _get_floating_ip_pools()
1837+
1838+
result = {
1839+
"timestamp": datetime.now().isoformat(),
1840+
"pools": result_data,
1841+
"total_pools": len(result_data)
1842+
}
1843+
1844+
return json.dumps(result, indent=2)
1845+
1846+
except Exception as e:
1847+
error_msg = f"Error: Failed to get floating IP pools - {str(e)}"
1848+
logger.error(error_msg)
1849+
return error_msg
1850+
1851+
1852+
@conditional_tool
1853+
async def set_floating_ip_port_forwarding(
1854+
action: str,
1855+
floating_ip_id: str = "",
1856+
floating_ip_address: str = "",
1857+
port_forwarding_id: str = "",
1858+
protocol: str = "tcp",
1859+
external_port: int = 0,
1860+
internal_port: int = 0,
1861+
internal_ip_address: str = "",
1862+
internal_port_id: str = "",
1863+
description: str = ""
1864+
) -> str:
1865+
"""
1866+
Manage floating IP port forwarding rules for NAT translation.
1867+
1868+
Functions:
1869+
- Create port forwarding rules to redirect external traffic to internal IPs
1870+
- Delete existing port forwarding rules
1871+
- List all port forwarding rules for a floating IP
1872+
- Show detailed configuration of specific port forwarding rule
1873+
- Update port forwarding settings (description, internal target)
1874+
1875+
Use when user requests:
1876+
- "Create port forwarding rule for floating IP [ip] from port [ext] to [int:internal]"
1877+
- "Delete port forwarding rule [id] from floating IP [ip]"
1878+
- "List port forwarding rules for floating IP [ip]"
1879+
- "Show port forwarding rule [id] details"
1880+
- "Update port forwarding rule [id] description to [text]"
1881+
1882+
Args:
1883+
action: Action to perform (create, delete, list, show, set)
1884+
floating_ip_id: Floating IP ID (alternative to floating_ip_address)
1885+
floating_ip_address: Floating IP address (alternative to floating_ip_id)
1886+
port_forwarding_id: Port forwarding rule ID (for delete/show/set actions)
1887+
protocol: Protocol for port forwarding (tcp, udp, icmp) - default: tcp
1888+
external_port: External port number (for create action)
1889+
internal_port: Internal port number (for create action)
1890+
internal_ip_address: Internal IP address target (for create/set actions)
1891+
internal_port_id: Internal port ID target (optional)
1892+
description: Description for the port forwarding rule
1893+
1894+
Returns:
1895+
Result of port forwarding management operation in JSON format.
1896+
"""
1897+
try:
1898+
logger.info(f"Managing floating IP port forwarding with action '{action}'")
1899+
1900+
kwargs = {
1901+
'floating_ip_id': floating_ip_id.strip() if floating_ip_id.strip() else None,
1902+
'floating_ip_address': floating_ip_address.strip() if floating_ip_address.strip() else None,
1903+
'port_forwarding_id': port_forwarding_id.strip() if port_forwarding_id.strip() else None,
1904+
'protocol': protocol.lower() if protocol.strip() else 'tcp',
1905+
'description': description.strip() if description.strip() else None
1906+
}
1907+
1908+
if external_port > 0:
1909+
kwargs['external_port'] = external_port
1910+
if internal_port > 0:
1911+
kwargs['internal_port'] = internal_port
1912+
if internal_ip_address.strip():
1913+
kwargs['internal_ip_address'] = internal_ip_address.strip()
1914+
if internal_port_id.strip():
1915+
kwargs['internal_port_id'] = internal_port_id.strip()
1916+
1917+
result_data = _set_floating_ip_port_forwarding(action, **kwargs)
1918+
1919+
result = {
1920+
"timestamp": datetime.now().isoformat(),
1921+
"action": action,
1922+
"parameters": kwargs,
1923+
"result": result_data
1924+
}
1925+
1926+
return json.dumps(result, indent=2)
1927+
1928+
except Exception as e:
1929+
error_msg = f"Error: Failed to manage floating IP port forwarding - {str(e)}"
1930+
logger.error(error_msg)
1931+
return error_msg
1932+
1933+
17931934
@mcp.tool()
17941935
async def get_routers() -> str:
17951936
"""

0 commit comments

Comments
 (0)