fix: comprehensive audit fixes for dashboard and backend

Backend:
- Emit WebSocket events from REST delete/promote/demote handlers
- Emit DreamStarted/ConsolidationStarted from MCP tool dispatch
- Add path validation in backup_to() for defense-in-depth

Dashboard:
- Fix ConnectionDiscovered field names (source_id/target_id)
- Fix $effect → onMount in settings (prevents infinite loop)
- Fix $derived → $derived.by in RetentionCurve
- Fix field name mismatches in settings (nodesProcessed, etc.)
- Fix nested <button> → <span role="button"> in memories
- Fix unhandled Promise rejection in stats consolidation
- Add missing EVENT_TYPE_COLORS entries
- Add Three.js resource disposal and event listener cleanup
- Eliminate duplicate root page, redirect to /graph
- Update nav links and keyboard shortcuts to /graph

All 734+ tests passing, 22MB binary, zero build warnings.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Sam Valladares 2026-02-22 15:50:47 -06:00
parent 22831af509
commit ec2af6e71b
220 changed files with 347 additions and 443 deletions

View file

@ -157,6 +157,10 @@ pub async fn delete_memory(
.map_err(|_| StatusCode::INTERNAL_SERVER_ERROR)?;
if deleted {
state.emit(VestigeEvent::MemoryDeleted {
id: id.clone(),
timestamp: chrono::Utc::now(),
});
Ok(Json(serde_json::json!({ "deleted": true, "id": id })))
} else {
Err(StatusCode::NOT_FOUND)
@ -172,6 +176,12 @@ pub async fn promote_memory(
.promote_memory(&id)
.map_err(|_| StatusCode::INTERNAL_SERVER_ERROR)?;
state.emit(VestigeEvent::MemoryPromoted {
id: node.id.clone(),
new_retention: node.retention_strength,
timestamp: chrono::Utc::now(),
});
Ok(Json(serde_json::json!({
"promoted": true,
"id": node.id,
@ -188,6 +198,12 @@ pub async fn demote_memory(
.demote_memory(&id)
.map_err(|_| StatusCode::INTERNAL_SERVER_ERROR)?;
state.emit(VestigeEvent::MemoryDemoted {
id: node.id.clone(),
new_retention: node.retention_strength,
timestamp: chrono::Utc::now(),
});
Ok(Json(serde_json::json!({
"demoted": true,
"id": node.id,

View file

@ -604,7 +604,12 @@ impl McpServer {
// ================================================================
// MAINTENANCE TOOLS (v1.2+, non-deprecated)
// ================================================================
"consolidate" => tools::maintenance::execute_consolidate(&self.storage, request.arguments).await,
"consolidate" => {
self.emit(VestigeEvent::ConsolidationStarted {
timestamp: chrono::Utc::now(),
});
tools::maintenance::execute_consolidate(&self.storage, request.arguments).await
}
"backup" => tools::maintenance::execute_backup(&self.storage, request.arguments).await,
"export" => tools::maintenance::execute_export(&self.storage, request.arguments).await,
"gc" => tools::maintenance::execute_gc(&self.storage, request.arguments).await,
@ -618,7 +623,13 @@ impl McpServer {
// ================================================================
// COGNITIVE TOOLS (v1.5+)
// ================================================================
"dream" => tools::dream::execute(&self.storage, &self.cognitive, request.arguments).await,
"dream" => {
self.emit(VestigeEvent::DreamStarted {
memory_count: self.storage.get_stats().map(|s| s.total_nodes as usize).unwrap_or(0),
timestamp: chrono::Utc::now(),
});
tools::dream::execute(&self.storage, &self.cognitive, request.arguments).await
}
"explore_connections" => tools::explore::execute(&self.storage, &self.cognitive, request.arguments).await,
"predict" => tools::predict::execute(&self.storage, &self.cognitive, request.arguments).await,
"restore" => tools::restore::execute(&self.storage, request.arguments).await,