Create the first administrator
This page creates the administrator of a freshly installed server. Self sign-up is disabled on purpose; every other user is created or invited by an administrator in Studio.
Prerequisites
A server installed with Install the server (/health returns HTTP 200 with "status":"ok").
Steps
Open the one-time setup link the installer printed. It fills in the setup token and Studio removes it from the address bar.
If you lost the link, open
https://studio.example.com/installand paste the token from the server:bashsudo cat /etc/automaton/secrets/setup-tokenSelect Check installation, then enter your name, email and a password of at least 12 characters with uppercase, lowercase, a number and a symbol.
Sign in with that account.
The email you type in step 3 is the administrator's sign-in. Nothing on the server stores it for you. /etc/automaton/installation.json holds only the certificate email, which Let's Encrypt uses for expiry notices; it is not an account and signing in with it gives 401. If you forgot which email you used, check the confirmation you saved or ask whoever ran the setup; an AI agent must ask the person, not guess.
SMTP is not needed to start: the first administrator's email is confirmed by this setup flow. The setup page does not reopen once setup is complete.
Without a browser (SSH or an AI agent)
Studio's setup page calls two endpoints, and you can call them yourself. The snippet below needs Bash (for process substitution) and jq, which a fresh Ubuntu 24.04 installation does not include; install it first with sudo apt-get install -y jq. Run this on the server, in a shell where the password is typed at a hidden prompt, never given as an argument and never echoed:
API=https://api.example.com
read -rp "Administrator email: " EMAIL
read -rp "Name: " NAME
read -rsp "Password (12+ characters, upper, lower, number, symbol): " PASSWORD; echo
# No terminal (an AI agent or a script)? Read it from a file only you can read instead:
# PASSWORD=$(< /root/admin-password); (create it with: umask 077; read -rs p; printf %s "$p" > /root/admin-password)
# or from standard input: IFS= read -r PASSWORD
# An agent generates a compliant password into the variable, never echoed and never in a file:
# PASSWORD=$(printf 'Aa1!'; openssl rand -base64 24 | tr -d '\n=') # then see "When an AI agent sets up the server"
# 1. Optional: ask whether setup is open and whether a token is required.
curl -s "$API/api/install/status"
# 2. Create the first administrator. The setup token goes from the file into a header
# through a pipe, so it is never printed or stored in your shell history.
jq -n --arg name "$NAME" --arg email "$EMAIL" --arg password "$PASSWORD" \
'{name: $name, email: $email, password: $password}' |
curl -s -w '\nHTTP %{http_code}\n' -X POST "$API/api/install" \
-H @<(printf 'X-Automaton-Setup-Token: %s\n' "$(sudo cat /etc/automaton/secrets/setup-token)") \
-H 'Content-Type: application/json' --data-binary @-
unset PASSWORDPOST /api/install takes name, email and password and returns 200 when the account exists. A wrong or missing token returns 403 ("A valid server setup token is required."); a password that is too weak returns 400 with the reason; 409 means setup was already completed. POST /api/install/checks (same header) runs the installation checks that Studio shows after the first sign-in. The token the installer printed is single-purpose: when setup completes the server replaces the content of /etc/automaton/secrets/setup-token with a new random value that is never printed, so the printed one stops working. Re-running the installer or the updater does not print or reset it. The new value is what lets root create one-time password links. If you edit the token file by hand, restart the API afterwards (it is mounted into the container as one file).
EMAIL and PASSWORD in the snippet are the sign-in you are creating now: the email you chose, not the certificate email. Keep both: the CLI sign-in below asks for them again. Then sign in the CLI without a browser: see Log in the CLI on a server without a browser.
If an AI agent or script created the administrator this way, finish with the one-time link: run server password-link and show the printed link to the user, as in When an AI agent sets up the server for you. Do not end before the link is shown.
The password never goes on the command line: jq --arg receives it from the shell variable. If you keep it in a file, make it mode 0600 and delete it afterwards.
When an AI agent sets up the server for you
The agent steps are in Install the server. An agent needs a signed-in CLI to deploy, so it creates the administrator itself with a password it generates and never prints or writes to a file, used in the same shell, then unset. In the same shell as the install, with API and EMAIL set:
PASSWORD=$(printf 'Aa1!'; openssl rand -base64 24 | tr -d '\n=')
jq -n --arg name "Administrator" --arg email "$EMAIL" --arg password "$PASSWORD" \
'{name: $name, email: $email, password: $password}' |
curl -s -w '\nHTTP %{http_code}\n' -X POST "$API/api/install" \
-H @<(printf 'X-Automaton-Setup-Token: %s\n' "$(cat /etc/automaton/secrets/setup-token)") \
-H 'Content-Type: application/json' --data-binary @-Check: the output ends with HTTP 200 (403, 400 and 409 are explained above). Keep PASSWORD for the CLI sign-in, then unset it.
It ends with a one-time link for the user. Run this last, after any app you were asked to build, so the 30-minute link is fresh:
"$(command -v automaton)" server password-link --email "$EMAIL"As a non-root user, prefix it with sudo. Show the printed link in your final message, together with https://studio.<domain>. It is a link to Studio's set-password page; if it is not, stop.
The link works once and for 30 minutes. Opening it asks for a new password; the generated one stops working at that moment and the user signs in with theirs. If the link expires or is lost, run the command again: each new link voids the earlier ones. Only someone who can read /etc/automaton/secrets/setup-token (root) can create it, it needs no sign-in and no email (SMTP), and it works only for administrator accounts. The command finds the server from /etc/automaton/installation.json, so it works under sudo without the CLI's sign-in; use --config-dir if the configuration is elsewhere and --server <api-url> to name another server. Treat the link like a password until it has been used.
Verify it worked
Studio opens after sign-in and Admin → Installation shows Check installation results. Public DNS and open ports show as unverified there; check them from another network.
Common errors
- Token rejected. Use the current value from
/etc/automaton/secrets/setup-token. After setup is complete the printed token no longer works; the file holds a new value for root. - Setup returns 409. The administrator already exists. Run
server password-linkto give the user a link. - Link rejected or rate limited. Creating and using links is limited to 5 per hour per IP; wait and run the command again.
- Password refused. Use 12 or more characters with all four character kinds.
Next: add a Runner.