115 lines
2.9 KiB
Bash
Executable File
115 lines
2.9 KiB
Bash
Executable File
#!/bin/sh
|
|
|
|
_printhelp()
|
|
{
|
|
cat <<EOF
|
|
Usage: ${1##*/} [-m METHOD] [-v] FILES|FOLDERS
|
|
|
|
Create an archive in current folder from a single or multiples
|
|
files/folders. Each input entry will be at archive root (no absolute path is
|
|
used). If only one file/folder is given as input, then the archive is named
|
|
after this input. Otherwise it is named after current PWD.
|
|
|
|
-h: Display this help.
|
|
-i: The archive is created without owner/group information. (GNU tar only.)
|
|
-m: Choose compression method.
|
|
* gz: gzip (default).
|
|
* none: Simple tar archive.
|
|
* xz: LZMA.
|
|
-s: Archive each input entry an individual file.
|
|
-v: Exclude VCS data. (GNU tar only.)
|
|
EOF
|
|
}
|
|
|
|
OUTPATH="$PWD"
|
|
ARCEXT=".gz"
|
|
ARCOPT="z"
|
|
OPTIONS=""
|
|
OPT_SPLIT=false
|
|
while getopts ":him:sv" opt; do
|
|
case $opt in
|
|
h)
|
|
_printhelp "$0"
|
|
exit 1 ;;
|
|
i)
|
|
OPTIONS="$OPTIONS --owner=root --group=root --numeric-owner" ;;
|
|
m)
|
|
[ "$OPTARG" = "gz" ] && ARCEXT=".gz" && ARCOPT="z"
|
|
[ "$OPTARG" = "xz" ] && ARCEXT=".xz" && ARCOPT="J"
|
|
[ "$OPTARG" = "none" ] && ARCEXT="" && ARCOPT=""
|
|
;;
|
|
s)
|
|
OPT_SPLIT=true ;;
|
|
v)
|
|
OPTIONS="$OPTIONS --exclude-vcs" ;;
|
|
?)
|
|
_printhelp "$0"
|
|
exit 1 ;;
|
|
:)
|
|
echo "Missing argument."
|
|
_printhelp "$0"
|
|
exit 1 ;;
|
|
esac
|
|
done
|
|
|
|
|
|
shift $(($OPTIND - 1))
|
|
|
|
if [ $# -eq 0 ]; then
|
|
_printhelp "$0"
|
|
exit 1
|
|
fi
|
|
|
|
## We need 'realpath' since we need to work on the real path for the input
|
|
## files/folders and the archive location. Otherwise we could have troubles with
|
|
## circular symlinks and so on.
|
|
if ! command -v realpath >/dev/null 2>&1; then
|
|
echo >&2 "'realpath' not found in PATH. Exiting."
|
|
exit 1
|
|
fi
|
|
|
|
_archive()
|
|
{
|
|
## Only one input entry: use it as base name for the archive.
|
|
if [ $# -eq 1 ]; then
|
|
REALPATH="$(realpath "$1")"
|
|
OUTFILE="${REALPATH##*/}-$(date +%F-%H%M%S).tar${ARCEXT}"
|
|
else
|
|
OUTFILE="${PWD##*/}-$(date +%F-%H%M%S).tar${ARCEXT}"
|
|
fi
|
|
|
|
REALPWD="$(realpath "$PWD")"
|
|
for i; do
|
|
REALPATH="$(realpath "$i")"
|
|
|
|
## Check if one of the arguments is current folder. We need to make sure the
|
|
## archive is not created in an input folder, otherwise it will include
|
|
## itself.
|
|
if [ "$REALPATH" = "$REALPWD" ]; then
|
|
OUTPATH="$(realpath "$REALPWD/..")"
|
|
break
|
|
fi
|
|
done
|
|
|
|
if [ ! -w "$OUTPATH" ]; then
|
|
echo "[$OUTPATH] is not writable. Exiting."
|
|
return
|
|
fi
|
|
|
|
echo "==> [$OUTPATH/$OUTFILE]"
|
|
for i; do
|
|
REALPATH="$(realpath "$i")"
|
|
echo "${REALPATH}" >&2
|
|
echo "-C '${REALPATH%/*}'"
|
|
echo "${REALPATH##*/}"
|
|
done | tar $OPTIONS -${ARCOPT}cf "$OUTPATH/$OUTFILE" -T -
|
|
}
|
|
|
|
if $OPT_SPLIT; then
|
|
for j ; do
|
|
_archive "$j"
|
|
done
|
|
else
|
|
_archive "$@"
|
|
fi
|