DEV Community

Maksym
Maksym

Posted on • Edited on

Complete Guide: Fish Shell Adding Custom Functions

Fish in wizard hat

WARNING
Some of the commands used in this tutorial may not work on your machine, especially if you're using macOS instead of Linux. Tools like free, top, or certain awk filters behave differently across systems. If you run into issues, try using macOS alternatives.

Fish (Friendly Interactive Shell) is a modern, user-friendly command-line shell that offers powerful features like syntax highlighting, autosuggestions, and easy customization. This guide will walk you through downloading Fish and creating custom functions to enhance your command-line experience.

Getting Started with Fish

Launch Fish by typing fish in your terminal, or start a new terminal session if you've set it as your default shell.

Basic Fish Configuration

Fish stores its configuration in ~/.config/fish/. The main configuration file is config.fish.

# Create configuration directory if it doesn't exist mkdir -p ~/.config/fish # Edit main configuration file nano ~/.config/fish/config.fish 
Enter fullscreen mode Exit fullscreen mode

Understanding Fish Functions

Fish functions are similar to aliases or shell functions in other shells, but more powerful. They can:

  • Accept arguments
  • Include complex logic
  • Be saved persistently
  • Have descriptions and help text

Function Storage Locations

  • User functions: ~/.config/fish/functions/
  • System-wide functions: /usr/share/fish/functions/
  • Session functions: Defined in memory for current session only

Creating Your First Fish Function

Method 1: Interactive Function Creation

# Start Fish and use the function editor function hello echo "Hello, $argv!" end # Save the function permanently funcsave hello 
Enter fullscreen mode Exit fullscreen mode

Method 2: Creating Function Files

Create a file in ~/.config/fish/functions/ with the function name:

# Create the functions directory mkdir -p ~/.config/fish/functions # Create a function file nano ~/.config/fish/functions/hello.fish 
Enter fullscreen mode Exit fullscreen mode

Add the function content:

function hello --description "Say hello to someone" if test (count $argv) -eq 0 echo "Hello, World!" else echo "Hello, $argv!" end end 
Enter fullscreen mode Exit fullscreen mode

Practical Fish Function Examples

1. Enhanced Directory Navigation

# ~/.config/fish/functions/mkcd.fish function mkcd --description "Create directory and cd into it" mkdir -p $argv[1] && cd $argv[1] end 
Enter fullscreen mode Exit fullscreen mode

2. Git Shortcuts

# ~/.config/fish/functions/gst.fish function gst --description "Git status with short format" git status --short --branch end # ~/.config/fish/functions/glog.fish function glog --description "Pretty git log" git log --oneline --decorate --graph --all end # ~/.config/fish/functions/gcm.fish function gcm --description "Git commit with message" if test (count $argv) -eq 0 echo "Usage: gcm 'commit message'" return 1 end git commit -m "$argv" end 
Enter fullscreen mode Exit fullscreen mode

3. System Information Functions

# ~/.config/fish/functions/sysinfo.fish function sysinfo --description "Display system information" echo "System Information:" echo "==================" echo "Hostname: "(hostname) echo "User: "$USER echo "OS: "(uname -s) echo "Kernel: "(uname -r) echo "Uptime: "(uptime | cut -d',' -f1 | cut -d' ' -f4-) echo "Memory: "(free -h | grep '^Mem:' | awk '{print $3"/"$2}') echo "Disk Usage: "(df -h / | tail -1 | awk '{print $5" used"}') end 
Enter fullscreen mode Exit fullscreen mode

4. Development Environment Functions

# ~/.config/fish/functions/serve.fish function serve --description "Start a simple HTTP server" set port 8000 if test (count $argv) -gt 0 set port $argv[1] end if command -v python3 >/dev/null python3 -m http.server $port else if command -v python >/dev/null python -m SimpleHTTPServer $port else echo "Python not found" return 1 end end # ~/.config/fish/functions/venv.fish function venv --description "Python virtual environment helper" switch $argv[1] case create python3 -m venv $argv[2] case activate source $argv[2]/bin/activate.fish case deactivate deactivate case '*' echo "Usage: venv [create|activate|deactivate] [name]" end end 
Enter fullscreen mode Exit fullscreen mode

5. File and Text Manipulation

# ~/.config/fish/functions/extract.fish function extract --description "Extract various archive formats" if test (count $argv) -eq 0 echo "Usage: extract <archive_file>" return 1 end switch $argv[1] case '*.tar.bz2' tar xjf $argv[1] case '*.tar.gz' tar xzf $argv[1] case '*.bz2' bunzip2 $argv[1] case '*.rar' unrar x $argv[1] case '*.gz' gunzip $argv[1] case '*.tar' tar xf $argv[1] case '*.tbz2' tar xjf $argv[1] case '*.tgz' tar xzf $argv[1] case '*.zip' unzip $argv[1] case '*.Z' uncompress $argv[1] case '*.7z' 7z x $argv[1] case '*' echo "Don't know how to extract '$argv[1]'" return 1 end end 
Enter fullscreen mode Exit fullscreen mode

Advanced Function Features

Function Arguments and Options

function myfunction --description "Example function with options" argparse 'h/help' 'v/verbose' 'o/output=' -- $argv or return if set -q _flag_help echo "Usage: myfunction [options] <input>" echo "Options:" echo " -h, --help Show this help" echo " -v, --verbose Verbose output" echo " -o, --output Specify output file" return end if set -q _flag_verbose echo "Verbose mode enabled" end if set -q _flag_output echo "Output file: $_flag_output" end echo "Processing: $argv" end 
Enter fullscreen mode Exit fullscreen mode

Using Variables and Conditionals

function backup --description "Backup files with timestamp" set timestamp (date +%Y%m%d_%H%M%S) if test (count $argv) -eq 0 echo "Usage: backup <file1> [file2] ..." return 1 end for file in $argv if test -f $file cp $file "$file.backup_$timestamp" echo "Backed up: $file -> $file.backup_$timestamp" else echo "File not found: $file" end end end 
Enter fullscreen mode Exit fullscreen mode

Managing Fish Functions

Listing Functions

# List all functions functions # List functions matching a pattern functions | grep git # Show function definition functions functionname 
Enter fullscreen mode Exit fullscreen mode

Editing Functions

# Edit a function interactively funced functionname # Save changes permanently funcsave functionname 
Enter fullscreen mode Exit fullscreen mode

Removing Functions

# Remove from current session functions -e functionname # Remove permanently rm ~/.config/fish/functions/functionname.fish 
Enter fullscreen mode Exit fullscreen mode

Fish Configuration Tips

Setting Environment Variables

# In ~/.config/fish/config.fish set -gx EDITOR vim set -gx PATH $HOME/bin $PATH set -gx GOPATH $HOME/go 
Enter fullscreen mode Exit fullscreen mode

Creating Aliases

# In ~/.config/fish/config.fish alias python 'python3' alias l 'ls -a' alias ll 'ls -la' alias grep 'grep --color=auto' alias .. 'cd ..' alias ... 'cd ../..' alisa c 'clear' 
Enter fullscreen mode Exit fullscreen mode

Custom Prompt

# ~/.config/fish/functions/fish_prompt.fish function fish_prompt set_color $fish_color_cwd echo -n (basename (prompt_pwd)) set_color normal echo -n ' $ ' end 
Enter fullscreen mode Exit fullscreen mode

Troubleshooting Common Issues

Function Not Loading

  1. Check function file location
  2. Verify syntax with fish -n ~/.config/fish/functions/functionname.fish
  3. Reload Fish configuration: source ~/.config/fish/config.fish

Best Practices

  1. Use descriptive function names - Make them easy to remember
  2. Add descriptions - Use the --description flag
  3. Handle arguments properly - Check for required arguments
  4. Provide help information - Include usage examples
  5. Test functions thoroughly - Especially error conditions
  6. Keep functions focused - One function, one purpose
  7. Use meaningful variable names - Improve readability
  8. Comment complex logic - Help future you understand the code

Conclusion

Fish shell offers a powerful and user-friendly environment for command-line work. With custom functions, you can automate repetitive tasks, create shortcuts for complex commands, and build a personalized toolkit that matches your workflow.

Start with simple functions and gradually build more complex ones as you become comfortable with Fish's syntax and capabilities. The investment in learning Fish and creating custom functions will pay dividends in improved productivity and a more enjoyable command-line experience.

Remember to back up your Fish configuration regularly, and consider using version control to track changes to your functions and configuration files.

Top comments (0)