65 lines
2.4 KiB
Bash
Executable File
65 lines
2.4 KiB
Bash
Executable File
#!/bin/sh
|
|
# Create-or-update the `frosty-observer` Grafana account with the Editor role.
|
|
#
|
|
# Why an account and not a role: Grafana OSS cannot define custom RBAC roles -
|
|
# /api/access-control/roles is Enterprise-licensed and 404s here - so a
|
|
# pre-provisioned principal with a scoped basic role is the OSS equivalent.
|
|
# Anonymous access stays read-only Viewer; this account is what trace drill-down
|
|
# through Explore uses.
|
|
#
|
|
# Idempotent: safe to re-run, and re-running fixes a drifted role or password.
|
|
set -eu
|
|
|
|
API="${GF_URL:-http://grafana:3000}"
|
|
AUTH="${GF_ADMIN_USER}:${GF_ADMIN_PASSWORD}"
|
|
LOGIN="${GF_OBSERVER_USER}"
|
|
PASSWORD="${GF_OBSERVER_PASSWORD}"
|
|
ROLE="${GF_OBSERVER_ROLE:-Editor}"
|
|
|
|
api() {
|
|
# $1 method, $2 path, $3 optional JSON body. Prints body, then HTTP code on
|
|
# the last line so the caller can branch on it.
|
|
if [ $# -ge 3 ]; then
|
|
curl -sS -u "$AUTH" -X "$1" -H 'Content-Type: application/json' \
|
|
-d "$3" -w '\n%{http_code}' "$API$2"
|
|
else
|
|
curl -sS -u "$AUTH" -X "$1" -w '\n%{http_code}' "$API$2"
|
|
fi
|
|
}
|
|
|
|
code_of() { printf '%s' "$1" | tail -n 1; }
|
|
body_of() { printf '%s' "$1" | sed '$d'; }
|
|
|
|
# Grafana can accept connections a moment before its API is serving.
|
|
i=0
|
|
until [ "$(code_of "$(api GET /api/health)")" = "200" ]; do
|
|
i=$((i + 1))
|
|
[ "$i" -lt 60 ] || { echo "grafana API never became ready" >&2; exit 1; }
|
|
sleep 2
|
|
done
|
|
|
|
lookup=$(api GET "/api/users/lookup?loginOrEmail=$LOGIN")
|
|
if [ "$(code_of "$lookup")" = "200" ]; then
|
|
id=$(body_of "$lookup" | sed -n 's/.*"id":\([0-9]*\).*/\1/p')
|
|
echo "grafana: '$LOGIN' exists (id=$id)"
|
|
# Re-assert the password so a redeploy with new credentials converges.
|
|
api PUT "/api/admin/users/$id/password" "{\"password\":\"$PASSWORD\"}" >/dev/null
|
|
else
|
|
created=$(api POST /api/admin/users \
|
|
"{\"name\":\"Frosty Observer\",\"login\":\"$LOGIN\",\"password\":\"$PASSWORD\"}")
|
|
if [ "$(code_of "$created")" != "200" ]; then
|
|
echo "grafana: failed to create '$LOGIN': $(body_of "$created")" >&2
|
|
exit 1
|
|
fi
|
|
id=$(body_of "$created" | sed -n 's/.*"id":\([0-9]*\).*/\1/p')
|
|
echo "grafana: created '$LOGIN' (id=$id)"
|
|
fi
|
|
|
|
# Org role is what actually gates Explore, so assert it every run.
|
|
role=$(api PATCH "/api/org/users/$id" "{\"role\":\"$ROLE\"}")
|
|
if [ "$(code_of "$role")" != "200" ]; then
|
|
echo "grafana: failed to set role $ROLE on '$LOGIN': $(body_of "$role")" >&2
|
|
exit 1
|
|
fi
|
|
echo "grafana: '$LOGIN' has org role $ROLE - sign in to use Explore -> Tempo"
|