133 lines
4.8 KiB
Bash
Executable File
133 lines
4.8 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
|
|
function error_handler() {
|
|
echo >&2 "Exited with BAD EXIT CODE '${2}' in ${0} script at line: ${1}."
|
|
exit "$2"
|
|
}
|
|
trap 'error_handler ${LINENO} $?' ERR
|
|
set -o errtrace -o errexit -o nounset -o pipefail
|
|
|
|
# you can get a list of users from the keycloak realm file like:
|
|
# grep '"email" :' keycloak/realm_exports/spiffworkflow-realm.json | awk -F : '{print $2}' | sed -E 's/ "//g' | sed -E 's/",//g' > s
|
|
|
|
# we keep some of these in keycloak/test_user_lists
|
|
# spiffworkflow-realm.json is a mashup of the status and sartography user lists.
|
|
user_file_with_one_email_per_line="${1:-}"
|
|
|
|
keycloak_realm="${2:-spiffworkflow}"
|
|
if [[ -z "${1:-}" ]]; then
|
|
echo >&2 "usage: $(basename "$0") [user_file_with_one_email_per_line]"
|
|
exit 1
|
|
fi
|
|
|
|
if [[ -z "${KEYCLOAK_BASE_URL:-}" ]]; then
|
|
KEYCLOAK_BASE_URL=http://localhost:7002
|
|
fi
|
|
if [[ -z "${ADMIN_USERNAME:-}" ]]; then
|
|
ADMIN_USERNAME="admin"
|
|
fi
|
|
if [[ -z "${ADMIN_PASSWORD:-}" ]]; then
|
|
ADMIN_PASSWORD="admin"
|
|
fi
|
|
|
|
REALM_NAME="$keycloak_realm"
|
|
SECURE=false
|
|
|
|
KEYCLOAK_URL=$KEYCLOAK_BASE_URL/realms/$REALM_NAME/protocol/openid-connect/token
|
|
|
|
if [[ $SECURE = 'y' ]]; then
|
|
INSECURE=
|
|
else
|
|
INSECURE=--insecure
|
|
fi
|
|
|
|
# https://www.appsdeveloperblog.com/keycloak-rest-api-create-a-new-user/
|
|
result=$(
|
|
curl --fail -s -X POST "$KEYCLOAK_URL" "$INSECURE" \
|
|
--header 'Content-Type: application/x-www-form-urlencoded' \
|
|
--data-urlencode "username=${ADMIN_USERNAME}" \
|
|
--data-urlencode "password=${ADMIN_PASSWORD}" \
|
|
--data-urlencode 'grant_type=password' \
|
|
--data-urlencode 'client_id=admin-cli'
|
|
)
|
|
backend_token=$(jq -r '.access_token' <<<"$result")
|
|
|
|
function add_user() {
|
|
local user_email=$1
|
|
local username=$2
|
|
local pass=$3
|
|
local user_attribute_one=$4
|
|
|
|
local credentials='{"type":"password","value":"'"${pass}"'","temporary":false}'
|
|
|
|
local data='{"email":"'"${user_email}"'", "enabled":"true", "username":"'"${username}"'", "credentials":['"${credentials}"']'
|
|
if [[ -n "$user_attribute_one" ]]; then
|
|
data=''${data}', "attributes": {"'${custom_attribute_one}'": [ "'$user_attribute_one'" ]}'
|
|
fi
|
|
data="${data}}"
|
|
|
|
local http_code
|
|
http_code=$(curl --silent -o /dev/null -w '%{http_code}' --location --request POST "${KEYCLOAK_BASE_URL}/admin/realms/${keycloak_realm}/users" \
|
|
-H 'Content-Type: application/json' \
|
|
-H "Authorization: Bearer $backend_token" \
|
|
--data-raw "$data")
|
|
echo "$http_code"
|
|
}
|
|
|
|
first_line_processed="false"
|
|
custom_attribute_one=''
|
|
|
|
while read -r input_line; do
|
|
if ! grep -qE '^#' <<<"$input_line"; then
|
|
if [[ "$first_line_processed" == "false" ]]; then
|
|
email_header=$(awk -F ',' '{print $1}' <<<"$input_line")
|
|
pass_header=$(awk -F ',' '{print $2}' <<<"$input_line")
|
|
if [[ "$email_header" != "email" ]]; then
|
|
echo >&2 "ERROR: the first column in the first row must be email."
|
|
exit 1
|
|
fi
|
|
if [[ "$pass_header" != "pass" ]]; then
|
|
echo >&2 "ERROR: the first column in the first row must be pass."
|
|
exit 1
|
|
fi
|
|
custom_attribute_one=$(awk -F ',' '{print $3}' <<<"$input_line")
|
|
first_line_processed="true"
|
|
elif [[ -n "$input_line" ]]; then
|
|
echo "Importing: $input_line"
|
|
user_email=$(awk -F ',' '{print $1}' <<<"$input_line")
|
|
username=$(awk -F '@' '{print $1}' <<<"$user_email")
|
|
|
|
if [[ "$username" == "$ADMIN_USERNAME" || "$user_email" == "$ADMIN_USERNAME" ]]; then
|
|
echo >&2 "ERROR: The user used as the admin user matches a user in the current import list. This should not happen. Comment out that user from the list or use a different admin user: ${ADMIN_USERNAME}"
|
|
exit 1
|
|
fi
|
|
|
|
password=$(awk -F ',' '{print $2}' <<<"$input_line")
|
|
echo "Password: $password"
|
|
user_attribute_one=$(awk -F ',' '{print $3}' <<<"$input_line")
|
|
http_code=$(add_user "$user_email" "$username" "$password" "$user_attribute_one")
|
|
|
|
if [[ "$http_code" == "409" ]]; then
|
|
user_info=$(curl --fail --silent --location --request GET "${KEYCLOAK_BASE_URL}/admin/realms/${keycloak_realm}/users?username=${username}&exact=true" \
|
|
-H 'Content-Type: application/json' \
|
|
-H "Authorization: Bearer $backend_token")
|
|
|
|
user_id=$(jq -r '.[0] | .id' <<<"$user_info")
|
|
if [[ -z "$user_id" ]]; then
|
|
echo >&2 "ERROR: Could not find user_id for user: ${user_email}"
|
|
exit 1
|
|
fi
|
|
curl --fail --location --silent --request DELETE "${KEYCLOAK_BASE_URL}/admin/realms/${keycloak_realm}/users/${user_id}" \
|
|
-H 'Content-Type: application/json' \
|
|
-H "Authorization: Bearer $backend_token"
|
|
|
|
http_code=$(add_user "$user_email" "$username" "$password" "$user_attribute_one")
|
|
fi
|
|
if [[ "$http_code" != "201" ]]; then
|
|
echo >&2 "ERROR: Failed to create user: ${user_email} with http_code: ${http_code}"
|
|
exit 1
|
|
fi
|
|
fi
|
|
fi
|
|
done <"$user_file_with_one_email_per_line"
|