#!/usr/bin/env bash

. lib.bash || exit

usage() {
	echo "Usage: $progname [-i <path>] <host...>"
	echo
	echo_opt "-i <path>" "OpenSSH public key to upload"
}

ids=()

while getopts ':i:' OPT; do
	case $OPT in
	i) ids+=("$OPTARG");;
	*) lib:die_getopts;;
	esac
done; shift $((OPTIND-1))

hosts=("$@")

if (( ! ${#hosts[@]} )); then
	die "hostname not provided"
fi

if (( ! ${#ids[@]} )); then
	ids=(~/.ssh/id_rsa.pub)
fi

for file in "${ids[@]}"; do
	if [[ ! -s $file ]]; then
		err "$file: does not exist"
		continue
	fi
	if [[ $file != *.pub ]]; then
		err "$file: not a public key file"
		continue
	fi
	while read -r algo _; do
		if [[ $algo != @(ssh-rsa|ssh-ed25519) ]]; then
			err "$file: \"$algo\" keys are not supported by RouterOS"
			continue
		fi
	done < "$file"
done

(( !errors )) || exit

for host in "${hosts[@]}"; do
	if [[ $host == \[*:*\] ]]; then
		scphost="$host"
		host="${host#'['}"
		host="${host%']'}"
	elif [[ $host == *:*:*:* ]]; then
		scphost="[$host]"
	elif [[ $host == *[:/]* ]]; then
		die "invalid hostname '$host'"
	else
		scphost="$host"
	fi

	# Establish mux socket (new OpenSSH's scp no longer does so)
	ssh "$host" :

	ltmpfile=$(mktemp /tmp/key_XXXXXXXXXX)
	for file in "${ids[@]}"; do
		vmsg "Uploading $file to $host"
		rtmpfile="tmp_$(uuidgen).pub"
		key=$(< "$file")
		key=${key//'('}
		key=${key//')'}
		printf '%s\n' "$key" > "$ltmpfile"
		scp "$ltmpfile" "$scphost:$rtmpfile" || exit
		# Wait for the file to show up (not always instant; silly RouterOS SSH)
		sleep 0.5
		waited=0
		until ssh "$host" "/file print detail where name=\"$rtmpfile\"" \
		      | grep -qs "$rtmpfile"; do
			sleep 0.5
			echo -n "."
			(( ++waited ))
		done
		if (( waited )); then
			echo ""
		fi
		ssh "$host" "/user ssh-keys import public-key-file=\"$rtmpfile\""
		ssh "$host" "/file remove [find name=\"$rtmpfile\"]"
	done
	rm -f "$ltmpfile"

	ssh "$host" "/user ssh-keys print"
done

(( !errors )) || exit
