diff --git a/README.md b/README.md index 06343f25..5362ee1f 100644 --- a/README.md +++ b/README.md @@ -165,6 +165,25 @@ Then setup Atuin echo 'eval "$(atuin init bash)"' >> ~/.bashrc ``` +### nushell + +#### Manual + +Open up your config file in your editor (run `config path` to locate the file). + +Add these two items to your startup section + +``` +"atuin init nushell | save ~/.atuin.nu", +"source ~/.atuin.nu", +``` + +#### Automatic + +```nu +config get startup | append 'atuin init nushell | save ~/.atuin.nu' | append 'source ~/.atuin.nu' | config set_into startup +``` + ## ...what's with the name? Atuin is named after "The Great A'Tuin", a giant turtle from Terry Pratchett's diff --git a/atuin-client/src/import/mod.rs b/atuin-client/src/import/mod.rs index 135e1d19..dbaf486e 100644 --- a/atuin-client/src/import/mod.rs +++ b/atuin-client/src/import/mod.rs @@ -6,9 +6,9 @@ use eyre::Result; use crate::history::History; pub mod bash; +pub mod nu; pub mod resh; pub mod zsh; -pub mod nu; // this could probably be sped up fn count_lines(buf: &mut BufReader) -> Result { diff --git a/atuin-client/src/import/nu.rs b/atuin-client/src/import/nu.rs index 87c7e19e..542583fc 100644 --- a/atuin-client/src/import/nu.rs +++ b/atuin-client/src/import/nu.rs @@ -35,10 +35,7 @@ impl Importer for Nu { let mut hist = history::History::new(); hist.load(path)?; let len = hist.len(); - Ok(Self { - hist, - iter: 0..len, - }) + Ok(Self { hist, iter: 0..len }) } } diff --git a/src/command/history.rs b/src/command/history.rs index 9c792cf0..4606b304 100644 --- a/src/command/history.rs +++ b/src/command/history.rs @@ -60,7 +60,7 @@ pub enum Cmd { }, } -#[allow(clippy::clippy::cast_sign_loss)] +#[allow(clippy::cast_sign_loss)] pub fn print_list(h: &[History], human: bool, cmd_only: bool) { let mut writer = TabWriter::new(std::io::stdout()).padding(2); diff --git a/src/command/import.rs b/src/command/import.rs index 751315bf..d8811d4d 100644 --- a/src/command/import.rs +++ b/src/command/import.rs @@ -37,8 +37,9 @@ pub enum Cmd { #[structopt( about="import history from the nu history file", + aliases=&["nu"], )] - Nu, + Nushell, } const BATCH_SIZE: usize = 100; @@ -72,7 +73,7 @@ impl Cmd { Self::Zsh => import::, _>(db, BATCH_SIZE).await, Self::Bash => import::, _>(db, BATCH_SIZE).await, Self::Resh => import::(db, BATCH_SIZE).await, - Self::Nu => import::(db, BATCH_SIZE).await, + Self::Nushell => import::(db, BATCH_SIZE).await, } } } diff --git a/src/command/init.rs b/src/command/init.rs index d0f31f34..bf70da3d 100644 --- a/src/command/init.rs +++ b/src/command/init.rs @@ -7,6 +7,8 @@ pub enum Cmd { Zsh, #[structopt(about = "bash setup")] Bash, + #[structopt(about = "nu setup")] + Nushell, } fn init_zsh() { @@ -19,11 +21,17 @@ fn init_bash() { println!("{}", full); } +fn init_nu() { + let full = include_str!("../shell/atuin.nu"); + println!("{}", full); +} + impl Cmd { pub fn run(&self) -> Result<()> { match self { Self::Zsh => init_zsh(), Self::Bash => init_bash(), + Self::Nushell => init_nu(), } Ok(()) } diff --git a/src/command/search.rs b/src/command/search.rs index d3807bca..1468a36e 100644 --- a/src/command/search.rs +++ b/src/command/search.rs @@ -31,7 +31,7 @@ struct State { } impl State { - #[allow(clippy::clippy::cast_sign_loss)] + #[allow(clippy::cast_sign_loss)] fn durations(&self) -> Vec<(String, String)> { self.results .iter() @@ -179,7 +179,7 @@ async fn key_handler( app: &mut State, ) -> Option { match input { - Key::Esc | Key::Ctrl('c') | Key::Ctrl('d') | Key::Ctrl('g') => { + Key::Esc | Key::Ctrl('c' | 'd' | 'g') => { return Some(String::from("")) } Key::Char('\n') => { @@ -241,7 +241,7 @@ async fn key_handler( None } -#[allow(clippy::clippy::cast_possible_truncation)] +#[allow(clippy::cast_possible_truncation)] fn draw(f: &mut Frame<'_, T>, history_count: i64, app: &mut State) { let chunks = Layout::default() .direction(Direction::Vertical) @@ -312,7 +312,7 @@ fn draw(f: &mut Frame<'_, T>, history_count: i64, app: &mut State) { // this is a big blob of horrible! clean it up! // for now, it works. But it'd be great if it were more easily readable, and // modular. I'd like to add some more stats and stuff at some point -#[allow(clippy::clippy::cast_possible_truncation)] +#[allow(clippy::cast_possible_truncation)] async fn select_history( query: &[String], search_mode: SearchMode, @@ -350,7 +350,7 @@ async fn select_history( // This is supposed to more-or-less mirror the command line version, so ofc // it is going to have a lot of args -#[allow(clippy::clippy::clippy::too_many_arguments)] +#[allow(clippy::clippy::too_many_arguments)] pub async fn run( settings: &Settings, cwd: Option, diff --git a/src/shell/atuin.nu b/src/shell/atuin.nu new file mode 100644 index 00000000..be5dd3e9 --- /dev/null +++ b/src/shell/atuin.nu @@ -0,0 +1,24 @@ +# Default prompt for Nushell. +def __atuin_prompt [] { + let git = $'(do -i {git rev-parse --abbrev-ref HEAD} | str trim)' + let git = (if ($git | str length) == 0 { + '' + } { + build-string (char lparen) (ansi cb) $git (ansi reset) (char rparen) + }) + build-string (ansi gb) (pwd) (ansi reset) $git '> ' +} + +# Hook to add new entries to the database. +def __atuin_hook [] { + echo command took $CMD_DURATION_MS +} + +# Initialize hook. +let-env PROMPT_STRING = ( + let prompt = (if ($nu.env | select PROMPT_STRING | empty?) { + if ($nu.config | select prompt | empty?) { '__atuin_prompt' } { $nu.config.prompt } + } { $nu.env.PROMPT_STRING }); + + if ($prompt | str contains '__atuin_hook') { $prompt } { $'__atuin_hook;($prompt)' } +)