Where is the OpenClaw config file, and how do you change its location?
The short answer is ~/.openclaw/openclaw.json, written in JSON5. The longer answer matters when your edits appear to be ignored, which is almost always a second config file or an environment variable winning over the one you edited.

By default OpenClaw reads a single file:
~/.openclaw/openclaw.json
It is JSON5, not strict JSON, which means comments and trailing commas are allowed. That is deliberate, because the file is meant to be edited by hand.
The exact path per platform
| Platform | Path |
|---|---|
| Linux | /home/<user>/.openclaw/openclaw.json |
| macOS | /Users/<user>/.openclaw/openclaw.json |
| Windows | C:\Users\<user>\.openclaw\openclaw.json |
| Docker | Inside the container, at the home of the user the process runs as |
On a managed server the file belongs to the user the gateway runs as, which is
often not the user you logged in with. If ls ~/.openclaw comes back
empty on a machine where OpenClaw is clearly running, that is usually why.
The three environment variables that move it
| Variable | Default | What it changes |
|---|---|---|
OPENCLAW_HOME | ~/.openclaw/ | The root of everything, config included |
OPENCLAW_CONFIG_PATH | $OPENCLAW_HOME/openclaw.json | The config file alone |
OPENCLAW_STATE_DIR | $OPENCLAW_HOME/state/ | Mutable state, not config |
OPENCLAW_CONFIG_PATH is the specific one. Set it and the default is
ignored entirely, which is exactly what you want when running more than one
instance on the same machine.
Why your edit did not take effect
This is the real reason most people search for the config path. Settings resolve in a fixed order, and the first source that defines a value wins:
- Process environment variables
.envin the current working directory~/.openclaw/.env- The
envblock insideopenclaw.json - Shell import, meaning files you sourced
Read that list twice if you are debugging. An ANTHROPIC_API_KEY
exported in your shell beats the one written in the config file, every time. The
config is not being ignored, it is being outranked.
The same trap catches services. A variable exported in .bashrc does
not exist for a systemd unit, so the config file wins there and loses in your
terminal, and the same install behaves differently depending on how it was
started.
Running more than one instance
Each instance needs its own values for all four of these, or they will fight over the same files:
OPENCLAW_CONFIG_PATHOPENCLAW_STATE_DIR- The workspace path
- The gateway port, default
18789
Permissions, because the file holds secrets
openclaw.json stores API keys in plaintext. So do several of its
neighbours. All of these should be chmod 600:
~/.openclaw/openclaw.json~/.openclaw/credentials/~/.openclaw/nodes/paired.json~/.openclaw/exec-approvals.json~/.openclaw/agents/<id>/agent/auth-profiles.json
If you would rather keep keys out of the file altogether, reference them instead
of writing them: "apiKey": "env:ANTHROPIC_API_KEY". Note the
env: prefix. Writing process.env.ANTHROPIC_API_KEY does
not work, that is JavaScript syntax and the config is data.
One more warning worth having
The setup wizard overwrites config sections rather than merging into them. Back up
openclaw.json before running it on an install you have customised.
Frequently asked questions
- Why are my edits ignored?
- Almost always because an environment variable outranks the config file, or because OPENCLAW_CONFIG_PATH points at a different file than the one you opened. Check the precedence table on this page.
- Can I put comments in the config?
- Yes. The file is JSON5, not strict JSON, so line comments and trailing commas are both legal.
- Is it safe to keep API keys in there?
- They are stored in plaintext, so the file must be chmod 600. If you would rather not have keys on disk at all, reference them as env:VAR_NAME and set the variable elsewhere.
Related guides
- OpenClaw error: gateway connect failed, pairing requiredThis error means the gateway is running and reachable, but it does not trust the client that just connected. Nothing is broken. The device simply has no approved identity yet, and there are four different reasons that can happen.
- OpenClaw error: API rate limit reached, please try again laterThe single most useful thing to know about this error is that OpenClaw did not produce it. It is relaying a 429 from whichever model provider it was calling, so the fix is on the provider side or in how hard OpenClaw is hitting it.
- How to Fix "Hermes backend exited before it became ready"The number in the brackets decides everything. Zero means a healthy backend shut itself down, usually a Windows watchdog misfire, and any other number means it genuinely failed, usually an update applied while Hermes was still running.
- How to Fix "Timed out connecting to Hermes backend after 15000ms"The 15000ms timeout is a single slow answer from a healthy local backend, not a broken agent or a bad API key. Running the terminal version once warms the cache and clears it in most cases, and the underlying stall was repaired upstream in release v2026.7.1.
