use std::path::PathBuf;

use chrono::{DateTime, Utc};
use serde::{Deserialize, Serialize};
use uuid::Uuid;

use crate::error::Result;

/// Handle to an active worktree managed by the system
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct WorktreeHandle {
    /// Unique worktree identifier
    pub id: String,
    /// Agent ID that owns this worktree
    pub agent_id: String,
    /// Branch name created for this worktree
    pub branch: String,
    /// Path to the worktree on disk
    pub path: PathBuf,
    /// When the worktree was created
    pub created_at: DateTime<Utc>,
    /// Whether changes can still be made
    pub is_active: bool,
}

impl WorktreeHandle {
    /// Create a new worktree handle
    pub fn new(agent_id: String, branch: String, path: PathBuf) -> Self {
        Self {
            id: Uuid::new_v4().to_string(),
            agent_id,
            branch,
            path,
            created_at: Utc::now(),
            is_active: true,
        }
    }

    /// Mark worktree as inactive (no more changes allowed)
    pub fn deactivate(&mut self) {
        self.is_active = false;
    }

    /// Check if worktree is still active for modifications
    pub fn can_modify(&self) -> Result<()> {
        if !self.is_active {
            return Err(crate::error::WorktreeError::InvalidState(format!(
                "Worktree {} is no longer active",
                self.id
            )));
        }
        Ok(())
    }
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn test_handle_creation() {
        let handle = WorktreeHandle::new(
            "agent-001".to_string(),
            "feature/test".to_string(),
            PathBuf::from("/tmp/wt-001"),
        );

        assert_eq!(handle.agent_id, "agent-001");
        assert_eq!(handle.branch, "feature/test");
        assert!(handle.is_active);
    }

    #[test]
    fn test_deactivate() {
        let mut handle = WorktreeHandle::new(
            "agent-001".to_string(),
            "feature/test".to_string(),
            PathBuf::from("/tmp/wt-001"),
        );

        assert!(handle.can_modify().is_ok());
        handle.deactivate();
        assert!(handle.can_modify().is_err());
    }
}
