use std::path::PathBuf;
use std::fs::{File, OpenOptions};
use std::io::{Read, Write, Seek, SeekFrom};
use super::{RaidController, RaidError};

pub struct RaidExporter {
    controller: RaidController,
}

impl RaidExporter {
    pub fn new(controller: RaidController) -> Self {
        RaidExporter { controller }
    }
    
    pub fn export_to_vdisk(
        &self,
        array_id: &str,
        output_path: &PathBuf,
        block_size: u64,
    ) -> Result<u64, RaidError> {
        let array = self.controller.get_array(array_id)
            .ok_or("RAID array not found")?;
        
        let total_size = array.total_size;
        
        if total_size == 0 {
            return Err("RAID array has zero size".into());
        }
        
        let mut output_file = OpenOptions::new()
            .write(true)
            .create(true)
            .truncate(true)
            .open(output_path)?;
        
        output_file.set_len(total_size)?;
        
        let mut exported_bytes = 0u64;
        let mut current_offset = 0u64;
        
        while current_offset < total_size {
            let chunk_size = std::cmp::min(block_size, total_size - current_offset);
            
            let data = match self.controller.read(array_id, current_offset, chunk_size) {
                Ok(d) => d,
                Err(_) => {
                    let zeros = vec![0u8; chunk_size as usize];
                    zeros
                },
            };
            
            output_file.seek(SeekFrom::Start(current_offset))?;
            output_file.write_all(&data)?;
            
            exported_bytes += chunk_size;
            current_offset += chunk_size;
        }
        
        output_file.sync_all()?;
        
        Ok(exported_bytes)
    }
    
    pub fn import_from_vdisk(
        &self,
        array_id: &str,
        input_path: &PathBuf,
        block_size: u64,
    ) -> Result<u64, RaidError> {
        let array = self.controller.get_array(array_id)
            .ok_or("RAID array not found")?;
        
        let total_size = array.total_size;
        
        let mut input_file = File::open(input_path)?;
        
        let mut imported_bytes = 0u64;
        let mut current_offset = 0u64;
        
        while current_offset < total_size {
            let chunk_size = std::cmp::min(block_size, total_size - current_offset);
            
            input_file.seek(SeekFrom::Start(current_offset))?;
            let mut buffer = vec![0u8; chunk_size as usize];
            input_file.read_exact(&mut buffer)?;
            
            self.controller.write(array_id, current_offset, &buffer)?;
            
            imported_bytes += chunk_size;
            current_offset += chunk_size;
        }
        
        Ok(imported_bytes)
    }
}

#[cfg(test)]
mod tests {
    use super::*;
    use std::path::PathBuf;
    
    #[test]
    fn test_exporter_creation() {
        let controller = RaidController::new();
        let exporter = RaidExporter::new(controller);
        assert!(true);
    }
}