Install
openclaw skills install olares-sharedOlares profile and authentication foundation for olares-cli — required prerequisite for every other olares-cli skill on Olares (files, market, settings, dashboard, cluster). Covers the Olares profile model (one profile = one Olares instance + one Olares ID, e.g. alice@olares.com), first-time Olares login with password and optional TOTP, importing an existing refresh_token, switching / listing / removing Olares profiles, OS-keychain token storage keyed by Olares ID, automatic access_token refresh on 401/403, and the full Olares auth-error recovery table. Use when the user mentions Olares, Olares ID, olares-cli, OpenClaw on Olares, profile, login, logout, two-factor / 2FA / TOTP, refresh token, keychain, or sees errors like 'server rejected the access token', 'refresh token for X became invalid', 'no access token for X', 'already authenticated', or 'two-factor authentication required'.
openclaw skills install olares-sharedFoundation for every other olares-cli skill. Every business verb under cluster / files / market / settings / dashboard rides the active profile's token. Read this first.
Source of truth for flags & syntax is always
olares-cli <command> --help. This file only carries what--helpcannot give: the profile mental model, agent-driven login flow, token-storage backends, refresh semantics, and the error → fix matrix.
One profile = one Olares instance + one user identity, keyed by olaresId (e.g. alice@olares.com). Each profile owns its own access_token / refresh_token pair, stored in the OS keychain.
| Command | Purpose |
|---|---|
olares-cli profile login | Mode A — password (+ TOTP if 2FA is on); auto-creates the profile on first run |
olares-cli profile import | Mode B — bootstrap an access_token from an existing refresh_token |
olares-cli profile list | List every profile, mark the current one, show login status per profile |
olares-cli profile use <name|-> | Switch the current profile; - reverts to the previous one (like cd -) |
olares-cli profile remove <name> | Delete a profile and its stored token in one shot |
There is no
auth login/auth logoutnamespace and no per-invocation--profileoverride flag. Everything lives underprofile. "Logout" isprofile remove. Identity is whichever profile is currently selected; to target a different one, runolares-cli profile use <name>first.
olares-cli profile login --olares-id <olaresId>
--password-stdin; if 2FA is on, you MUST also pass --totp <code> because there is no second prompt.--password <plaintext> flag — passwords are never accepted on the command line.olares-cli profile import --olares-id <olaresId> --refresh-token "$OLARES_REFRESH_TOKEN"
Exchanges the refresh_token for an access_token once via /api/refresh and writes both to the keychain. Read the token from an env var or secret manager — never inline plaintext.
When you (an AI agent) drive the login on the user's behalf, do NOT pass password / TOTP as command-line arguments. Spawn olares-cli profile login --olares-id <id> as a background process so it parks at the password prompt, forward the prompt to the user, and read its output after the command exits to confirm success.
profile list output:
NAME OLARES-ID STATUS
* alice alice@olares.com logged-in (23h59m)
bob bob@olares.com expired
eve eve@olares.com invalidated
frank frank@olares.com never
| STATUS | Meaning | Recovery |
|---|---|---|
logged-in (Xh Ym) | Token valid; column shows time-to-expiry | — |
logged-in | Token present but JWT has no exp claim (can't verify locally) | Trust until the server says no |
expired | JWT exp is in the past | profile login |
invalidated | Server explicitly rejected the refresh leg | profile login directly (no need to profile remove first) |
never | No token has ever been stored | profile login or profile import |
The leading * marks the current profile. profile use accepts either the NAME alias or the olaresId.
| OS | Backend | Location |
|---|---|---|
| darwin | macOS Keychain | service olares-cli, account = olaresId |
| linux | AES-256-GCM file | under ~/.local/share/olares-cli/ |
| windows | DPAPI | HKCU\Software\OlaresCli\keychain |
After login / import succeeds, the CLI prints token stored via <backend> (service "olares-cli", account "<id>"). If the backend resolves to file-fallback (sandboxed / CI environments), be aware the token now sits in a file with different security properties than the system keychain.
The plaintext
~/.olares-cli/tokens.jsonfrom older builds is deprecated — if a user upgraded and suddenly appears "logged out",profile loginis the fix.
profile login and profile import both reject the case "a still-valid token already exists for this olaresId" — to force-overwrite, run profile remove <id> first. Expired / invalidated / never-logged-in profiles get the new token written in place; this lets scripts call login after invalidated without an extra remove step.
The CLI rotates expired access_tokens transparently. Users do NOT need to run profile login just because their access_token aged out — only when the refresh_token itself becomes invalid.
files cat, files download, files rm, market verbs, …): on 401/403 the transport calls /api/refresh and retries once with the new token.files upload chunks): pre-decode the JWT exp; if within 60s of expiry, refresh BEFORE sending, because once a *os.File chunk is consumed it can't be replayed on a 401.Across goroutines AND across concurrent olares-cli processes, /api/refresh is hit at most once per stale token (in-process mutex + cross-process flock).
Do not implement custom retry/backoff loops on top of auth errors. Once you see
ErrTokenInvalidatedorErrNotLoggedIn, onlyprofile login/profile importwill help.
| Error message (excerpt) | Meaning | Fix |
|---|---|---|
refresh token for <id> became invalid at <ts> | /api/refresh returned 401/403 — the grant is dead | olares-cli profile login --olares-id <id> |
no access token for <id> | Profile selected but keychain has no entry | olares-cli profile login or profile import |
server rejected the access token (HTTP 401) / (HTTP 403) | After auto-refresh the server still rejects (rare) | olares-cli profile login --olares-id <id> |
--olares-id is required | login / import invoked without olaresId | Add --olares-id <id> |
already authenticated for <id> (expires in ...) | Still-valid token exists | olares-cli profile remove <id> then re-run |
a token is already stored for <id> but its expiry can't be determined client-side | Token present but JWT carries no exp claim | profile remove <id> then re-run |
two-factor authentication required: re-run with --totp <code> | 2FA on, non-TTY context | Re-run with --totp <code>, or run interactively |
password is empty / TOTP code is empty | stdin / TTY returned an empty string | Check for premature EOF or an empty pipe |
profile <name> not found | profile use / profile remove referenced an unknown profile | profile list to see the actual names |
Do not silently retry auth errors. 401/403 after auto-refresh and
already authenticatedare deterministic — follow the table; blind retries make it worse.
--password <plaintext> argument (it does not exist). Passwords go through the TTY or --password-stdin fed by a secret pipe.access_token / refresh_token to the terminal. When passing a refresh_token to profile import, source it from an environment variable: --refresh-token "$OLARES_REFRESH_TOKEN".profile remove, files rm, files upload --overwrite, cluster pod delete, …). Do not act unilaterally on the user's behalf.