Initial commit: MCP Hub Community Edition v3.0.0
Community edition generated from private repo via sync pipeline. Includes 9 plugins (WordPress, WooCommerce, WP Advanced, Gitea, n8n, Supabase, OpenPanel, Appwrite, Directus) with ~587 tools. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
143
tests/legacy/test_access_fix.py
Normal file
143
tests/legacy/test_access_fix.py
Normal file
@@ -0,0 +1,143 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
Test API Key Access Control Fix
|
||||
|
||||
Validates that:
|
||||
1. Site-level keys get proper error message for system tools (not validation failure)
|
||||
2. Global keys work for all tools
|
||||
3. Per-project keys work for their own unified tools
|
||||
"""
|
||||
|
||||
|
||||
def test_system_tool_detection():
|
||||
"""Test that system tools are detected correctly."""
|
||||
SYSTEM_TOOLS = [
|
||||
"list_projects",
|
||||
"get_project_info",
|
||||
"check_all_projects_health",
|
||||
"get_project_health",
|
||||
"get_system_metrics",
|
||||
"get_system_uptime",
|
||||
"get_rate_limit_stats",
|
||||
"export_health_metrics",
|
||||
"manage_api_keys_list",
|
||||
"manage_api_keys_get_info",
|
||||
]
|
||||
|
||||
# Test with and without MCP prefix
|
||||
test_cases = [
|
||||
("list_projects", True),
|
||||
("mcp__coolify-projects__list_projects", True),
|
||||
("get_project_info", True),
|
||||
("wordpress_list_posts", False),
|
||||
("woocommerce_list_orders", False),
|
||||
("unknown", False),
|
||||
]
|
||||
|
||||
for tool_name, expected in test_cases:
|
||||
is_system_tool = any(tool_name.endswith(st) for st in SYSTEM_TOOLS)
|
||||
assert (
|
||||
is_system_tool == expected
|
||||
), f"Failed for {tool_name}: expected {expected}, got {is_system_tool}"
|
||||
print(f"✓ {tool_name}: is_system_tool={is_system_tool}")
|
||||
|
||||
|
||||
def test_unified_tool_detection():
|
||||
"""Test that unified tools are detected correctly."""
|
||||
test_cases = [
|
||||
("wordpress_list_posts", True),
|
||||
("woocommerce_list_orders", True),
|
||||
("mcp__coolify-projects__wordpress_list_posts", True),
|
||||
("mcp__coolify-projects__woocommerce_list_orders", True),
|
||||
("list_projects", False),
|
||||
("get_project_info", False),
|
||||
("unknown", True), # Falls to fallback
|
||||
]
|
||||
|
||||
for tool_name, expected in test_cases:
|
||||
if tool_name == "unknown":
|
||||
is_unified_tool = True # Fallback
|
||||
else:
|
||||
is_unified_tool = (
|
||||
tool_name.startswith("wordpress_")
|
||||
or tool_name.startswith("woocommerce_")
|
||||
or tool_name.startswith("mcp__coolify-projects__wordpress_")
|
||||
or tool_name.startswith("mcp__coolify-projects__woocommerce_")
|
||||
)
|
||||
assert (
|
||||
is_unified_tool == expected
|
||||
), f"Failed for {tool_name}: expected {expected}, got {is_unified_tool}"
|
||||
print(f"✓ {tool_name}: is_unified_tool={is_unified_tool}")
|
||||
|
||||
|
||||
def test_skip_project_check_logic():
|
||||
"""Test that skip_project_check is set correctly."""
|
||||
SYSTEM_TOOLS = [
|
||||
"list_projects",
|
||||
"get_project_info",
|
||||
"check_all_projects_health",
|
||||
"get_project_health",
|
||||
"get_system_metrics",
|
||||
"get_system_uptime",
|
||||
"get_rate_limit_stats",
|
||||
"export_health_metrics",
|
||||
"manage_api_keys_list",
|
||||
"manage_api_keys_get_info",
|
||||
]
|
||||
|
||||
test_cases = [
|
||||
# (tool_name, expected_skip)
|
||||
("list_projects", True), # System tool
|
||||
("wordpress_list_posts", True), # Unified tool
|
||||
("woocommerce_list_orders", True), # Unified tool
|
||||
("mcp__coolify-projects__list_projects", True), # System tool with prefix
|
||||
("mcp__coolify-projects__wordpress_list_posts", True), # Unified tool with prefix
|
||||
("unknown", True), # Fallback to unified
|
||||
]
|
||||
|
||||
for tool_name, expected_skip in test_cases:
|
||||
# Determine is_system_tool
|
||||
is_system_tool = any(tool_name.endswith(st) for st in SYSTEM_TOOLS)
|
||||
|
||||
# Determine is_unified_tool
|
||||
if tool_name == "unknown":
|
||||
is_unified_tool = True
|
||||
else:
|
||||
is_unified_tool = (
|
||||
tool_name.startswith("wordpress_")
|
||||
or tool_name.startswith("woocommerce_")
|
||||
or tool_name.startswith("mcp__coolify-projects__wordpress_")
|
||||
or tool_name.startswith("mcp__coolify-projects__woocommerce_")
|
||||
)
|
||||
|
||||
# Calculate skip_project_check
|
||||
skip_project_check = is_unified_tool or is_system_tool
|
||||
|
||||
assert skip_project_check == expected_skip, (
|
||||
f"Failed for {tool_name}: expected skip={expected_skip}, got {skip_project_check} "
|
||||
f"(unified={is_unified_tool}, system={is_system_tool})"
|
||||
)
|
||||
print(
|
||||
f"✓ {tool_name}: skip_project_check={skip_project_check} (unified={is_unified_tool}, system={is_system_tool})"
|
||||
)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
print("\n=== Testing System Tool Detection ===")
|
||||
test_system_tool_detection()
|
||||
|
||||
print("\n=== Testing Unified Tool Detection ===")
|
||||
test_unified_tool_detection()
|
||||
|
||||
print("\n=== Testing skip_project_check Logic ===")
|
||||
test_skip_project_check_logic()
|
||||
|
||||
print("\n✅ All tests passed!")
|
||||
print("\nExpected behavior after fix:")
|
||||
print("1. Site-level key + list_projects → Validation passes, then gets proper error:")
|
||||
print(" 'System tools require global API key (project_id=\"*\")'")
|
||||
print(
|
||||
"2. Site-level key + wordpress_list_posts(site=other) → Validation passes, handler blocks with:"
|
||||
)
|
||||
print(" 'Access denied. This API key is restricted to project X'")
|
||||
print("3. Global key + any tool → Works")
|
||||
Reference in New Issue
Block a user