# # Offer slightly friendlier error messages for certain types of errors. # function err_handle { status=$? if [[ $status -ne 2 && $status -ne 126 && $status -ne 127 ]]; then return fi # Ucky pipeline which is, amazingly enough, # the only way to get the last typed command from bash. # fc -n -l -1 doesn't always have the command yet, # !! doesn't work from inside functions # and BASH_COMMAND gets confused by functions like ls(). lastcmd=$(history | tail -1 | sed 's/^ *[0-9]* *//') # cool way to split a string into component words: read cmd args <<< "$lastcmd" # Handle possible errors involving forgetting a leading slash if the # command was okay but the error was 2, "no such file or directory". if [[ $status -eq 2 ]]; then # loop over args looking for the first one that might be missing a slash for f in $cmd "${args[@]}"; do if [[ $f = */* && ! -e $f ]]; then if [[ -e /$f ]]; then echo "" echo "$f doesn't exist, but /$f does." echo "Did you forget a leading slash?" return fi fi done return fi if [[ -e $cmd ]]; then if [[ -d $cmd ]]; then echo "Perhaps you meant: cd $cmd" elif [[ ! -x $cmd ]]; then if [[ ! -r $cmd ]]; then echo "" echo "$cmd is a file but it's not readable or executable." echo "Maybe you need to be root?" echo "You could try sudo less $cmd" echo "or sudo $(myeditor) $cmd" return 127 fi # # By now, we know it's a file and it's readable. # Figure out the file's type, and print appropriate messages: # echo "" filetype=$(file $cmd) # HTML must come before text, since file says "HTML document text" if [[ $filetype = *HTML* ]]; then echo "$cmd is an HTML file. Did you want to run: firefox $cmd" elif [[ $filetype = *text* ]]; then echo "$cmd is a text file. Did you want to run:" echo " less $cmd" echo " vim $cmd" elif [[ $filetype = *image* ]]; then echo "$cmd is an image file. Did you want to run:" echo " pho $cmd" echo " gimp $cmd" else # "file" gives terribly complex output for MS Office documents # so get the mime type to detect those: mimetype=$(xdg-mime query filetype $cmd | sed 's/;.*$//') if [[ $mimetype == application/msword ]]; then echo "$cmd is a Microsoft Word file." echo "Perhaps run: ooffice $cmd" elif [[ $mimetype =~ application/.*ms- ]]; then echo "$cmd is a file of type" echo " $mimetype (Microsoft)." echo "Perhaps try: ooffice $cmd" else # # Unknown file type -- bomb out. # echo "$cmd is a file of type $mimetype." echo "What do you want to do with it?" fi fi else echo "Hmm, $cmd exists and is executable -- not sure what went wrong" fi # else # echo "Sorry, $cmd doesn't exist" # If we want to be REALLY nice we could look for similarly named progs. # But it turns out Ubuntu's command-not-found-handle does that already. fi } # Trap errors. trap 'err_handle' ERR