crackerjack 0.33.0__py3-none-any.whl → 0.33.1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of crackerjack might be problematic. Click here for more details.
- crackerjack/__main__.py +1350 -34
- crackerjack/adapters/__init__.py +17 -0
- crackerjack/adapters/lsp_client.py +358 -0
- crackerjack/adapters/rust_tool_adapter.py +194 -0
- crackerjack/adapters/rust_tool_manager.py +193 -0
- crackerjack/adapters/skylos_adapter.py +231 -0
- crackerjack/adapters/zuban_adapter.py +560 -0
- crackerjack/agents/base.py +7 -3
- crackerjack/agents/coordinator.py +271 -33
- crackerjack/agents/documentation_agent.py +9 -15
- crackerjack/agents/dry_agent.py +3 -15
- crackerjack/agents/formatting_agent.py +1 -1
- crackerjack/agents/import_optimization_agent.py +36 -180
- crackerjack/agents/performance_agent.py +17 -98
- crackerjack/agents/performance_helpers.py +7 -31
- crackerjack/agents/proactive_agent.py +1 -3
- crackerjack/agents/refactoring_agent.py +16 -85
- crackerjack/agents/refactoring_helpers.py +7 -42
- crackerjack/agents/security_agent.py +9 -48
- crackerjack/agents/test_creation_agent.py +356 -513
- crackerjack/agents/test_specialist_agent.py +0 -4
- crackerjack/api.py +6 -25
- crackerjack/cli/cache_handlers.py +204 -0
- crackerjack/cli/cache_handlers_enhanced.py +683 -0
- crackerjack/cli/facade.py +100 -0
- crackerjack/cli/handlers.py +224 -9
- crackerjack/cli/interactive.py +6 -4
- crackerjack/cli/options.py +642 -55
- crackerjack/cli/utils.py +2 -1
- crackerjack/code_cleaner.py +58 -117
- crackerjack/config/global_lock_config.py +8 -48
- crackerjack/config/hooks.py +53 -62
- crackerjack/core/async_workflow_orchestrator.py +24 -34
- crackerjack/core/autofix_coordinator.py +3 -17
- crackerjack/core/enhanced_container.py +4 -13
- crackerjack/core/file_lifecycle.py +12 -89
- crackerjack/core/performance.py +2 -2
- crackerjack/core/performance_monitor.py +15 -55
- crackerjack/core/phase_coordinator.py +104 -204
- crackerjack/core/resource_manager.py +14 -90
- crackerjack/core/service_watchdog.py +62 -95
- crackerjack/core/session_coordinator.py +149 -0
- crackerjack/core/timeout_manager.py +14 -72
- crackerjack/core/websocket_lifecycle.py +13 -78
- crackerjack/core/workflow_orchestrator.py +171 -174
- crackerjack/docs/INDEX.md +11 -0
- crackerjack/docs/generated/api/API_REFERENCE.md +10895 -0
- crackerjack/docs/generated/api/CLI_REFERENCE.md +109 -0
- crackerjack/docs/generated/api/CROSS_REFERENCES.md +1755 -0
- crackerjack/docs/generated/api/PROTOCOLS.md +3 -0
- crackerjack/docs/generated/api/SERVICES.md +1252 -0
- crackerjack/documentation/__init__.py +31 -0
- crackerjack/documentation/ai_templates.py +756 -0
- crackerjack/documentation/dual_output_generator.py +765 -0
- crackerjack/documentation/mkdocs_integration.py +518 -0
- crackerjack/documentation/reference_generator.py +977 -0
- crackerjack/dynamic_config.py +55 -50
- crackerjack/executors/async_hook_executor.py +10 -15
- crackerjack/executors/cached_hook_executor.py +117 -43
- crackerjack/executors/hook_executor.py +8 -34
- crackerjack/executors/hook_lock_manager.py +26 -183
- crackerjack/executors/individual_hook_executor.py +13 -11
- crackerjack/executors/lsp_aware_hook_executor.py +270 -0
- crackerjack/executors/tool_proxy.py +417 -0
- crackerjack/hooks/lsp_hook.py +79 -0
- crackerjack/intelligence/adaptive_learning.py +25 -10
- crackerjack/intelligence/agent_orchestrator.py +2 -5
- crackerjack/intelligence/agent_registry.py +34 -24
- crackerjack/intelligence/agent_selector.py +5 -7
- crackerjack/interactive.py +17 -6
- crackerjack/managers/async_hook_manager.py +0 -1
- crackerjack/managers/hook_manager.py +79 -1
- crackerjack/managers/publish_manager.py +44 -8
- crackerjack/managers/test_command_builder.py +1 -15
- crackerjack/managers/test_executor.py +1 -3
- crackerjack/managers/test_manager.py +98 -7
- crackerjack/managers/test_manager_backup.py +10 -9
- crackerjack/mcp/cache.py +2 -2
- crackerjack/mcp/client_runner.py +1 -1
- crackerjack/mcp/context.py +191 -68
- crackerjack/mcp/dashboard.py +7 -5
- crackerjack/mcp/enhanced_progress_monitor.py +31 -28
- crackerjack/mcp/file_monitor.py +30 -23
- crackerjack/mcp/progress_components.py +31 -21
- crackerjack/mcp/progress_monitor.py +50 -53
- crackerjack/mcp/rate_limiter.py +6 -6
- crackerjack/mcp/server_core.py +17 -16
- crackerjack/mcp/service_watchdog.py +2 -1
- crackerjack/mcp/state.py +4 -7
- crackerjack/mcp/task_manager.py +11 -9
- crackerjack/mcp/tools/core_tools.py +173 -32
- crackerjack/mcp/tools/error_analyzer.py +3 -2
- crackerjack/mcp/tools/execution_tools.py +8 -10
- crackerjack/mcp/tools/execution_tools_backup.py +42 -30
- crackerjack/mcp/tools/intelligence_tool_registry.py +7 -5
- crackerjack/mcp/tools/intelligence_tools.py +5 -2
- crackerjack/mcp/tools/monitoring_tools.py +33 -70
- crackerjack/mcp/tools/proactive_tools.py +24 -11
- crackerjack/mcp/tools/progress_tools.py +5 -8
- crackerjack/mcp/tools/utility_tools.py +20 -14
- crackerjack/mcp/tools/workflow_executor.py +62 -40
- crackerjack/mcp/websocket/app.py +8 -0
- crackerjack/mcp/websocket/endpoints.py +352 -357
- crackerjack/mcp/websocket/jobs.py +40 -57
- crackerjack/mcp/websocket/monitoring_endpoints.py +2935 -0
- crackerjack/mcp/websocket/server.py +7 -25
- crackerjack/mcp/websocket/websocket_handler.py +6 -17
- crackerjack/mixins/__init__.py +0 -2
- crackerjack/mixins/error_handling.py +1 -70
- crackerjack/models/config.py +12 -1
- crackerjack/models/config_adapter.py +49 -1
- crackerjack/models/protocols.py +122 -122
- crackerjack/models/resource_protocols.py +55 -210
- crackerjack/monitoring/ai_agent_watchdog.py +13 -13
- crackerjack/monitoring/metrics_collector.py +426 -0
- crackerjack/monitoring/regression_prevention.py +8 -8
- crackerjack/monitoring/websocket_server.py +643 -0
- crackerjack/orchestration/advanced_orchestrator.py +11 -6
- crackerjack/orchestration/coverage_improvement.py +3 -3
- crackerjack/orchestration/execution_strategies.py +26 -6
- crackerjack/orchestration/test_progress_streamer.py +8 -5
- crackerjack/plugins/base.py +2 -2
- crackerjack/plugins/hooks.py +7 -0
- crackerjack/plugins/managers.py +11 -8
- crackerjack/security/__init__.py +0 -1
- crackerjack/security/audit.py +6 -35
- crackerjack/services/anomaly_detector.py +392 -0
- crackerjack/services/api_extractor.py +615 -0
- crackerjack/services/backup_service.py +2 -2
- crackerjack/services/bounded_status_operations.py +15 -152
- crackerjack/services/cache.py +127 -1
- crackerjack/services/changelog_automation.py +395 -0
- crackerjack/services/config.py +15 -9
- crackerjack/services/config_merge.py +19 -80
- crackerjack/services/config_template.py +506 -0
- crackerjack/services/contextual_ai_assistant.py +48 -22
- crackerjack/services/coverage_badge_service.py +171 -0
- crackerjack/services/coverage_ratchet.py +27 -25
- crackerjack/services/debug.py +3 -3
- crackerjack/services/dependency_analyzer.py +460 -0
- crackerjack/services/dependency_monitor.py +14 -11
- crackerjack/services/documentation_generator.py +491 -0
- crackerjack/services/documentation_service.py +675 -0
- crackerjack/services/enhanced_filesystem.py +6 -5
- crackerjack/services/enterprise_optimizer.py +865 -0
- crackerjack/services/error_pattern_analyzer.py +676 -0
- crackerjack/services/file_hasher.py +1 -1
- crackerjack/services/git.py +8 -25
- crackerjack/services/health_metrics.py +10 -8
- crackerjack/services/heatmap_generator.py +735 -0
- crackerjack/services/initialization.py +11 -30
- crackerjack/services/input_validator.py +5 -97
- crackerjack/services/intelligent_commit.py +327 -0
- crackerjack/services/log_manager.py +15 -12
- crackerjack/services/logging.py +4 -3
- crackerjack/services/lsp_client.py +628 -0
- crackerjack/services/memory_optimizer.py +19 -87
- crackerjack/services/metrics.py +42 -33
- crackerjack/services/parallel_executor.py +9 -67
- crackerjack/services/pattern_cache.py +1 -1
- crackerjack/services/pattern_detector.py +6 -6
- crackerjack/services/performance_benchmarks.py +18 -59
- crackerjack/services/performance_cache.py +20 -81
- crackerjack/services/performance_monitor.py +27 -95
- crackerjack/services/predictive_analytics.py +510 -0
- crackerjack/services/quality_baseline.py +234 -0
- crackerjack/services/quality_baseline_enhanced.py +646 -0
- crackerjack/services/quality_intelligence.py +785 -0
- crackerjack/services/regex_patterns.py +605 -524
- crackerjack/services/regex_utils.py +43 -123
- crackerjack/services/secure_path_utils.py +5 -164
- crackerjack/services/secure_status_formatter.py +30 -141
- crackerjack/services/secure_subprocess.py +11 -92
- crackerjack/services/security.py +9 -41
- crackerjack/services/security_logger.py +12 -24
- crackerjack/services/server_manager.py +124 -16
- crackerjack/services/status_authentication.py +16 -159
- crackerjack/services/status_security_manager.py +4 -131
- crackerjack/services/thread_safe_status_collector.py +19 -125
- crackerjack/services/unified_config.py +21 -13
- crackerjack/services/validation_rate_limiter.py +5 -54
- crackerjack/services/version_analyzer.py +459 -0
- crackerjack/services/version_checker.py +1 -1
- crackerjack/services/websocket_resource_limiter.py +10 -144
- crackerjack/services/zuban_lsp_service.py +390 -0
- crackerjack/slash_commands/__init__.py +2 -7
- crackerjack/slash_commands/run.md +2 -2
- crackerjack/tools/validate_input_validator_patterns.py +14 -40
- crackerjack/tools/validate_regex_patterns.py +19 -48
- {crackerjack-0.33.0.dist-info → crackerjack-0.33.1.dist-info}/METADATA +196 -25
- crackerjack-0.33.1.dist-info/RECORD +229 -0
- crackerjack/CLAUDE.md +0 -207
- crackerjack/RULES.md +0 -380
- crackerjack/py313.py +0 -234
- crackerjack-0.33.0.dist-info/RECORD +0 -187
- {crackerjack-0.33.0.dist-info → crackerjack-0.33.1.dist-info}/WHEEL +0 -0
- {crackerjack-0.33.0.dist-info → crackerjack-0.33.1.dist-info}/entry_points.txt +0 -0
- {crackerjack-0.33.0.dist-info → crackerjack-0.33.1.dist-info}/licenses/LICENSE +0 -0
|
@@ -1,10 +1,3 @@
|
|
|
1
|
-
"""
|
|
2
|
-
Status Security Manager for comprehensive security controls.
|
|
3
|
-
|
|
4
|
-
Provides authentication, authorization, rate limiting, and resource protection
|
|
5
|
-
for status collection operations to prevent security vulnerabilities.
|
|
6
|
-
"""
|
|
7
|
-
|
|
8
1
|
import asyncio
|
|
9
2
|
import threading
|
|
10
3
|
import time
|
|
@@ -16,41 +9,22 @@ from .security_logger import SecurityEventLevel, SecurityEventType, get_security
|
|
|
16
9
|
|
|
17
10
|
|
|
18
11
|
class StatusSecurityError(Exception):
|
|
19
|
-
"""Base exception for status security violations."""
|
|
20
|
-
|
|
21
12
|
pass
|
|
22
13
|
|
|
23
14
|
|
|
24
15
|
class AccessDeniedError(StatusSecurityError):
|
|
25
|
-
"""Raised when access is denied to status information."""
|
|
26
|
-
|
|
27
16
|
pass
|
|
28
17
|
|
|
29
18
|
|
|
30
19
|
class ResourceLimitExceededError(StatusSecurityError):
|
|
31
|
-
"""Raised when resource limits are exceeded."""
|
|
32
|
-
|
|
33
20
|
pass
|
|
34
21
|
|
|
35
22
|
|
|
36
23
|
class RateLimitExceededError(StatusSecurityError):
|
|
37
|
-
"""Raised when rate limits are exceeded."""
|
|
38
|
-
|
|
39
24
|
pass
|
|
40
25
|
|
|
41
26
|
|
|
42
27
|
class StatusSecurityManager:
|
|
43
|
-
"""
|
|
44
|
-
Comprehensive security manager for status operations.
|
|
45
|
-
|
|
46
|
-
Provides:
|
|
47
|
-
- Authentication and authorization controls
|
|
48
|
-
- Rate limiting for status requests
|
|
49
|
-
- Resource usage monitoring and limits
|
|
50
|
-
- Concurrent operation tracking
|
|
51
|
-
- Path traversal protection
|
|
52
|
-
"""
|
|
53
|
-
|
|
54
28
|
def __init__(
|
|
55
29
|
self,
|
|
56
30
|
max_concurrent_requests: int = 5,
|
|
@@ -58,30 +32,18 @@ class StatusSecurityManager:
|
|
|
58
32
|
max_resource_usage_mb: int = 100,
|
|
59
33
|
allowed_paths: set[str] | None = None,
|
|
60
34
|
):
|
|
61
|
-
"""
|
|
62
|
-
Initialize status security manager.
|
|
63
|
-
|
|
64
|
-
Args:
|
|
65
|
-
max_concurrent_requests: Maximum concurrent status requests
|
|
66
|
-
rate_limit_per_minute: Maximum requests per minute per client
|
|
67
|
-
max_resource_usage_mb: Maximum memory usage in MB
|
|
68
|
-
allowed_paths: Set of allowed paths for file operations
|
|
69
|
-
"""
|
|
70
35
|
self.max_concurrent_requests = max_concurrent_requests
|
|
71
36
|
self.rate_limit_per_minute = rate_limit_per_minute
|
|
72
37
|
self.max_resource_usage_mb = max_resource_usage_mb
|
|
73
38
|
self.allowed_paths = allowed_paths or set()
|
|
74
39
|
|
|
75
|
-
# Thread-safe tracking
|
|
76
40
|
self._lock = threading.RLock()
|
|
77
41
|
self._concurrent_requests = 0
|
|
78
42
|
self._rate_limit_tracker: dict[str, list[float]] = defaultdict(list)
|
|
79
43
|
self._resource_usage = 0.0
|
|
80
44
|
|
|
81
|
-
# Security logging
|
|
82
45
|
self.security_logger = get_security_logger()
|
|
83
46
|
|
|
84
|
-
# Active request tracking for resource cleanup
|
|
85
47
|
self._active_requests: set[str] = set()
|
|
86
48
|
|
|
87
49
|
def validate_request(
|
|
@@ -90,21 +52,7 @@ class StatusSecurityManager:
|
|
|
90
52
|
operation: str,
|
|
91
53
|
request_data: dict[str, t.Any] | None = None,
|
|
92
54
|
) -> None:
|
|
93
|
-
"""
|
|
94
|
-
Validate status request for security compliance.
|
|
95
|
-
|
|
96
|
-
Args:
|
|
97
|
-
client_id: Unique client identifier
|
|
98
|
-
operation: Operation being requested
|
|
99
|
-
request_data: Additional request data to validate
|
|
100
|
-
|
|
101
|
-
Raises:
|
|
102
|
-
AccessDeniedError: If access is denied
|
|
103
|
-
RateLimitExceededError: If rate limit exceeded
|
|
104
|
-
ResourceLimitExceededError: If resource limits exceeded
|
|
105
|
-
"""
|
|
106
55
|
with self._lock:
|
|
107
|
-
# Check concurrent request limit
|
|
108
56
|
if self._concurrent_requests >= self.max_concurrent_requests:
|
|
109
57
|
self.security_logger.log_security_event(
|
|
110
58
|
event_type=SecurityEventType.RATE_LIMIT_EXCEEDED,
|
|
@@ -117,25 +65,19 @@ class StatusSecurityManager:
|
|
|
117
65
|
f"Too many concurrent requests: {self._concurrent_requests}"
|
|
118
66
|
)
|
|
119
67
|
|
|
120
|
-
# Check rate limiting
|
|
121
68
|
self._check_rate_limit(client_id, operation)
|
|
122
69
|
|
|
123
|
-
# Validate request data if provided
|
|
124
70
|
if request_data:
|
|
125
71
|
self._validate_request_data(client_id, operation, request_data)
|
|
126
72
|
|
|
127
73
|
def _check_rate_limit(self, client_id: str, operation: str) -> None:
|
|
128
|
-
"""Check if client has exceeded rate limits."""
|
|
129
|
-
|
|
130
74
|
current_time = time.time()
|
|
131
75
|
client_requests = self._rate_limit_tracker[client_id]
|
|
132
76
|
|
|
133
|
-
# Remove requests older than 1 minute
|
|
134
77
|
client_requests[:] = [
|
|
135
78
|
req_time for req_time in client_requests if current_time - req_time < 60
|
|
136
79
|
]
|
|
137
80
|
|
|
138
|
-
# Check if limit exceeded
|
|
139
81
|
if len(client_requests) >= self.rate_limit_per_minute:
|
|
140
82
|
self.security_logger.log_security_event(
|
|
141
83
|
event_type=SecurityEventType.RATE_LIMIT_EXCEEDED,
|
|
@@ -148,7 +90,6 @@ class StatusSecurityManager:
|
|
|
148
90
|
f"Rate limit exceeded: {len(client_requests)} requests in last minute"
|
|
149
91
|
)
|
|
150
92
|
|
|
151
|
-
# Record this request
|
|
152
93
|
client_requests.append(current_time)
|
|
153
94
|
|
|
154
95
|
def _validate_request_data(
|
|
@@ -157,9 +98,6 @@ class StatusSecurityManager:
|
|
|
157
98
|
operation: str,
|
|
158
99
|
request_data: dict[str, t.Any],
|
|
159
100
|
) -> None:
|
|
160
|
-
"""Validate request data for security issues."""
|
|
161
|
-
|
|
162
|
-
# Check for path traversal attempts
|
|
163
101
|
for key, value in request_data.items():
|
|
164
102
|
if isinstance(value, str):
|
|
165
103
|
if self._contains_path_traversal(value):
|
|
@@ -173,16 +111,12 @@ class StatusSecurityManager:
|
|
|
173
111
|
)
|
|
174
112
|
raise AccessDeniedError(f"Invalid path in parameter: {key}")
|
|
175
113
|
|
|
176
|
-
# Validate file paths if present
|
|
177
114
|
if "path" in request_data or "file_path" in request_data:
|
|
178
115
|
path_value = request_data.get("path") or request_data.get("file_path")
|
|
179
116
|
if path_value:
|
|
180
117
|
self._validate_file_path(client_id, operation, str(path_value))
|
|
181
118
|
|
|
182
119
|
def _contains_path_traversal(self, value: str) -> bool:
|
|
183
|
-
"""Check if value contains path traversal patterns."""
|
|
184
|
-
|
|
185
|
-
# Common path traversal patterns
|
|
186
120
|
traversal_patterns = [
|
|
187
121
|
"../",
|
|
188
122
|
"..\\",
|
|
@@ -194,7 +128,7 @@ class StatusSecurityManager:
|
|
|
194
128
|
"....\\\\",
|
|
195
129
|
"..\\/",
|
|
196
130
|
"../\\",
|
|
197
|
-
"%252e%252e%252f",
|
|
131
|
+
"%252e%252e%252f",
|
|
198
132
|
]
|
|
199
133
|
|
|
200
134
|
value_lower = value.lower()
|
|
@@ -203,12 +137,9 @@ class StatusSecurityManager:
|
|
|
203
137
|
def _validate_file_path(
|
|
204
138
|
self, client_id: str, operation: str, file_path: str
|
|
205
139
|
) -> None:
|
|
206
|
-
"""Validate file path for security compliance."""
|
|
207
|
-
|
|
208
140
|
try:
|
|
209
141
|
path = Path(file_path).resolve()
|
|
210
142
|
|
|
211
|
-
# Check if path is within allowed paths
|
|
212
143
|
if self.allowed_paths:
|
|
213
144
|
path_allowed = any(
|
|
214
145
|
path.is_relative_to(Path(allowed_path).resolve())
|
|
@@ -242,24 +173,8 @@ class StatusSecurityManager:
|
|
|
242
173
|
operation: str,
|
|
243
174
|
timeout: float = 30.0,
|
|
244
175
|
) -> "RequestLock":
|
|
245
|
-
""
|
|
246
|
-
Acquire a request lock for concurrent operation tracking.
|
|
247
|
-
|
|
248
|
-
Args:
|
|
249
|
-
client_id: Client identifier
|
|
250
|
-
operation: Operation being performed
|
|
251
|
-
timeout: Maximum wait time for lock acquisition
|
|
252
|
-
|
|
253
|
-
Returns:
|
|
254
|
-
RequestLock context manager
|
|
176
|
+
request_id = f"{client_id}: {operation}: {int(time.time())}"
|
|
255
177
|
|
|
256
|
-
Raises:
|
|
257
|
-
ResourceLimitExceededError: If unable to acquire lock within timeout
|
|
258
|
-
"""
|
|
259
|
-
|
|
260
|
-
request_id = f"{client_id}:{operation}:{int(time.time())}"
|
|
261
|
-
|
|
262
|
-
# Try to acquire lock with timeout
|
|
263
178
|
start_time = time.time()
|
|
264
179
|
while time.time() - start_time < timeout:
|
|
265
180
|
with self._lock:
|
|
@@ -277,10 +192,8 @@ class StatusSecurityManager:
|
|
|
277
192
|
|
|
278
193
|
return RequestLock(self, request_id, client_id, operation)
|
|
279
194
|
|
|
280
|
-
# Wait briefly before retrying
|
|
281
195
|
await asyncio.sleep(0.1)
|
|
282
196
|
|
|
283
|
-
# Timeout exceeded
|
|
284
197
|
self.security_logger.log_security_event(
|
|
285
198
|
event_type=SecurityEventType.REQUEST_TIMEOUT,
|
|
286
199
|
level=SecurityEventLevel.ERROR,
|
|
@@ -296,8 +209,6 @@ class StatusSecurityManager:
|
|
|
296
209
|
def _release_request_lock(
|
|
297
210
|
self, request_id: str, client_id: str, operation: str
|
|
298
211
|
) -> None:
|
|
299
|
-
"""Release a request lock."""
|
|
300
|
-
|
|
301
212
|
with self._lock:
|
|
302
213
|
if request_id in self._active_requests:
|
|
303
214
|
self._active_requests.remove(request_id)
|
|
@@ -312,12 +223,9 @@ class StatusSecurityManager:
|
|
|
312
223
|
)
|
|
313
224
|
|
|
314
225
|
def get_security_status(self) -> dict[str, t.Any]:
|
|
315
|
-
"""Get current security status and metrics."""
|
|
316
|
-
|
|
317
226
|
with self._lock:
|
|
318
227
|
current_time = time.time()
|
|
319
228
|
|
|
320
|
-
# Calculate recent request rates
|
|
321
229
|
recent_requests = 0
|
|
322
230
|
for client_requests in self._rate_limit_tracker.values():
|
|
323
231
|
recent_requests += len(
|
|
@@ -330,7 +238,7 @@ class StatusSecurityManager:
|
|
|
330
238
|
|
|
331
239
|
return {
|
|
332
240
|
"concurrent_requests": self._concurrent_requests,
|
|
333
|
-
"active_request_ids": list(self._active_requests),
|
|
241
|
+
"active_request_ids": list[t.Any](self._active_requests),
|
|
334
242
|
"recent_requests_per_minute": recent_requests,
|
|
335
243
|
"rate_limit_clients": len(self._rate_limit_tracker),
|
|
336
244
|
"max_concurrent_limit": self.max_concurrent_requests,
|
|
@@ -342,8 +250,6 @@ class StatusSecurityManager:
|
|
|
342
250
|
|
|
343
251
|
|
|
344
252
|
class RequestLock:
|
|
345
|
-
"""Context manager for request lock acquisition and release."""
|
|
346
|
-
|
|
347
253
|
def __init__(
|
|
348
254
|
self,
|
|
349
255
|
security_manager: StatusSecurityManager,
|
|
@@ -367,16 +273,12 @@ class RequestLock:
|
|
|
367
273
|
)
|
|
368
274
|
|
|
369
275
|
|
|
370
|
-
# Global instance for singleton pattern
|
|
371
276
|
_security_manager: StatusSecurityManager | None = None
|
|
372
277
|
|
|
373
278
|
|
|
374
279
|
def get_status_security_manager() -> StatusSecurityManager:
|
|
375
|
-
"""Get the global status security manager instance."""
|
|
376
|
-
|
|
377
280
|
global _security_manager
|
|
378
281
|
if _security_manager is None:
|
|
379
|
-
# Initialize with project-specific paths
|
|
380
282
|
import tempfile
|
|
381
283
|
from pathlib import Path
|
|
382
284
|
|
|
@@ -385,9 +287,7 @@ def get_status_security_manager() -> StatusSecurityManager:
|
|
|
385
287
|
allowed_paths = {
|
|
386
288
|
str(project_root),
|
|
387
289
|
str(project_root / "temp"),
|
|
388
|
-
str(
|
|
389
|
-
temp_dir / "crackerjack-mcp-progress"
|
|
390
|
-
), # B108: Use tempfile.gettempdir()
|
|
290
|
+
str(temp_dir / "crackerjack-mcp-progress"),
|
|
391
291
|
}
|
|
392
292
|
|
|
393
293
|
_security_manager = StatusSecurityManager(
|
|
@@ -402,18 +302,6 @@ async def validate_status_request(
|
|
|
402
302
|
operation: str,
|
|
403
303
|
request_data: dict[str, t.Any] | None = None,
|
|
404
304
|
) -> None:
|
|
405
|
-
"""
|
|
406
|
-
Convenience function to validate status requests.
|
|
407
|
-
|
|
408
|
-
Args:
|
|
409
|
-
client_id: Client identifier
|
|
410
|
-
operation: Operation being requested
|
|
411
|
-
request_data: Optional request data to validate
|
|
412
|
-
|
|
413
|
-
Raises:
|
|
414
|
-
StatusSecurityError: If security validation fails
|
|
415
|
-
"""
|
|
416
|
-
|
|
417
305
|
security_manager = get_status_security_manager()
|
|
418
306
|
security_manager.validate_request(client_id, operation, request_data)
|
|
419
307
|
|
|
@@ -423,20 +311,5 @@ async def secure_status_operation(
|
|
|
423
311
|
operation: str,
|
|
424
312
|
timeout: float = 30.0,
|
|
425
313
|
) -> RequestLock:
|
|
426
|
-
"""
|
|
427
|
-
Acquire security lock for status operations.
|
|
428
|
-
|
|
429
|
-
Args:
|
|
430
|
-
client_id: Client identifier
|
|
431
|
-
operation: Operation being performed
|
|
432
|
-
timeout: Maximum wait time for lock
|
|
433
|
-
|
|
434
|
-
Returns:
|
|
435
|
-
RequestLock context manager
|
|
436
|
-
|
|
437
|
-
Raises:
|
|
438
|
-
ResourceLimitExceededError: If unable to acquire lock
|
|
439
|
-
"""
|
|
440
|
-
|
|
441
314
|
security_manager = get_status_security_manager()
|
|
442
315
|
return await security_manager.acquire_request_lock(client_id, operation, timeout)
|