#!/bin/bash # Moves and links a file back at its initial location # It can not cross filesystems! # # Usage: mvln PATH1 PATH2 # Depends on: realpath, basename, dirname if [[ $# -ne 2 ]] then echo "Usage: mvln " exit 0 fi # Step 1: building full path out of both arguments ############################# [[ $1 =~ ^/ ]] && F1=$1 || F1=$(realpath -s $1) [[ $2 =~ ^/ ]] && F2=$2 || F2=$(realpath -s $2) # Step 2: enumerating all interesting cases #################################### # PATH1 can be: if [[ -f $F1 ]] then STATE1="0" # a regular file elif [[ -d $PWD/$F1 ]] then STATE1="1" # a directory elif [[ -e $F1 ]] then STATE1="8" # an other kind of file else STATE1="9" # a non-existent file fi # PATH2 can be: if [[ -d $F2 ]] then STATE2="0" # a directory elif [[ -d $(dirname $F2) ]] then STATE2="1" # a non-existent file in an existent directory elif [[ -e $F2 ]] then STATE2="8" # any other kind of file else STATE2="9" # a non-existent file in a non-existent directory fi # Step 3: eat this my little state automaton ################################### STATE="$STATE1$STATE2" case $STATE in [89]* ) >&2 echo "$F1 is not a proper file (or a non-existent one)" >&2 echo "Note that only regular files and directories are allowed" exit $STATE ;; *[89] ) >&2 echo "$F2 can not be created (containing directory does not exist)" >&2 echo "or exists already (refusing to overwrite)" exit $STATE ;; [01]0 ) # file or dir to an existing dir DEGUB="File/Dir to same name in existing dir" PATH1=$F1 PATH2=$F2/$(basename $F1) ;; [01]1 ) # file to new file name in an existing dir DEGUB="File/Dir to new name in existing dir" PATH1=$F1 PATH2=$F2 ;; * ) echo "Uncaught error (this is f*****g bad)" exit $STATE ;; esac #echo $DEGUB # Step 4: eventually act upon gathered knowledge ############################### mv $PATH1 $PATH2 # Works across filesystems (fast enough!) ln -s $PATH2 $PATH1 # Soft link back to old location