#!/bin/sh set -eu usage() { cat <<-'EOF' Usage: grun [-r RECIPIENT] FILENAME -- COMMAND... grun -h EOF } help() { cat <<-'EOF' Options: -r RECIPIENT the recipient to encrypt to. Can be given multiple for multiple recipients. -h, --help show this message COMMAND A command to be executed, that accepts input in STDIN and emits result in STDOUT, and emits errors as non-zero return codes. FILENAME The GPG-encrypted file to be processed. If it doesn't exist yet, it will be created. Examples: Edit "secrets.txt.gpg" using `vipe` and the default recipient: $ grun secrets.txt.gpg -- vipe Delete lines containing "FIXME" in todos.gpg: $ grun -r ABC123DEF321 todos.gpg -- sed '/FIXME/d' If COMMAND emits a non-zero return code, the file is left unmodified. EOF } for flag in "$@"; do case "$flag" in --) break ;; --help) usage help exit ;; *) ;; esac done while getopts 'rh' flag; do case "$flag" in r) RECIPIENTS_FLAG="${RECIPIENTS_FLAG:-} -r $OPTARG" ;; h) usage help exit ;; *) usage >&2 exit 2 ;; esac done shift $((OPTIND - 1)) assert_arg() { if [ -z "$1" ]; then printf 'Missing %s\n\n' "$2" >&2 usage >&2 exit 2 fi } FILENAME="${1:-}" assert_arg "$FILENAME" 'FILENAME' shift if [ "${1:-}" != '--' ]; then printf 'Missing "--" separator\n\n' >&2 usage >&2 exit 2 fi shift assert_arg "${1:-}" 'COMMAND' if [ ! -e "$FILENAME" ]; then OUT="$(printf '' | "$@")" else OUT="$(gpg -dq "$FILENAME" | "$@")" fi echo "$OUT" | gpg -e ${RECIPIENTS_FLAG:--r eu@euandre.org} | sponge "$FILENAME"