myvesta/bin/v-change-wordpress-admin-passwords

128 lines
4.8 KiB
Bash

#!/bin/bash
# info: interactively delete or change WordPress admin passwords for a given domain
# options: DOMAIN
#
# d → delete user (with content reassignment)
# c → change password (random 10-char alnum)
# s → skip
# x → exit
#----------------------------------------------------------#
# Variable & Function #
#----------------------------------------------------------#
[ "$(whoami)" != "root" ] && { echo "You must be root to run this command."; exit 1; }
source /etc/profile
DOMAIN="$1"
[ -z "$DOMAIN" ] && { echo "Usage: v-change-wp-admins-pass DOMAIN"; exit 1; }
USER="$(/usr/local/vesta/bin/v-search-domain-owner "$DOMAIN")"
[ -z "$USER" ] && { echo "Domain $DOMAIN does not exist."; exit 1; }
WP_PATH="/home/$USER/web/$DOMAIN/public_html"
[ ! -f "$WP_PATH/wp-config.php" ] && { echo "WordPress is not installed on this domain."; exit 1; }
# WP-CLI wrapper
WP_RUN=(/usr/local/vesta/bin/v-run-wp-cli $DOMAIN --skip-plugins --skip-themes)
# random 10-char password
gen_pass() { tr -dc 'A-Za-z0-9' </dev/urandom | head -c 10; }
#----------------------------------------------------------#
# Action #
#----------------------------------------------------------#
cd "$WP_PATH" || exit 1
echo
echo "WordPress administrators for $DOMAIN:"
echo "-------------------------------------"
ADMIN_LIST_CSV=$("${WP_RUN[@]}" user list --role=administrator \
--fields=ID,user_login,user_email \
--format=csv 2>/dev/null | tail -n +2)
[ -z "$ADMIN_LIST_CSV" ] && { echo "No administrator accounts found."; exit 0; }
printf "%-6s %-20s %s\n" "ID" "Username" "Email"
echo "$ADMIN_LIST_CSV" | while IFS=',' read -r PID PLOGIN PEMAIL; do
printf "%-6s %-20s %s\n" "$PID" "$PLOGIN" "$PEMAIL"
done
echo
echo "For each admin choose: (d) delete, (c) change password, (s) skip, (x) exit."
# interactive loop
while IFS=',' read -r ID LOGIN EMAIL; do
[ -n "$EMAIL" ] && TARGET="$LOGIN <$EMAIL>" || TARGET="$LOGIN"
while true; do
echo "-------------------------------------"
read -r -p "Action for \"$TARGET\" [d/c/s/x]? " ACT < /dev/tty
case "$ACT" in
[Dd]* )
read -r -p "Really DELETE \"$TARGET\" ? ('y' or ENTER for yes / 'n' for no) " CONF < /dev/tty
if [[ ! "$CONF" =~ ^[Nn]$ ]]; then
# build an array of OTHER admin usernames
mapfile -t OTHER_USERS < <(echo "$ADMIN_LIST_CSV" | awk -F',' -v cur="$ID" '$1!=cur {print $2}')
if [ "${#OTHER_USERS[@]}" -eq 0 ]; then
echo "Cannot delete the only administrator account."
break
fi
DEFAULT_USER="${OTHER_USERS[0]}"
echo "Available admin usernames for reassignment: ${OTHER_USERS[*]}"
while true; do
read -r -p "Reassign content to which username? [default $DEFAULT_USER] " REASSIGN < /dev/tty
REASSIGN=${REASSIGN:-$DEFAULT_USER}
if printf '%s\n' "${OTHER_USERS[@]}" | grep -qx "$REASSIGN"; then
break
else
echo "Invalid username. Please choose one of: ${OTHER_USERS[*]}"
fi
done
# delete by username, reassign by username
"${WP_RUN[@]}" user delete "$LOGIN" --reassign="$REASSIGN" --yes >/dev/null 2>&1
echo "$TARGET deleted (content reassigned to $REASSIGN)."
else
echo "Deletion cancelled."
fi
break
;;
[Cc]* )
NEW_PASS=$(gen_pass)
if "${WP_RUN[@]}" user update "$LOGIN" --user_pass="$NEW_PASS" --quiet; then
echo "Password for $TARGET changed to: $NEW_PASS"
else
echo "Failed to change password for $TARGET."
fi
break
;;
[Ss]* )
echo "Skipping $TARGET."
break
;;
[Xx]* )
echo "Exiting."
exit 0
;;
* ) echo "Please answer d, c, s, or x." ;;
esac
done
done <<< "$ADMIN_LIST_CSV"
#----------------------------------------------------------#
# flush cache and refresh all security salts #
#----------------------------------------------------------#
echo "-------------------------------------"
echo
echo "Flushing cache and refreshing salts..."
"${WP_RUN[@]}" cache flush
"${WP_RUN[@]}" config shuffle-salts WP_CACHE_KEY_SALT --force
"${WP_RUN[@]}" config shuffle-salts
echo "Cache flushed and salts refreshed."
echo
echo "Done."
exit 0