use crate::server::LspServer;
use log::info;
use ropey::Rope;
use std::process::{Command, Stdio};
use tower_lsp::lsp_types::*;

impl LspServer {
    pub fn formatting(&self, params: DocumentFormattingParams) -> Option<Vec<TextEdit>> {
        None
        // let uri = params.text_document.uri;
        // info!("formatting {}", &uri);
        // let file_id = self.srcs.get_id(&uri).to_owned();
        // self.srcs.wait_parse_ready(file_id, false);
        // let file = self.srcs.get_file(file_id)?;
        // let file = file.read().ok()?;

        // let conf = self.configuration.read().unwrap();
        // if conf.verible.format.enabled {
        //     Some(vec![TextEdit::new(
        //         Range::new(
        //             file.text.char_to_pos(0),
        //             file.text.char_to_pos(file.text.len_chars()),
        //         ),
        //         format_document(
        //             &file.text,
        //             None,
        //             &conf.verible.format.path,
        //             &conf.verible.format.args,
        //         )?,
        //     )])
        // } else {
        //     None
        // }
    }

    pub fn range_formatting(&self, params: DocumentRangeFormattingParams) -> Option<Vec<TextEdit>> {
        None
        // let uri = params.text_document.uri;
        // info!("range formatting {}", &uri);
        // let file_id = self.srcs.get_id(&uri).to_owned();
        // self.srcs.wait_parse_ready(file_id, false);
        // let file = self.srcs.get_file(file_id)?;
        // let file = file.read().ok()?;

        // let conf = self.configuration.read().unwrap();
        // if conf.verible.format.enabled {
        //     Some(vec![TextEdit::new(
        //         file.text.char_range_to_range(0..file.text.len_chars()),
        //         format_document(
        //             &file.text,
        //             Some(params.range),
        //             &conf.verible.format.path,
        //             &conf.verible.format.args,
        //         )?,
        //     )])
        // } else {
    //         None
    //     }
    }
}

/// format the document using verible-verilog-format
pub fn format_document(
    rope: &Rope,
    range: Option<Range>,
    verible_format_path: &str,
    verible_format_args: &[String],
) -> Option<String> {
    let mut child = Command::new(verible_format_path);
    child
        .stdin(Stdio::piped())
        .stderr(Stdio::piped())
        .stdout(Stdio::piped())
        .args(verible_format_args);
    // rangeFormatting
    if let Some(r) = range {
        child
            .arg("--lines")
            .arg(format!("{}-{}", r.start.line + 1, r.end.line + 1));
    }
    let mut child = child.arg("-").spawn().ok()?;

    // write file to stdin, read output from stdout
    rope.write_to(child.stdin.as_mut()?).ok()?;
    let output = child.wait_with_output().ok()?;
    if output.status.success() {
        info!("formatting succeeded");
        let raw_output = String::from_utf8(output.stdout).ok()?;
        Some(raw_output)
    } else {
        None
    }
}
