diff --git a/pros/cli/misc_commands.py b/pros/cli/misc_commands.py index fc3d7c6a..80dd3cc3 100644 --- a/pros/cli/misc_commands.py +++ b/pros/cli/misc_commands.py @@ -58,7 +58,7 @@ def upgrade(force_check, no_install): def _get_shell_script(shell: str) -> str: - script_file = Path(__file__).parent / '..' / 'autocomplete' / _SCRIPT_FILES[shell] + script_file = Path(__file__).parent.parent / 'autocomplete' / _SCRIPT_FILES[shell] with script_file.open('r') as f: return f.read() @@ -76,22 +76,24 @@ def format_completion(self, item: CompletionItem) -> str: @misc_commands_cli.command() @click.argument('shell', type=click.Choice(['bash', 'zsh', 'fish', 'pwsh', 'powershell']), required=True) -@click.argument('config_file', type=click.Path(file_okay=True, dir_okay=True), default=None, required=False) +@click.argument('config_path', type=click.Path(resolve_path=True), default=None, required=False) @click.option('--force', '-f', is_flag=True, default=False, help='Skip confirmation prompts') @default_options -def setup_autocomplete(shell, config_file, force): +def setup_autocomplete(shell, config_path, force): """ Set up autocomplete for PROS CLI in the specified shell SHELL: The shell to set up autocomplete for - CONFIG_FILE: The configuration file to add the autocomplete script to. If not specified, the default configuration + CONFIG_PATH: The configuration path to add the autocomplete script to. If not specified, the default configuration file for the shell will be used. + + Example: pros setup-autocomplete bash ~/.bashrc """ # https://click.palletsprojects.com/en/8.1.x/shell-completion/ - default_config_files = { + default_config_paths = { 'bash': '~/.bashrc', 'zsh': '~/.zshrc', 'fish': '~/.config/fish/completions/', @@ -99,57 +101,58 @@ def setup_autocomplete(shell, config_file, force): 'powershell': None, } - if shell in ('pwsh', 'powershell') and config_file is None: + if shell in ('pwsh', 'powershell') and config_path is None: try: profile_command = f'{shell} -NoLogo -NoProfile -Command "Write-Output $PROFILE"' if os.name == 'nt' else f"{shell} -NoLogo -NoProfile -Command 'Write-Output $PROFILE'" - default_config_files[shell] = subprocess.run(profile_command, shell=True, capture_output=True, check=True).stdout.decode().strip() + default_config_paths[shell] = subprocess.run(profile_command, shell=True, capture_output=True, check=True).stdout.decode().strip() except subprocess.CalledProcessError as exc: raise click.UsageError("Failed to determine the PowerShell profile path. Please specify a valid config file.") from exc - if config_file is None: - config_file = default_config_files[shell] - ui.echo(f"Using default config file {config_file}. To specify a different config file, run 'pros setup-autocomplete {shell} CONFIG_FILE'.\n") - config_file = Path(config_file).expanduser().resolve() + if config_path is None: + config_path = default_config_paths[shell] + ui.echo(f"Using default config path {config_path}. To specify a different config path, run 'pros setup-autocomplete {shell} [CONFIG_PATH]'.\n") + config_path = Path(config_path).expanduser().resolve() if shell in ('bash', 'zsh', 'pwsh', 'powershell'): - if config_file.is_dir(): - raise click.UsageError(f"Config file {config_file} is a directory. Please specify a valid config file.") - if not config_file.exists(): - raise click.UsageError(f"Config file {config_file} does not exist. Please specify a valid config file.") + if config_path.is_dir(): + raise click.UsageError(f"Config file {config_path} is a directory. Please specify a valid config file.") + if not config_path.exists(): + raise click.UsageError(f"Config file {config_path} does not exist. Please specify a valid config file.") # Write the autocomplete script to a shell script file - script_file = config_file.parent / _SCRIPT_FILES[shell] - with open(script_file, 'w') as f: + script_file = config_path.parent / _SCRIPT_FILES[shell] + with script_file.open('w') as f: f.write(_get_shell_script(shell)) if shell in ('bash', 'zsh'): source_autocomplete = f". {script_file.as_posix()}\n" elif shell in ('pwsh', 'powershell'): source_autocomplete = f"{script_file} | Invoke-Expression\n" - if force or ui.confirm(f"Add the autocomplete script to {config_file}?", default=True): + if force or ui.confirm(f"Add the autocomplete script to {config_path}?", default=True): # Source the autocomplete script in the config file - with open(config_file, 'r+') as f: + with config_path.open('r+') as f: # Only append if the source command is not already in the file if source_autocomplete not in f.readlines(): f.write("\n# PROS CLI autocomplete\n") f.write(source_autocomplete) else: - ui.echo(f"Autocomplete script written to {script_file}. Add the following line to {config_file} then restart your shell to enable autocomplete:\n") + ui.echo(f"Autocomplete script written to {script_file}.") + ui.echo(f"Add the following line to {config_path} then restart your shell to enable autocomplete:\n") ui.echo(source_autocomplete) return elif shell == 'fish': - if config_file.is_file(): - script_dir = config_file.parent - script_file = config_file + if config_path.is_file(): + script_dir = config_path.parent + script_file = config_path else: - script_dir = config_file - script_file = config_file / _SCRIPT_FILES[shell] + script_dir = config_path + script_file = config_path / _SCRIPT_FILES[shell] if not script_dir.exists(): raise click.UsageError(f"Completions directory {script_dir} does not exist. Please specify a valid completions file or directory.") # Write the autocomplete script to a shell script file - with open(script_file, 'w') as f: + with script_file.open('w') as f: f.write(_get_shell_script(shell)) - ui.echo(f"Succesfully set up autocomplete for {shell} in {config_file}. Restart your shell to apply changes.") + ui.echo(f"Succesfully set up autocomplete for {shell} in {config_path}. Restart your shell to apply changes.")