summaryrefslogtreecommitdiff
path: root/makima/src/server/handlers/mesh_daemon.rs
diff options
context:
space:
mode:
authorsoryu <soryu@soryu.co>2026-01-15 17:59:37 +0000
committersoryu <soryu@soryu.co>2026-01-15 17:59:37 +0000
commit11c78ade600a2d74b8f033f18045a0c28fac4362 (patch)
tree19a62408769292cefd2f990f9fd8d9fff43becdf /makima/src/server/handlers/mesh_daemon.rs
parent3efdab36ca61a6795454668881d5b925abe22bd3 (diff)
downloadsoryu-11c78ade600a2d74b8f033f18045a0c28fac4362.tar.gz
soryu-11c78ade600a2d74b8f033f18045a0c28fac4362.zip
Implement simple git checkpoint command for supervisor
Diffstat (limited to 'makima/src/server/handlers/mesh_daemon.rs')
-rw-r--r--makima/src/server/handlers/mesh_daemon.rs124
1 files changed, 124 insertions, 0 deletions
diff --git a/makima/src/server/handlers/mesh_daemon.rs b/makima/src/server/handlers/mesh_daemon.rs
index 39b12da..0d00f5b 100644
--- a/makima/src/server/handlers/mesh_daemon.rs
+++ b/makima/src/server/handlers/mesh_daemon.rs
@@ -381,6 +381,35 @@ pub enum DaemonMessage {
/// Error message if operation failed
error: Option<String>,
},
+ /// Notification that a checkpoint was created
+ CheckpointCreated {
+ #[serde(rename = "taskId")]
+ task_id: Uuid,
+ /// Whether the operation succeeded
+ success: bool,
+ /// Commit SHA if successful
+ #[serde(rename = "commitSha")]
+ commit_sha: Option<String>,
+ /// Branch name where checkpoint was created
+ #[serde(rename = "branchName")]
+ branch_name: Option<String>,
+ /// Checkpoint number in sequence
+ #[serde(rename = "checkpointNumber")]
+ checkpoint_number: Option<i32>,
+ /// Files changed in this checkpoint
+ #[serde(rename = "filesChanged")]
+ files_changed: Option<serde_json::Value>,
+ /// Lines added
+ #[serde(rename = "linesAdded")]
+ lines_added: Option<i32>,
+ /// Lines removed
+ #[serde(rename = "linesRemoved")]
+ lines_removed: Option<i32>,
+ /// Error message if operation failed
+ error: Option<String>,
+ /// User-provided checkpoint message
+ message: String,
+ },
}
/// Validated daemon authentication result.
@@ -1115,6 +1144,101 @@ async fn handle_daemon_connection(socket: WebSocket, state: SharedState, auth_re
});
}
}
+ Ok(DaemonMessage::CheckpointCreated {
+ task_id,
+ success,
+ commit_sha,
+ branch_name,
+ checkpoint_number: _, // We'll get from DB
+ files_changed,
+ lines_added,
+ lines_removed,
+ error,
+ message,
+ }) => {
+ tracing::info!(
+ task_id = %task_id,
+ success = success,
+ commit_sha = ?commit_sha,
+ "Checkpoint created notification received"
+ );
+
+ if success {
+ if let (Some(sha), Some(branch)) = (commit_sha.clone(), branch_name.clone()) {
+ // Store checkpoint in database
+ if let Some(pool) = state.db_pool.as_ref() {
+ match repository::create_task_checkpoint(
+ pool,
+ task_id,
+ &sha,
+ &branch,
+ &message,
+ files_changed.clone(),
+ lines_added,
+ lines_removed,
+ ).await {
+ Ok(checkpoint) => {
+ tracing::info!(
+ task_id = %task_id,
+ checkpoint_id = %checkpoint.id,
+ checkpoint_number = checkpoint.checkpoint_number,
+ "Checkpoint stored in database"
+ );
+
+ // Broadcast success as task output
+ state.broadcast_task_output(TaskOutputNotification {
+ task_id,
+ owner_id: Some(owner_id),
+ message_type: "system".to_string(),
+ content: format!(
+ "✓ Checkpoint #{} created: {} ({})",
+ checkpoint.checkpoint_number,
+ message,
+ &sha[..7.min(sha.len())]
+ ),
+ tool_name: None,
+ tool_input: None,
+ is_error: Some(false),
+ cost_usd: None,
+ duration_ms: None,
+ is_partial: false,
+ });
+ }
+ Err(e) => {
+ tracing::error!(error = %e, "Failed to store checkpoint in database");
+ state.broadcast_task_output(TaskOutputNotification {
+ task_id,
+ owner_id: Some(owner_id),
+ message_type: "error".to_string(),
+ content: format!("Checkpoint commit succeeded but DB storage failed: {}", e),
+ tool_name: None,
+ tool_input: None,
+ is_error: Some(true),
+ cost_usd: None,
+ duration_ms: None,
+ is_partial: false,
+ });
+ }
+ }
+ }
+ }
+ } else {
+ // Broadcast failure
+ let error_msg = error.unwrap_or_else(|| "Unknown error".to_string());
+ state.broadcast_task_output(TaskOutputNotification {
+ task_id,
+ owner_id: Some(owner_id),
+ message_type: "error".to_string(),
+ content: format!("✗ Checkpoint failed: {}", error_msg),
+ tool_name: None,
+ tool_input: None,
+ is_error: Some(true),
+ cost_usd: None,
+ duration_ms: None,
+ is_partial: false,
+ });
+ }
+ }
Err(e) => {
tracing::warn!("Failed to parse daemon message: {}", e);
}