nucleus-mcp 1.0.7 → 1.2.0

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.
Files changed (135) hide show
  1. package/package.json +2 -4
  2. package/.github/workflows/ci.yml +0 -72
  3. package/.smithery/shttp/module.js +0 -3
  4. package/.smithery/shttp/module.js.map +0 -7
  5. package/.smithery/stdio/index.cjs +0 -74
  6. package/.smithery/stdio/index.cjs.map +0 -7
  7. package/CHANGELOG.md +0 -65
  8. package/CODE_OF_CONDUCT.md +0 -34
  9. package/COMPARISON.md +0 -20
  10. package/CONTRIBUTING.md +0 -137
  11. package/DEVELOPMENT.md +0 -109
  12. package/LICENSE +0 -21
  13. package/README.md +0 -319
  14. package/ROADMAP.md +0 -24
  15. package/SECURITY.md +0 -88
  16. package/docs/COMMUNITY_FAQ.md +0 -48
  17. package/docs/COMPETITIVE_ANALYSIS.md +0 -90
  18. package/docs/DEMO_SCRIPT.md +0 -86
  19. package/docs/ENTERPRISE.md +0 -169
  20. package/docs/FAQ.md +0 -228
  21. package/docs/QUICK_START.md +0 -155
  22. package/docs/README.md +0 -67
  23. package/docs/RECURSIVE_SNAP_DEMO.gif +0 -0
  24. package/docs/social-preview-hq.png +0 -0
  25. package/docs/social-preview.png +0 -0
  26. package/examples/basic_usage.py +0 -84
  27. package/package.json.real +0 -24
  28. package/pyproject.toml +0 -50
  29. package/registry-server.json +0 -20
  30. package/scripts/demo_governance.py +0 -109
  31. package/scripts/sse_bridge.py +0 -87
  32. package/scripts/verify_windows_paths.py +0 -48
  33. package/server.json +0 -20
  34. package/src/mcp_server_nucleus/__init__.py +0 -8583
  35. package/src/mcp_server_nucleus/__main__.py +0 -9
  36. package/src/mcp_server_nucleus/cli.py +0 -1225
  37. package/src/mcp_server_nucleus/commitment_core.py +0 -146
  38. package/src/mcp_server_nucleus/commitment_ledger.py +0 -841
  39. package/src/mcp_server_nucleus/core/__init__.py +0 -6
  40. package/src/mcp_server_nucleus/core/orchestrator.py +0 -9
  41. package/src/mcp_server_nucleus/core/tool_registration_impl.py +0 -99
  42. package/src/mcp_server_nucleus/daemon/safety/lock.py +0 -121
  43. package/src/mcp_server_nucleus/deployment/render_integration.py +0 -4
  44. package/src/mcp_server_nucleus/hypervisor/__init__.py +0 -0
  45. package/src/mcp_server_nucleus/hypervisor/injector.py +0 -83
  46. package/src/mcp_server_nucleus/hypervisor/locker.py +0 -130
  47. package/src/mcp_server_nucleus/hypervisor/watchdog.py +0 -71
  48. package/src/mcp_server_nucleus/runtime/__init__.py +0 -58
  49. package/src/mcp_server_nucleus/runtime/agent.py +0 -517
  50. package/src/mcp_server_nucleus/runtime/agent_pool.py +0 -797
  51. package/src/mcp_server_nucleus/runtime/agents/base.py +0 -34
  52. package/src/mcp_server_nucleus/runtime/agents/oracle/manifest.json +0 -28
  53. package/src/mcp_server_nucleus/runtime/auth.py +0 -98
  54. package/src/mcp_server_nucleus/runtime/autopilot.py +0 -1057
  55. package/src/mcp_server_nucleus/runtime/broker.py +0 -126
  56. package/src/mcp_server_nucleus/runtime/budget.py +0 -153
  57. package/src/mcp_server_nucleus/runtime/capabilities/base.py +0 -20
  58. package/src/mcp_server_nucleus/runtime/capabilities/brain_ops.py +0 -253
  59. package/src/mcp_server_nucleus/runtime/capabilities/code_ops.py +0 -192
  60. package/src/mcp_server_nucleus/runtime/capabilities/depth_tracker.py +0 -81
  61. package/src/mcp_server_nucleus/runtime/capabilities/feature_map.py +0 -274
  62. package/src/mcp_server_nucleus/runtime/capabilities/marketing_engine.py +0 -205
  63. package/src/mcp_server_nucleus/runtime/capabilities/memory_ops.py +0 -79
  64. package/src/mcp_server_nucleus/runtime/capabilities/proof_system.py +0 -127
  65. package/src/mcp_server_nucleus/runtime/capabilities/render_ops.py +0 -80
  66. package/src/mcp_server_nucleus/runtime/capabilities/render_poller_cap.py +0 -266
  67. package/src/mcp_server_nucleus/runtime/capabilities/self_healing.py +0 -110
  68. package/src/mcp_server_nucleus/runtime/capabilities/strategy.py +0 -138
  69. package/src/mcp_server_nucleus/runtime/capabilities/synthesizer.py +0 -134
  70. package/src/mcp_server_nucleus/runtime/capabilities/web_ops.py +0 -94
  71. package/src/mcp_server_nucleus/runtime/common.py +0 -134
  72. package/src/mcp_server_nucleus/runtime/context_manager.py +0 -342
  73. package/src/mcp_server_nucleus/runtime/context_rules.json +0 -86
  74. package/src/mcp_server_nucleus/runtime/crdt_task_store.py +0 -349
  75. package/src/mcp_server_nucleus/runtime/critic.py +0 -150
  76. package/src/mcp_server_nucleus/runtime/daemon.py +0 -142
  77. package/src/mcp_server_nucleus/runtime/dashboard.py +0 -1087
  78. package/src/mcp_server_nucleus/runtime/depth_ops.py +0 -339
  79. package/src/mcp_server_nucleus/runtime/event_ops.py +0 -103
  80. package/src/mcp_server_nucleus/runtime/event_stream.py +0 -213
  81. package/src/mcp_server_nucleus/runtime/export.py +0 -64
  82. package/src/mcp_server_nucleus/runtime/factory.py +0 -594
  83. package/src/mcp_server_nucleus/runtime/federation.py +0 -1040
  84. package/src/mcp_server_nucleus/runtime/fetcher.py +0 -92
  85. package/src/mcp_server_nucleus/runtime/file_monitor.py +0 -208
  86. package/src/mcp_server_nucleus/runtime/firestore_bridge.py +0 -91
  87. package/src/mcp_server_nucleus/runtime/gcloud_ops.py +0 -186
  88. package/src/mcp_server_nucleus/runtime/hooks.py +0 -246
  89. package/src/mcp_server_nucleus/runtime/identity/gatekeeper.py +0 -106
  90. package/src/mcp_server_nucleus/runtime/identity/keygen.py +0 -147
  91. package/src/mcp_server_nucleus/runtime/identity/manifest.py +0 -62
  92. package/src/mcp_server_nucleus/runtime/identity/trust.py +0 -27
  93. package/src/mcp_server_nucleus/runtime/inspector.py +0 -74
  94. package/src/mcp_server_nucleus/runtime/installer.py +0 -81
  95. package/src/mcp_server_nucleus/runtime/ipc_auth.py +0 -377
  96. package/src/mcp_server_nucleus/runtime/lifecycle.py +0 -129
  97. package/src/mcp_server_nucleus/runtime/llm_client.py +0 -408
  98. package/src/mcp_server_nucleus/runtime/llm_tiers.json +0 -88
  99. package/src/mcp_server_nucleus/runtime/locking.py +0 -228
  100. package/src/mcp_server_nucleus/runtime/loops/fixer.py +0 -110
  101. package/src/mcp_server_nucleus/runtime/memory.py +0 -158
  102. package/src/mcp_server_nucleus/runtime/mounter.py +0 -210
  103. package/src/mcp_server_nucleus/runtime/mounter_ops.py +0 -250
  104. package/src/mcp_server_nucleus/runtime/nuke_protocol.py +0 -147
  105. package/src/mcp_server_nucleus/runtime/orchestrator.py +0 -370
  106. package/src/mcp_server_nucleus/runtime/orchestrator_unified.py +0 -263
  107. package/src/mcp_server_nucleus/runtime/orchestrator_v3.py +0 -617
  108. package/src/mcp_server_nucleus/runtime/plugin_loader.py +0 -84
  109. package/src/mcp_server_nucleus/runtime/policy.py +0 -117
  110. package/src/mcp_server_nucleus/runtime/profiling.py +0 -219
  111. package/src/mcp_server_nucleus/runtime/prometheus.py +0 -286
  112. package/src/mcp_server_nucleus/runtime/proposals.py +0 -101
  113. package/src/mcp_server_nucleus/runtime/publisher.py +0 -109
  114. package/src/mcp_server_nucleus/runtime/pulse.py +0 -516
  115. package/src/mcp_server_nucleus/runtime/registry.py +0 -82
  116. package/src/mcp_server_nucleus/runtime/render_ops.py +0 -83
  117. package/src/mcp_server_nucleus/runtime/schema_gen.py +0 -140
  118. package/src/mcp_server_nucleus/runtime/session_ops.py +0 -224
  119. package/src/mcp_server_nucleus/runtime/stdio_server.py +0 -633
  120. package/src/mcp_server_nucleus/runtime/storage.py +0 -83
  121. package/src/mcp_server_nucleus/runtime/strategy.py +0 -91
  122. package/src/mcp_server_nucleus/runtime/swarm.py +0 -170
  123. package/src/mcp_server_nucleus/runtime/sync_ops.py +0 -878
  124. package/src/mcp_server_nucleus/runtime/task_ingestion.py +0 -1020
  125. package/src/mcp_server_nucleus/runtime/task_ops.py +0 -449
  126. package/src/mcp_server_nucleus/runtime/task_scheduler.py +0 -488
  127. package/src/mcp_server_nucleus/runtime/team.py +0 -59
  128. package/src/mcp_server_nucleus/runtime/triggers.py +0 -237
  129. package/src/mcp_server_nucleus/runtime/vector_store.py +0 -125
  130. package/src/mcp_server_nucleus/runtime/watcher.py +0 -112
  131. package/src/mcp_server_nucleus/tool_tiers.py +0 -243
  132. package/tests/__init__.py +0 -1
  133. package/tests/conftest.py +0 -42
  134. package/tests/test_core.py +0 -235
  135. package/tests/test_search.py +0 -69
@@ -1,633 +0,0 @@
1
-
2
- import sys
3
- import json
4
- import logging
5
- import traceback
6
- import time
7
- import os
8
- import re
9
- from typing import Any, Dict, Optional
10
- from ..hypervisor.locker import Locker
11
- from ..hypervisor.watchdog import Watchdog
12
- from ..hypervisor.injector import Injector
13
- from .task_ops import (
14
- _list_tasks, _add_task, _update_task,
15
- _claim_task, _get_next_task
16
- )
17
- from pathlib import Path
18
- from datetime import datetime
19
- import asyncio
20
- from .mounter_ops import Mounter
21
-
22
- # Configure logging to stderr to not corrupt stdout (which is for JSON-RPC)
23
- logging.basicConfig(stream=sys.stderr, level=logging.INFO, format='[Nucleus] %(message)s')
24
- logger = logging.getLogger("nucleus_server")
25
-
26
- START_TIME = time.time()
27
-
28
- def make_response(success: bool, data: Any = None, error: str = None) -> str:
29
- """Helper to create a formatted JSON response string."""
30
- response = {"success": success}
31
- if data is not None:
32
- response["data"] = data
33
- if error is not None:
34
- response["error"] = error
35
- return json.dumps(response, indent=2)
36
-
37
- class StdioServer:
38
- def __init__(self):
39
- # Resolve paths first
40
- self.brain_path = Path(os.environ.get("NUCLEAR_BRAIN_PATH", ".")).resolve()
41
- workspace_root = self.brain_path.parent
42
-
43
- self.locker = Locker()
44
- self.injector = Injector(str(workspace_root))
45
- self.watchdog = Watchdog(str(workspace_root))
46
-
47
- try:
48
- self.watchdog.start()
49
- except Exception as e:
50
- logger.error(f"Failed to start watchdog: {e}")
51
-
52
- self.mounter = Mounter(self.brain_path)
53
-
54
- async def run(self):
55
- # Restore mounts from persistence
56
- await self.mounter.restore_mounts()
57
-
58
- loop = asyncio.get_running_loop()
59
- while True:
60
- try:
61
- line = await loop.run_in_executor(None, sys.stdin.readline)
62
- if not line:
63
- break
64
-
65
- request = json.loads(line)
66
-
67
- response = await self.handle_request(request)
68
- if response:
69
- out = json.dumps(response)
70
- print(out, flush=True)
71
- except json.JSONDecodeError:
72
- logger.error("Failed to decode JSON")
73
- except Exception as e:
74
- logger.error(f"Server loop error: {e}")
75
- traceback.print_exc(file=sys.stderr)
76
-
77
- async def handle_request(self, request: Dict[str, Any]) -> Optional[Dict[str, Any]]:
78
- method = request.get("method")
79
- msg_id = request.get("id")
80
-
81
- if method == "initialize":
82
- return {
83
- "jsonrpc": "2.0",
84
- "id": msg_id,
85
- "result": {
86
- "protocolVersion": "2024-11-05", # Updated protocol version
87
- "capabilities": {
88
- "tools": {}
89
- },
90
- "serverInfo": {
91
- "name": "nucleus-mcp",
92
- "version": "1.0.0"
93
- }
94
- }
95
- }
96
-
97
- elif method == "notifications/initialized":
98
- # No response needed for notification
99
- return None
100
-
101
- elif method == "tools/list":
102
- # Create standard tools list
103
- tools = [
104
- {
105
- "name": "lock_resource",
106
- "description": "[HYPERVISOR] Lock a file/folder to prevent modification (Layer 4).",
107
- "inputSchema": {
108
- "type": "object",
109
- "properties": {
110
- "path": {"type": "string", "description": "Absolute path to lock"},
111
- "reason": {"type": "string", "description": "Why is this being locked?"},
112
- "agent_id": {"type": "string", "description": "Who is locking this?"}
113
- },
114
- "required": ["path"]
115
- }
116
- },
117
- {
118
- "name": "unlock_resource",
119
- "description": "[HYPERVISOR] Unlock a resource.",
120
- "inputSchema": {
121
- "type": "object",
122
- "properties": {
123
- "path": {"type": "string", "description": "Absolute path to unlock"}
124
- },
125
- "required": ["path"]
126
- }
127
- },
128
- {
129
- "name": "get_lock_metadata",
130
- "description": "[HYPERVISOR] Retrieve lock metadata (Why/Who/When).",
131
- "inputSchema": {
132
- "type": "object",
133
- "properties": {
134
- "path": {"type": "string", "description": "Path to inspect"}
135
- },
136
- "required": ["path"]
137
- }
138
- },
139
- {
140
- "name": "watch_resource",
141
- "description": "[HYPERVISOR] key file/folder monitoring (Layer 1).",
142
- "inputSchema": {
143
- "type": "object",
144
- "properties": {
145
- "path": {"type": "string", "description": "Path to watch"}
146
- },
147
- "required": ["path"]
148
- }
149
- },
150
- {
151
- "name": "hypervisor_status",
152
- "description": "[HYPERVISOR] Reports the current security state of the Agent OS.",
153
- "inputSchema": {
154
- "type": "object",
155
- "properties": {},
156
- }
157
- },
158
- {
159
- "name": "set_hypervisor_mode",
160
- "description": "[HYPERVISOR] Switch Visual Context (Injector).",
161
- "inputSchema": {
162
- "type": "object",
163
- "properties": {
164
- "mode": {"type": "string", "enum": ["red", "blue", "reset"]}
165
- },
166
- "required": ["mode"]
167
- }
168
- },
169
- {
170
- "name": "brain_health",
171
- "description": "Get comprehensive system health status.",
172
- "inputSchema": {
173
- "type": "object",
174
- "properties": {}
175
- }
176
- },
177
- {
178
- "name": "brain_audit_log",
179
- "description": "View the cryptographic interaction log for trust verification.",
180
- "inputSchema": {
181
- "type": "object",
182
- "properties": {
183
- "limit": {"type": "integer", "description": "Number of recent entries", "default": 20}
184
- }
185
- }
186
- },
187
- {
188
- "name": "brain_write_engram",
189
- "description": "Write a long-term memory engram (learning/pattern).",
190
- "inputSchema": {
191
- "type": "object",
192
- "properties": {
193
- "key": {"type": "string", "description": "Unique identifier"},
194
- "value": {"type": "string", "description": "Memory content"},
195
- "context": {"type": "string", "enum": ["Feature", "Architecture", "Brand", "Strategy", "Decision"], "default": "Decision"},
196
- "intensity": {"type": "integer", "minimum": 1, "maximum": 10, "default": 5}
197
- },
198
- "required": ["key", "value"]
199
- }
200
- },
201
- {
202
- "name": "brain_query_engrams",
203
- "description": "Query context-aware memory engrams.",
204
- "inputSchema": {
205
- "type": "object",
206
- "properties": {
207
- "context": {"type": "string", "enum": ["Feature", "Architecture", "Brand", "Strategy", "Decision"]},
208
- "min_intensity": {"type": "integer", "minimum": 1, "maximum": 10, "default": 1}
209
- }
210
- }
211
- },
212
- {
213
- "name": "brain_governance_status",
214
- "description": "Get the current governance status and statistics.",
215
- "inputSchema": {
216
- "type": "object",
217
- "properties": {}
218
- }
219
- },
220
- {
221
- "name": "brain_list_tasks",
222
- "description": "List all tasks from the Brain (Task Ledger).",
223
- "inputSchema": {
224
- "type": "object",
225
- "properties": {
226
- "status": {"type": "string"},
227
- "priority": {"type": "integer"},
228
- "skill": {"type": "string"},
229
- "claimed_by": {"type": "string"}
230
- }
231
- }
232
- },
233
- {
234
- "name": "brain_add_task",
235
- "description": "Add a new task to the Brain.",
236
- "inputSchema": {
237
- "type": "object",
238
- "properties": {
239
- "description": {"type": "string"},
240
- "priority": {"type": "integer"},
241
- "blocked_by": {"type": "array", "items": {"type": "string"}},
242
- "required_skills": {"type": "array", "items": {"type": "string"}}
243
- },
244
- "required": ["description"]
245
- }
246
- },
247
- {
248
- "name": "brain_update_task",
249
- "description": "Update an existing task in the Brain.",
250
- "inputSchema": {
251
- "type": "object",
252
- "properties": {
253
- "task_id": {"type": "string"},
254
- "status": {"type": "string"},
255
- "description": {"type": "string"},
256
- "priority": {"type": "integer"}
257
- },
258
- "required": ["task_id"]
259
- }
260
- },
261
- {
262
- "name": "brain_claim_task",
263
- "description": "Claim a task for execution.",
264
- "inputSchema": {
265
- "type": "object",
266
- "properties": {
267
- "task_id": {"type": "string"},
268
- "agent_id": {"type": "string"}
269
- },
270
- "required": ["task_id"]
271
- }
272
- },
273
- {
274
- "name": "brain_get_next_task",
275
- "description": "Get the highest priority actionable task.",
276
- "inputSchema": {
277
- "type": "object",
278
- "properties": {
279
- "skills": {"type": "array", "items": {"type": "string"}}
280
- }
281
- }
282
- }
283
- ]
284
-
285
- # --- MOUNTING TOOLS ---
286
- tools.append({
287
- "name": "brain_mount_server",
288
- "description": "Mount an external MCP server (Recursive/Aggregator).",
289
- "inputSchema": {
290
- "type": "object",
291
- "properties": {
292
- "mount_id": {"type": "string", "description": "Unique ID for this mount"},
293
- "transport": {"type": "string", "enum": ["stdio", "sse"], "default": "stdio"},
294
- "command": {"type": "string", "description": "Executable for stdio"},
295
- "args": {"type": "array", "items": {"type": "string"}, "description": "Arguments for stdio"},
296
- "env": {"type": "object", "description": "Environment vars"},
297
- "url": {"type": "string", "description": "URL for SSE"}
298
- },
299
- "required": ["mount_id"]
300
- }
301
- })
302
- tools.append({
303
- "name": "brain_unmount_server",
304
- "description": "Unmount an external MCP server.",
305
- "inputSchema": {
306
- "type": "object",
307
- "properties": {
308
- "mount_id": {"type": "string"}
309
- },
310
- "required": ["mount_id"]
311
- }
312
- })
313
- tools.append({
314
- "name": "brain_list_mounts",
315
- "description": "List all active mounted servers.",
316
- "inputSchema": {"type": "object", "properties": {}}
317
- })
318
- tools.append({
319
- "name": "brain_traverse_and_mount",
320
- "description": "Recursively explore and mount downstream servers.",
321
- "inputSchema": {
322
- "type": "object",
323
- "properties": {
324
- "root_mount_id": {"type": "string"}
325
- },
326
- "required": ["root_mount_id"]
327
- }
328
- })
329
-
330
- # Aggregate Tools from Mounts
331
- try:
332
- mounted_tools = await self.mounter.list_tools()
333
- tools.extend(mounted_tools)
334
- except Exception as e:
335
- logger.error(f"Failed to list mounted tools: {e}")
336
-
337
- return {
338
- "jsonrpc": "2.0",
339
- "id": msg_id,
340
- "result": {
341
- "tools": tools
342
- }
343
- }
344
-
345
- elif method == "tools/call":
346
- params = request.get("params", {})
347
- name = params.get("name")
348
- args = params.get("arguments", {})
349
-
350
- try:
351
- # --- MOUNTER DISPATCH ---
352
- if ":" in name:
353
- # Delegate to mounted server
354
- result = await self.mounter.call_tool(name, args)
355
- # Result is a ToolCallResult object from mcp SDK. We need to serialize it.
356
- # The SDK usually returns an object with `content`.
357
- # We need to adapt it to the dict format this server expects.
358
-
359
- # Inspect result structure or assume it matches
360
- content = []
361
- if hasattr(result, "content"):
362
- for item in result.content:
363
- item_dict = item.model_dump() if hasattr(item, "model_dump") else item.__dict__
364
- content.append(item_dict)
365
- else:
366
- content = [{"type": "text", "text": str(result)}]
367
-
368
- return {
369
- "jsonrpc": "2.0",
370
- "id": msg_id,
371
- "result": {
372
- "content": content,
373
- "isError": getattr(result, "isError", False)
374
- }
375
- }
376
-
377
- # --- LOCAL DISPATCH ---
378
- if name == "brain_mount_server":
379
- res = await self.mounter.mount_server(
380
- mount_id=args["mount_id"],
381
- transport=args.get("transport", "stdio"),
382
- command=args.get("command"),
383
- args=args.get("args"),
384
- env=args.get("env"),
385
- url=args.get("url")
386
- )
387
- return {"jsonrpc": "2.0", "id": msg_id, "result": {"content": [{"type": "text", "text": json.dumps(res)}], "isError": False}}
388
-
389
- elif name == "brain_unmount_server":
390
- await self.mounter.unmount_server(args["mount_id"])
391
- return {"jsonrpc": "2.0", "id": msg_id, "result": {"content": [{"type": "text", "text": "Unmounted"}], "isError": False}}
392
-
393
- elif name == "brain_list_mounts":
394
- res = await self.mounter.list_mounts()
395
- return {"jsonrpc": "2.0", "id": msg_id, "result": {"content": [{"type": "text", "text": json.dumps(res, indent=2)}], "isError": False}}
396
-
397
- elif name == "brain_traverse_and_mount":
398
- res = await self.mounter.traverse_and_mount(args["root_mount_id"])
399
- return {"jsonrpc": "2.0", "id": msg_id, "result": {"content": [{"type": "text", "text": json.dumps(res, indent=2)}], "isError": False}}
400
-
401
- result = self.execute_tool(name, args)
402
- return {
403
- "jsonrpc": "2.0",
404
- "id": msg_id,
405
- "result": {
406
- "content": [
407
- {
408
- "type": "text",
409
- "text": str(result)
410
- }
411
- ],
412
- "isError": False
413
- }
414
- }
415
- except Exception as e:
416
- return {
417
- "jsonrpc": "2.0",
418
- "id": msg_id,
419
- "error": {
420
- "code": -32000,
421
- "message": str(e)
422
- }
423
- }
424
-
425
- def execute_tool(self, name: str, args: Dict[str, Any]) -> str:
426
- if name == "lock_resource":
427
- metadata = {}
428
- if "reason" in args:
429
- metadata["reason"] = args["reason"]
430
- if "agent_id" in args:
431
- metadata["agent_id"] = args["agent_id"]
432
-
433
- self.locker.lock(args["path"], metadata=metadata)
434
- return f"🔒 LOCKED: {args['path']}"
435
-
436
- elif name == "unlock_resource":
437
- self.locker.unlock(args["path"])
438
- return f"🔓 UNLOCKED: {args['path']}"
439
-
440
- elif name == "get_lock_metadata":
441
- meta = self.locker.get_metadata(args["path"])
442
- return json.dumps(meta, indent=2)
443
-
444
- elif name == "watch_resource":
445
- self.watchdog.protect(args["path"])
446
- return f"👁️ WATCHING: {args['path']}"
447
-
448
- elif name == "hypervisor_status":
449
- status = []
450
- status.append("🛡️ NUCLEUS HYPERVISOR v0.8.0 (God Mode / Python 3.9 Shim)")
451
- status.append(f"👁️ Watchdog: {'Active' if self.watchdog.observer.is_alive() else 'Inactive'}")
452
- status.append(f"🔒 Protected Paths: {len(self.watchdog.protected_paths)}")
453
- return "\n".join(status)
454
-
455
- elif name == "set_hypervisor_mode":
456
- mode = args["mode"]
457
- if mode == "red":
458
- self.injector.inject_identity("RED TEAM", "#ff0000")
459
- return "🔴 Hypervisor Mode: RED TEAM"
460
- elif mode == "blue":
461
- self.injector.inject_identity("BLUE TEAM", "#007acc")
462
- return "🔵 Hypervisor Mode: BLUE TEAM"
463
- elif mode == "reset":
464
- self.injector.reset_identity()
465
- return "⚪ Hypervisor Mode: RESET"
466
-
467
- # --- GOVERNANCE & HEALTH ---
468
- elif name == "brain_health":
469
- try:
470
- return json.dumps({
471
- "status": "healthy",
472
- "version": "1.0.0",
473
- "tools_registered": 15,
474
- "brain_path": str(self.brain_path),
475
- "uptime_seconds": int(time.time() - START_TIME),
476
- "python_version": sys.version.split()[0]
477
- }, indent=2)
478
- except Exception as e:
479
- return json.dumps({"status": "unhealthy", "error": str(e)})
480
-
481
- elif name == "brain_audit_log":
482
- return self._audit_log_impl(args.get("limit", 20))
483
-
484
- elif name == "brain_governance_status":
485
- return self._governance_status_impl()
486
-
487
- elif name == "brain_write_engram":
488
- return self._write_engram_impl(
489
- args["key"],
490
- args["value"],
491
- args.get("context", "Decision"),
492
- args.get("intensity", 5)
493
- )
494
-
495
- elif name == "brain_query_engrams":
496
- return self._query_engrams_impl(
497
- args.get("context"),
498
- args.get("min_intensity", 1)
499
- )
500
-
501
- # --- TASK TOOLS ---
502
- elif name == "brain_list_tasks":
503
- return json.dumps(_list_tasks(
504
- status=args.get("status"),
505
- priority=args.get("priority"),
506
- skill=args.get("skill"),
507
- claimed_by=args.get("claimed_by")
508
- ), indent=2)
509
-
510
- elif name == "brain_add_task":
511
- return json.dumps(_add_task(
512
- description=args.get("description"),
513
- priority=args.get("priority", 3),
514
- blocked_by=args.get("blocked_by"),
515
- required_skills=args.get("required_skills"),
516
- source="hypervisor"
517
- ), indent=2)
518
-
519
- elif name == "brain_update_task":
520
- updates = {k: v for k, v in args.items() if k != "task_id"}
521
- return json.dumps(_update_task(
522
- task_id=args.get("task_id"),
523
- updates=updates
524
- ), indent=2)
525
-
526
- elif name == "brain_claim_task":
527
- return json.dumps(_claim_task(
528
- task_id=args.get("task_id"),
529
- agent_id=args.get("agent_id", "hypervisor_agent")
530
- ), indent=2)
531
-
532
- elif name == "brain_get_next_task":
533
- return json.dumps(_get_next_task(
534
- skills=args.get("skills", [])
535
- ), indent=2)
536
-
537
- raise ValueError(f"Unknown tool: {name}")
538
-
539
- def _audit_log_impl(self, limit: int) -> str:
540
- try:
541
- log_path = self.brain_path / "ledger" / "interaction_log.jsonl"
542
- if not log_path.exists():
543
- return make_response(True, data={"entries": [], "count": 0, "message": "No log found."})
544
-
545
- entries = []
546
- with open(log_path, "r") as f:
547
- for line in f:
548
- if line.strip():
549
- entries.append(json.loads(line))
550
-
551
- recent = entries[-limit:] if len(entries) > limit else entries
552
- recent.reverse()
553
- return make_response(True, data={"entries": recent, "count": len(recent), "total": len(entries)})
554
- except Exception as e:
555
- return make_response(False, error=str(e))
556
-
557
- def _governance_status_impl(self) -> str:
558
- try:
559
- audit_path = self.brain_path / "ledger" / "interaction_log.jsonl"
560
- audit_count = 0
561
- if audit_path.exists():
562
- with open(audit_path, "r") as f:
563
- audit_count = sum(1 for line in f if line.strip())
564
-
565
- engram_path = self.brain_path / "engrams" / "ledger.jsonl"
566
- engram_count = 0
567
- if engram_path.exists():
568
- with open(engram_path, "r") as f:
569
- engram_count = sum(1 for line in f if line.strip())
570
-
571
- governance = {
572
- "policies": {"default_deny": True, "isolation_boundaries": True, "immutable_audit": True},
573
- "statistics": {"audit_log_entries": audit_count, "engram_count": engram_count},
574
- "status": "ENFORCED"
575
- }
576
- return make_response(True, data=governance)
577
- except Exception as e:
578
- return make_response(False, error=str(e))
579
-
580
- def _write_engram_impl(self, key: str, value: str, context: str, intensity: int) -> str:
581
- try:
582
- if not re.match(r"^[a-zA-Z0-9_.-]+$", key):
583
- return make_response(False, error="Invalid key characters")
584
-
585
- engram_path = self.brain_path / "engrams" / "ledger.jsonl"
586
- engram_path.parent.mkdir(parents=True, exist_ok=True)
587
-
588
- engram = {
589
- "key": key, "value": value, "context": context,
590
- "intensity": intensity, "timestamp": datetime.now().isoformat()
591
- }
592
- with open(engram_path, "a") as f:
593
- f.write(json.dumps(engram) + "\n")
594
-
595
- return make_response(True, data={"engram": engram, "message": f"Engram '{key}' written."})
596
- except Exception as e:
597
- return make_response(False, error=str(e))
598
-
599
- def _query_engrams_impl(self, context: Optional[str], min_intensity: int) -> str:
600
- try:
601
- engram_path = self.brain_path / "engrams" / "ledger.jsonl"
602
- if not engram_path.exists():
603
- return make_response(True, data={"engrams": [], "count": 0})
604
-
605
- engrams = []
606
- with open(engram_path, "r") as f:
607
- for line in f:
608
- if line.strip():
609
- e = json.loads(line)
610
- if context and e.get("context", "").lower() != context.lower():
611
- continue
612
- if e.get("intensity", 5) < min_intensity:
613
- continue
614
- engrams.append(e)
615
-
616
- engrams.sort(key=lambda x: x.get("intensity", 5), reverse=True)
617
- return make_response(True, data={"engrams": engrams, "count": len(engrams)})
618
- except Exception as e:
619
- return make_response(False, error=str(e))
620
-
621
- def main():
622
- sys.stderr.write("DEBUG: STDIO_SERVER MAIN START\n")
623
- sys.stderr.flush()
624
- server = StdioServer()
625
- sys.stderr.write("DEBUG: STDIO_SERVER AFTER INIT\n")
626
- sys.stderr.flush()
627
- sys.stderr.write("Nucleus Sovereign Control Plane (Stdio Mode)\n")
628
- sys.stderr.flush()
629
- # Run async main loop
630
- asyncio.run(server.run())
631
-
632
- if __name__ == "__main__":
633
- main()