agetar/agetar

99 lines
3.0 KiB
Plaintext
Raw Normal View History

2023-05-03 17:33:45 -05:00
#!/bin/sh
2023-05-04 18:45:28 -05:00
RED="$(printf '\033[38;5;9m')"
RESET="$(printf '\033[m')"
2023-05-03 17:33:45 -05:00
set -euf
BN="${0##*/}"
export POSIXLY_CORRECT=1
2023-06-21 17:17:50 -05:00
if [ -n "${NO_COLOR:-}" ]; then
2023-05-04 18:45:28 -05:00
RED="" RESET=""
2023-05-03 17:33:45 -05:00
fi
errecho() {
>&2 echo "$*$RESET"
}
fail() {
errecho "${RED}error: $BN: $RESET$*"
exit 1
}
2023-05-09 23:48:53 -05:00
_type() { type "$@" >/dev/null 2>&1 ; }
2023-05-03 17:33:45 -05:00
usage() {
cat >&2 <<-EOF
usage:
2023-05-04 18:45:28 -05:00
$BN -e (-r RECIPIENT | -R PATH)... [-a] [-o OUTPUT] [--] FILES...
$BN -e -p [-a] [-o OUTPUT] [--] FILES...
$BN -d [-i PATH]... [-o OUTPUT] [--] FILES...
options:
-e encrypt the input files to an output tar
-d decrypt the input tar to output files
-o OUTPUT encrypting: write output tar to OUTPUT. stdout if omitted
decrypting: directory to extract to. PWD if omitted
-a encrypt to a PEM encoded format
-p encrypt with a passphrase
-r RECIPIENT encrypt to the specified RECIPIENT. can be repeated
-R PATH encrypt to the recipients listed at PATH. can be repeated
-i PATH decrypt using the identity file at PATH. can be repeated
at least one FILE is required for both encrypting and decrypting
if multiple are present, each will be processed with the same identities
you probably want an OUTPUT when encrypting, even if it's not required
(age will yet at you for that anyway unless you also use -a)
most of these options are passed directly to age(1). see its man page for
more details.
2023-05-03 17:33:45 -05:00
EOF
}
AGEOPTS=
RECIPIENTS=
RECIPIENTS_FILES=
IDENTITIES=
while getopts :hedo:apr:R:i: OPT; do
case $OPT in
h) usage && exit 0 ;;
e) TYPE=e; AGEOPTS="$AGEOPTS -e" ;;
d) TYPE=d; AGEOPTS="$AGEOPTS -d" ;;
2023-06-21 17:17:50 -05:00
o) [ -z "${OUTPUT:-}" ] && OUTPUT="$OPTARG" || fail "don't specify output twice D:" ;;
2023-05-03 17:33:45 -05:00
a) AGEOPTS="$AGEOPTS -a" ;;
p) AGEOPTS="$AGEOPTS -p" ;;
r) RECIPIENTS="$RECIPIENTS -r '$(printf '%s' "$OPTARG" | sed -e "s/'/'\\\\''/g")'" ;;
R) RECIPIENTS_FILES="$RECIPIENTS_FILES -R '$(printf '%s' "$OPTARG" | sed -e "s/'/'\\\\''/g")'" ;;
i) IDENTITIES="$IDENTITIES -i '$(printf '%s' "$OPTARG" | sed -e "s/'/'\\\\''/g")'" ;;
*) ;;
esac
done
shift $((OPTIND - 1))
[ "$#" -lt 1 ] && usage && exit 1
2023-06-21 17:17:50 -05:00
[ -z "${TYPE:-}" ] && fail 'specify one of -e or -d'
2023-05-03 17:33:45 -05:00
TAR="$(mktemp)"
trap 'rm "$TAR"' INT HUP QUIT EXIT
if [ "$TYPE" = "e" ]; then
2023-05-04 18:45:28 -05:00
{ _type bsdtar && CMD="bsdtar -rL -f"; } || \
{ _type tar && CMD="tar -rh -f"; } || \
2023-05-03 17:33:45 -05:00
fail "can't find tar command!"
for f; do
if [ -f "$f" ] || [ -d "$f" ]; then
$CMD "$TAR" "$f" >/dev/null 2>&1
else
errecho "$f is not a regular file or directory! skipping..."
fi
done
eval 'age $AGEOPTS ${OUTPUT:+-o "$OUTPUT"} '"$RECIPIENTS $RECIPIENTS_FILES $IDENTITIES"' "$TAR"'
else
2023-05-04 18:45:28 -05:00
{ _type bsdtar && CMD="bsdtar -x -f"; } || \
{ _type tar && CMD="tar -x -f"; } || \
2023-05-03 17:33:45 -05:00
fail "can't find tar command!"
for f; do
eval 'age $AGEOPTS -o "$TAR" '"$RECIPIENTS $RECIPIENTS_FILES $IDENTITIES"' "$f"'
2023-05-04 18:45:28 -05:00
[ ! -d "${OUTPUT:="$PWD"}" ] && mkdir -p "$OUTPUT"
2023-05-03 17:33:45 -05:00
$CMD "$TAR" -C "$OUTPUT"
done
fi