/// The path to the default TTY on linux
pub const TTY_PATH: &str = "/dev/tty";

#[cfg(unix)]
pub(crate) mod imp {
    use std::{
        fs::File,
        io,
        io::{BufRead, Read, Write},
    };

    use parking_lot::{const_mutex, lock_api::MutexGuard, Mutex, RawMutex};
    use rustix::termios::{self, Termios};

    use crate::{unix::TTY_PATH, Error, Mode, Options};

    static TERM_STATE: Mutex<Option<Termios>> = const_mutex(None);

    /// Ask the user given a `prompt`, returning the result.
    pub(crate) fn ask(prompt: &str, Options { mode, .. }: &Options<'_>) -> Result<String, Error> {
        match mode {
            Mode::Disable => Err(Error::Disabled),
            Mode::Hidden => {
                let state = TERM_STATE.lock();
                let mut in_out = save_term_state_and_disable_echo(
                    state,
                    std::fs::OpenOptions::new().write(true).read(true).open(TTY_PATH)?,
                )?;
                in_out.write_all(prompt.as_bytes())?;

                let mut buf_read = std::io::BufReader::with_capacity(64, in_out);
                let mut out = String::with_capacity(64);
                buf_read.read_line(&mut out)?;

                out.pop();
                if out.ends_with('\r') {
                    out.pop();
                }
                buf_read.into_inner().restore_term_state()?;
                Ok(out)
            }
            Mode::Visible => {
                let mut in_out = std::fs::OpenOptions::new().write(true).read(true).open(TTY_PATH)?;
                in_out.write_all(prompt.as_bytes())?;

                let mut buf_read = std::io::BufReader::with_capacity(64, in_out);
                let mut out = String::with_capacity(64);
                buf_read.read_line(&mut out)?;
                Ok(out.trim_end().to_owned())
            }
        }
    }

    type TermiosGuard<'a> = MutexGuard<'a, RawMutex, Option<Termios>>;

    struct RestoreTerminalStateOnDrop<'a> {
        state: TermiosGuard<'a>,
        fd: File,
    }

    impl<'a> Read for RestoreTerminalStateOnDrop<'a> {
        fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
            self.fd.read(buf)
        }

        fn read_vectored(&mut self, bufs: &mut [io::IoSliceMut<'_>]) -> io::Result<usize> {
            self.fd.read_vectored(bufs)
        }
    }

    impl<'a> Write for RestoreTerminalStateOnDrop<'a> {
        #[inline(always)]
        fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
            self.fd.write(buf)
        }

        #[inline(always)]
        fn write_vectored(&mut self, bufs: &[io::IoSlice<'_>]) -> io::Result<usize> {
            self.fd.write_vectored(bufs)
        }

        #[inline(always)]
        fn flush(&mut self) -> io::Result<()> {
            self.fd.flush()
        }
    }

    impl<'a> RestoreTerminalStateOnDrop<'a> {
        fn restore_term_state(mut self) -> Result<(), Error> {
            let state = self.state.take().expect("BUG: we exist only if something is saved");
            termios::tcsetattr(&self.fd, termios::OptionalActions::Flush, &state)?;
            Ok(())
        }
    }

    impl<'a> Drop for RestoreTerminalStateOnDrop<'a> {
        fn drop(&mut self) {
            if let Some(state) = self.state.take() {
                termios::tcsetattr(&self.fd, termios::OptionalActions::Flush, &state).ok();
            }
        }
    }

    fn save_term_state_and_disable_echo(
        mut state: TermiosGuard<'_>,
        fd: File,
    ) -> Result<RestoreTerminalStateOnDrop<'_>, Error> {
        assert!(
            state.is_none(),
            "BUG: recursive calls are not possible and we restore afterwards"
        );

        let prev = termios::tcgetattr(&fd)?;
        let mut new = prev.clone();
        *state = prev.into();

        new.local_modes &= !termios::LocalModes::ECHO;
        new.local_modes |= termios::LocalModes::ECHONL;
        termios::tcsetattr(&fd, termios::OptionalActions::Flush, &new)?;

        Ok(RestoreTerminalStateOnDrop { fd, state })
    }
}
