Skip to content
Merged
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
185 changes: 184 additions & 1 deletion backend/api/consciousness_endpoints.py
Original file line number Diff line number Diff line change
Expand Up @@ -257,6 +257,84 @@ async def get_emergence_score():
logger.error(f"Failed to get emergence score: {e}")
raise HTTPException(status_code=500, detail=f"Failed to retrieve emergence score: {str(e)}")


@router.get("/breakthroughs")
async def get_breakthroughs(limit: int = Query(50, ge=1, le=500)):
"""Return historical breakthrough log entries (newest first).

Reads the persistent ``logs/breakthroughs.jsonl`` file and returns up to
*limit* entries. Returns an empty list when no breakthroughs have been
recorded yet.
"""
try:
if emergence_detector is not None:
entries = emergence_detector.get_breakthroughs(limit=limit)
return {
"breakthroughs": entries,
"total": len(entries),
"limit": limit,
"threshold": emergence_detector.threshold,
}
raise HTTPException(
status_code=503,
detail="Emergence detector is not initialised",
)
except HTTPException:
raise
except Exception as e:
logger.error(f"Failed to get breakthroughs: {e}")
raise HTTPException(status_code=500, detail=f"Failed to retrieve breakthroughs: {str(e)}")


# Observatory reference — set by unified_server at startup
_observatory = None


def set_observatory(observatory) -> None:
"""Register the UnifiedConsciousnessObservatory instance."""
global _observatory
_observatory = observatory


def get_observatory():
"""Return the active UnifiedConsciousnessObservatory instance (may be None)."""
return _observatory


@router.get("/observatory")
async def get_observatory_report():
"""Return the full UnifiedConsciousnessObservatory report.

Includes uptime, total observed states, total breakthrough events, peak
score, current emergence snapshot, and the 10 most recent breakthroughs.
"""
try:
if _observatory is not None:
return _observatory.get_report()
# Fallback: lightweight report using the detector only
if emergence_detector is not None:
status = emergence_detector.get_emergence_status()
recent = emergence_detector.get_breakthroughs(limit=10)
return {
"running": False,
"uptime_seconds": 0,
"total_states_observed": 0,
"total_breakthroughs": len(recent),
"peak_score": status.get("emergence_score", 0.0),
"current_emergence": status,
"recent_breakthroughs": recent,
}
raise HTTPException(
status_code=503,
detail="Neither observatory nor emergence detector is available",
)
except HTTPException:
raise
except Exception as e:
logger.error(f"Failed to get observatory report: {e}")
raise HTTPException(status_code=500, detail=f"Failed to retrieve observatory report: {str(e)}")


# WebSocket endpoints for real-time consciousness streaming

@router.websocket("/stream")
Expand Down Expand Up @@ -313,6 +391,104 @@ async def global_workspace_stream(websocket: WebSocket):

await enhanced_websocket_manager.handle_consciousness_connection(websocket, "workspace")


# ---------------------------------------------------------------------------
# Autonomous Goal Engine endpoints (Issue #81)
# ---------------------------------------------------------------------------

# Module-level references populated at startup by unified_server
_goal_generator = None
_creative_engine = None


def set_goal_engine(generator, creative_engine) -> None:
"""Register the AutonomousGoalGenerator and CreativeSynthesisEngine."""
global _goal_generator, _creative_engine
_goal_generator = generator
_creative_engine = creative_engine


@router.get("/goals")
async def get_autonomous_goals():
"""Return the currently active autonomous goals generated by the system.

Goals are produced without external prompting by monitoring cognitive
state gaps (low phi, coherence drift, knowledge gaps, etc.).
"""
try:
if _goal_generator is not None:
goals = _goal_generator.active_goals
metrics = _goal_generator.get_metrics()
return {
"goals": goals,
"total": len(goals),
"metrics": metrics,
}
raise HTTPException(
status_code=503,
detail="Autonomous goal generator is not initialised",
)
except HTTPException:
raise
except Exception as e:
logger.error(f"Failed to get autonomous goals: {e}")
raise HTTPException(status_code=500, detail=f"Failed to retrieve goals: {str(e)}")


@router.post("/goals/generate")
async def trigger_goal_generation():
"""Manually trigger a round of autonomous goal generation.

Useful for testing or seeding the goal list before any cognitive state
has been observed. Returns the newly proposed goals.
"""
try:
if _goal_generator is not None:
# Use an empty cognitive state to trigger baseline exploration
new_goals = await _goal_generator.generate({})
return {
"new_goals": new_goals,
"total_new": len(new_goals),
"active_total": len(_goal_generator.active_goals),
}
raise HTTPException(
status_code=503,
detail="Autonomous goal generator is not initialised",
)
except HTTPException:
raise
except Exception as e:
logger.error(f"Failed to generate autonomous goals: {e}")
raise HTTPException(status_code=500, detail=f"Failed to generate goals: {str(e)}")


@router.get("/creative-synthesis")
async def get_creative_synthesis(n: int = Query(5, ge=1, le=20)):
"""Return the most recent creative concept-synthesis outputs.

The CreativeSynthesisEngine combines concepts from the active knowledge
store and scores them on novelty and coherence.
"""
try:
if _creative_engine is not None:
outputs = _creative_engine.get_recent_outputs(limit=n)
metrics = _creative_engine.get_metrics()
return {
"syntheses": outputs,
"total": len(outputs),
"metrics": metrics,
}
raise HTTPException(
status_code=503,
detail="Creative synthesis engine is not initialised",
)
except HTTPException:
raise
except Exception as e:
logger.error(f"Failed to get creative syntheses: {e}")
raise HTTPException(status_code=500, detail=f"Failed to retrieve syntheses: {str(e)}")


# Health and statistics endpoints

@router.get("/health")
Expand Down Expand Up @@ -410,4 +586,11 @@ async def assess_consciousness_level(query: str = "", context: Optional[Dict] =
raise HTTPException(status_code=500, detail=f"Assessment failed: {str(e)}")

# Export router
__all__ = ['router', 'set_consciousness_engine', 'set_emergence_detector']
__all__ = [
'router',
'set_consciousness_engine',
'set_emergence_detector',
'set_observatory',
'get_observatory',
'set_goal_engine',
]
Loading
Loading