mirror of
https://github.com/clap-rs/clap
synced 2024-12-14 06:42:33 +00:00
Merge pull request #5647 from epage/infer
feat(complete): Infer shell for dynamic completions
This commit is contained in:
commit
efdcad16e9
4 changed files with 77 additions and 14 deletions
|
@ -10,14 +10,77 @@ use clap::ValueEnum;
|
|||
pub enum Shell {
|
||||
/// Bourne Again `SHell` (bash)
|
||||
Bash,
|
||||
/// Elvish shell
|
||||
Elvish,
|
||||
/// Friendly Interactive `SHell` (fish)
|
||||
Fish,
|
||||
/// Z shell (zsh)
|
||||
Zsh,
|
||||
/// Elf `SHell` (elvish)
|
||||
Elvish,
|
||||
/// Powerful `SHell` (powershel)
|
||||
/// `PowerShell`
|
||||
Powershell,
|
||||
/// Z `SHell` (zsh)
|
||||
Zsh,
|
||||
}
|
||||
|
||||
impl Shell {
|
||||
/// Parse a shell from a path to the executable for the shell
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// use clap_complete::shells::Shell;
|
||||
///
|
||||
/// assert_eq!(Shell::from_shell_path("/bin/bash"), Some(Shell::Bash));
|
||||
/// assert_eq!(Shell::from_shell_path("/usr/bin/zsh"), Some(Shell::Zsh));
|
||||
/// assert_eq!(Shell::from_shell_path("/opt/my_custom_shell"), None);
|
||||
/// ```
|
||||
pub fn from_shell_path(path: impl AsRef<std::path::Path>) -> Option<Shell> {
|
||||
parse_shell_from_path(path.as_ref())
|
||||
}
|
||||
|
||||
/// Determine the user's current shell from the environment
|
||||
///
|
||||
/// This will read the SHELL environment variable and try to determine which shell is in use
|
||||
/// from that.
|
||||
///
|
||||
/// If SHELL is not set, then on windows, it will default to powershell, and on
|
||||
/// other operating systems it will return `None`.
|
||||
///
|
||||
/// If SHELL is set, but contains a value that doesn't correspond to one of the supported shell
|
||||
/// types, then return `None`.
|
||||
///
|
||||
/// # Example:
|
||||
///
|
||||
/// ```no_run
|
||||
/// # use clap::Command;
|
||||
/// use clap_complete::{generate, shells::Shell};
|
||||
/// # fn build_cli() -> Command {
|
||||
/// # Command::new("compl")
|
||||
/// # }
|
||||
/// let shell = Shell::from_env();
|
||||
/// println!("{shell:?}");
|
||||
/// ```
|
||||
pub fn from_env() -> Option<Shell> {
|
||||
if let Some(env_shell) = std::env::var_os("SHELL") {
|
||||
Shell::from_shell_path(env_shell)
|
||||
} else if cfg!(windows) {
|
||||
Some(Shell::Powershell)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// use a separate function to avoid having to monomorphize the entire function due
|
||||
// to from_shell_path being generic
|
||||
fn parse_shell_from_path(path: &std::path::Path) -> Option<Shell> {
|
||||
let name = path.file_stem()?.to_str()?;
|
||||
match name {
|
||||
"bash" => Some(Shell::Bash),
|
||||
"elvish" => Some(Shell::Elvish),
|
||||
"fish" => Some(Shell::Fish),
|
||||
"powershell" | "powershell_ise" => Some(Shell::Powershell),
|
||||
"zsh" => Some(Shell::Zsh),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Shell {
|
||||
|
@ -47,20 +110,20 @@ impl ValueEnum for Shell {
|
|||
fn value_variants<'a>() -> &'a [Self] {
|
||||
&[
|
||||
Shell::Bash,
|
||||
Shell::Fish,
|
||||
Shell::Zsh,
|
||||
Shell::Elvish,
|
||||
Shell::Fish,
|
||||
Shell::Powershell,
|
||||
Shell::Zsh,
|
||||
]
|
||||
}
|
||||
|
||||
fn to_possible_value(&self) -> Option<PossibleValue> {
|
||||
Some(match self {
|
||||
Shell::Bash => PossibleValue::new("bash"),
|
||||
Shell::Fish => PossibleValue::new("fish"),
|
||||
Shell::Zsh => PossibleValue::new("zsh"),
|
||||
Shell::Elvish => PossibleValue::new("elvish"),
|
||||
Shell::Fish => PossibleValue::new("fish"),
|
||||
Shell::Powershell => PossibleValue::new("powershell"),
|
||||
Shell::Zsh => PossibleValue::new("zsh"),
|
||||
})
|
||||
}
|
||||
}
|
||||
|
@ -69,10 +132,10 @@ impl Shell {
|
|||
fn completer(&self) -> &dyn crate::dynamic::shells::ShellCompleter {
|
||||
match self {
|
||||
Self::Bash => &super::Bash,
|
||||
Self::Fish => &super::Fish,
|
||||
Self::Zsh => &super::Zsh,
|
||||
Self::Elvish => &super::Elvish,
|
||||
Self::Fish => &super::Fish,
|
||||
Self::Powershell => &super::Powershell,
|
||||
Self::Zsh => &super::Zsh,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -245,7 +245,7 @@ _exhaustive() {
|
|||
fi
|
||||
case "${prev}" in
|
||||
--shell)
|
||||
COMPREPLY=($(compgen -W "bash fish zsh elvish powershell" -- "${cur}"))
|
||||
COMPREPLY=($(compgen -W "bash elvish fish powershell zsh" -- "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--register)
|
||||
|
|
|
@ -136,7 +136,7 @@ complete -c exhaustive -n "__fish_exhaustive_using_subcommand hint" -l email -r
|
|||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand hint" -l global -d 'everywhere'
|
||||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand hint" -s h -l help -d 'Print help'
|
||||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand hint" -s V -l version -d 'Print version'
|
||||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand complete" -l shell -d 'Specify shell to complete for' -r -f -a "{bash\t'',fish\t'',zsh\t'',elvish\t'',powershell\t''}"
|
||||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand complete" -l shell -d 'Specify shell to complete for' -r -f -a "{bash\t'',elvish\t'',fish\t'',powershell\t'',zsh\t''}"
|
||||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand complete" -l register -d 'Path to write completion-registration to' -r -F
|
||||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand complete" -l global -d 'everywhere'
|
||||
complete -c exhaustive -n "__fish_exhaustive_using_subcommand complete" -s h -l help -d 'Print help (see more with \'--help\')'
|
||||
|
|
|
@ -325,7 +325,7 @@ _arguments "${_arguments_options[@]}" : \
|
|||
;;
|
||||
(complete)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'--shell=[Specify shell to complete for]:SHELL:(bash fish zsh elvish powershell)' \
|
||||
'--shell=[Specify shell to complete for]:SHELL:(bash elvish fish powershell zsh)' \
|
||||
'--register=[Path to write completion-registration to]:REGISTER:_files' \
|
||||
'--global[everywhere]' \
|
||||
'-h[Print help (see more with '\''--help'\'')]' \
|
||||
|
|
Loading…
Reference in a new issue