#!/bin/bash #Sam Noble/Judicial Information Division 2019 snoble@nmcourts.gov #requires oauthtool,mysql-client and qrencode. ##You can edit these here, but if you create ~/.my.cnf containing: # [client] #user=username #password=password ## the script will be quieter and more secure. DBHOST=localhost DBUSER=guacamole_user DBPASS=secretmariadbpassword DBNAME=guacamole_db ##Path to depended binaries OATHTOOLBIN=$(which oathtool) QRENCODEBIN=$(which qrencode) USAGE() { echo "program to query the Guacamole database and perform TOTP operations Usage: $(basename "$0") [-dhsecrH] user where: Default action is to print user's One Time Password -h show this Help text -s display user's Secret key -e generate Enrollment quick response code -c Check user's enrollment status -r Reset user's enrollment to present QRcode on login. -H Hostname of the database server and user is a guacamole login" 1>&2; exit 1; } ##No further user editable options below if [ -z "$1" ]; then USAGE; exit 1; else TOTP_UTIL_ACTION=GEN_OTP #Parse the -options while getopts ':H:u:crdhse' OPT; do case "$OPT" in h) USAGE ;; s) TOTP_UTIL_ACTION=GET_USER_SECRET ;; e) TOTP_UTIL_ACTION=GEN_ENROLLMENT ;; c) TOTP_UTIL_ACTION=CHECK_ENROLLMENT ;; r) TOTP_UTIL_ACTION=RESET_ENROLLMENT ;; d) DEBUG=True ;; H) DBHOST="$OPTARG" ;; u) USERID="$OPTARG" ;; ## -u for compatibility with older version :) printf "missing argument for %USERID\n" "$OPTARG" >&2 exit 1 ;; \?) printf "illegal option: -%s\n" "$OPTARG" >&2 #USAGE >&2 USAGE exit 1 ;; esac done fi #Set USERID if it's not already set with -u if [ -z "$USERID" ]; then shift $(($OPTIND - 1)) export USERID=$1 fi #some input sanitizing, that doesn't work in dash. USERID=${USERID//[^a-zA-Z0-9_]/} MAIN () { if [ -n "$DEBUG" ]; then #echo "DEBUG is: $DEBUG" echo "USERID is: $USERID" echo "MODE is: $TOTP_UTIL_ACTION" echo "DBHOST is: $DBHOST" fi if [ -z "$USERID" ]; then echo "$USAGE" >&2 exit 1 fi GET_USER_SECRET if [ -z "$USER_SECRET" ]; then echo "username "$USERID" not found" >&2 exit 2 fi if [ "$TOTP_UTIL_ACTION" = GET_USER_SECRET ]; then echo $USERID"'s secret key is:" echo $USER_SECRET exit elif [ "$TOTP_UTIL_ACTION" = GEN_ENROLLMENT ]; then $QRENCODEBIN --type=ANSIUTF8 "otpauth://totp/remotedesktop?secret=$USER_SECRET&issuer=NMCOURTS&algorithm=SHA1&digits=6&period=30" exit elif [ "$TOTP_UTIL_ACTION" = RESET_ENROLLMENT ]; then RESET_ENROLLMENT exit elif [ "$TOTP_UTIL_ACTION" = CHECK_ENROLLMENT ]; then CONFIRMATION_TEST exit else GET_TOTP exit fi } FAKE_GET_USER_SECRET() { #GET_USER_SECRET() { #let's not bang up mysql during testing export USER_SECRET=IZAUWRKLIVMTENBVIZAUWRKLIVMQU=== #echo $USER_SECRET } GET_USER_SECRET() { #REAL_GET_USER_SECRET() { SQLQUERY="select entity_id from guacamole_entity where name = '$USERID' limit 1 into @userid; select attribute_value from guacamole_user_attribute where attribute_name = 'guac-totp-key-secret' and user_id = @userid;" #"Checking homedir for .my.cnf MariaDB configuration file" if [ -f ~/.my.cnf ]; then export USER_SECRET=$(mysql -h $DBHOST -D $DBNAME -B -N -e "$SQLQUERY") else echo "No ~/.my.cnf file found, create one or edit DBUSER:DBPASS directly in $0" export USER_SECRET=$(mysql -u $DBUSER -h $DBHOST -p$DBPASS -D $DBNAME -B -N -e "$SQLQUERY") fi } RESET_ENROLLMENT() { SQLUPDATE="select entity_id from guacamole_entity where name = '$USERID' limit 1 into @userid; update guacamole_user_attribute set attribute_value = "false" where attribute_name = 'guac-totp-key-confirmed' and user_id = @userid;" if [ -f ~/.my.cnf ]; then mysql -h $DBHOST -D $DBNAME -B -N -e "$SQLUPDATE" else echo "No ~/.my.cnf file found, create one or edit DBUSER:DBPASS directly in $0" mysql -u $DBUSER -h $DBHOST -p$DBPASS -D $DBNAME -B -N -e "$SQLUPDATE" fi CONFIRMATION_TEST } CONFIRMATION_TEST() { CHECK_SQLQUERY="select entity_id from guacamole_entity where name = '$USERID' limit 1 into @userid; select attribute_value from guacamole_user_attribute where attribute_name = 'guac-totp-key-confirmed' and user_id = @userid;" if [ -f ~/.my.cnf ]; then export CONFIRMATION_STATUS=$(mysql -h $DBHOST -D $DBNAME -B -N -e "$CHECK_SQLQUERY") else echo "No ~/.my.cnf file found, create one or edit DBUSER:DBPASS directly in $0" export CONFIRMATON_STATUS=$(mysql -u $DBUSER -h $DBHOST -p$DBPASS -D $DBNAME -B -N -e "$CHECK_SQLQUERY") fi if [ -n "$DEBUG" ]; then echo "CONFIRMATION_STATUS is: $CONFIRMATION_STATUS" fi if [ $CONFIRMATION_STATUS = "true" ]; then echo $USERID has previously enrolled and will not see a QRCODE on login. exit 0 else echo $USERID is not yet enrolled and will be presented a QRCODE on next login. exit 1 fi } GET_TOTP() { $OATHTOOLBIN -b --totp=sha1 $USER_SECRET } MAIN