> ## Documentation Index
> Fetch the complete documentation index at: https://docs-stg.outerlayer.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Troubleshoot setup

> Common errors in sign-in, sessions and review, and the command that fixes each.

Run `outerlayer doctor` first. Most failing checks name their fix. The entries below are grouped by the message or symptom you see.

A build that fails or never starts on a host is covered in [Troubleshoot builds](/troubleshoot-builds).

## Signing in and choosing a factory

### `outerlayer login` keeps waiting, or says the link expired

In a terminal, `login` prints a link and a code, then waits. Open the link, check the dashboard shows the same code, and approve it. The link has a time limit. After it, you see `the login link expired; run outerlayer login again`. A login someone declined ends with `the login was denied`.

When stdout is not a terminal, as in an agent's shell, `login` prints one JSON line with `"status": "waiting"` and exits 75. Approve the link it names, then run the `check` command from that line, `outerlayer login --check <id>`. Exit 75 again means it is still waiting. See [`outerlayer login`](/reference/cli-cloud#outerlayer-login).

### `login` exits 2 with "--url and --app-id apply only to a piped key"

Browser login takes its gateway address from the dashboard, so it refuses both flags. Drop them, or pipe a key in with them.

### `login` says it "is waiting for an API key on stdin"

Something left stdin open, so `login` waits for a key. Close stdin, or run it with nothing piped to sign in by browser.

### `outerlayer connect` exits 2: "has no link to … yet"

The connection is saved, but the repository is not linked to the factory. The message prints the factory's Work page link. Open it, choose **Connect GitHub repository** and grant the App access, then **Link repository**. Run `outerlayer connect` again. See [Connect a repository](/connect-repository).

### A command says no gateway URL or address is saved

There is no default gateway, so a cloud command with no URL refuses. You see `missing --url`, `no gateway address is saved`, or, from `mcp serve`, `no gateway URL`. Run `outerlayer login`, which saves the address from the dashboard. Or set `OUTERLAYER_URL`, or pass `--url`. See [Credential resolution](/reference/cli#credential-resolution).

### A command says credentials are missing

`sync`, `work` and `emit` refuse when no credential is saved. The message starts with `missing`, then names each value it lacks, such as `missing --url, a login or OUTERLAYER_API_KEY, --app-id`. Run `outerlayer login` with nothing piped and approve the link. Then run `outerlayer connect` to choose a factory.

If it says you are logged in but no factory is chosen, run `outerlayer connect`, or pass `--app-id`. To use a key you already have, pipe it in:

```bash theme={"system"}
echo "$OUTERLAYER_KEY" | outerlayer login --url https://api.outerlayer.ai --app-id <factory-id>
```

Never pass the key on the command line. The `--api-key` flag is deprecated. Pipe the key to `login`, or set `OUTERLAYER_API_KEY`. See [API keys](/api-keys).

### Commands use a factory key instead of your login

A factory key always [wins over a login](/reference/cli#credential-resolution). Run `outerlayer doctor`. A **Factory key** check means a key is in use, and its detail names where it came from. To use your login instead:

* `unset OUTERLAYER_API_KEY`, and remove it from your shell profile.
* Delete the `apiKey` field from `~/.outerlayer/config.json`.

After a browser login, `login` warns when an `apiKey` is saved in that file. It does not warn about `OUTERLAYER_API_KEY`.

### "not authorized — the API key is unknown, expired, or bound to a different factory"

The key was revoked, or the factory id you gave `login` is a different factory. Check **Settings → General** for the Factory Id and **Settings → API keys** for the key. Then run `login` again. With a login, the message says the login expired or was revoked: run `outerlayer login`.

## Sessions and sync

### sync says "not launched with OUTERLAYER\_WORK"

The sessions were started without the variable. They stay on this machine and never upload. Start a new session on the item's number. `work build --issue` adds the issue to the Work page if it is not there yet, and prints the item's number:

```bash theme={"system"}
outerlayer work build --issue 42 --local   # prints the item's number, say #7
OUTERLAYER_WORK=7 claude
```

See [Work on an item locally](/launch-a-session).

### `outerlayer sync` exits 2

The server rejected at least one session. The first 10 rejects are listed under the summary, then `… and N more rejects`. Each shows its reason, such as `session belongs to another work item`. A rejected session is not retried. Fix the cause, then run `outerlayer sync --all` to send it again. See [`outerlayer sync`](/reference/cli-cloud#outerlayer-sync).

### The session started but it is not on the work item's page

Read `~/.outerlayer/spool/hook-errors.log`. The usual reasons:

* `OUTERLAYER_WORK` named an issue (`#42`) rather than an item number. Run `work build --issue 42 --local` to get the item's number, then launch on it.
* The number names no item on this factory, or a withdrawn one. Check it on the Work page.
* The gateway could not be reached. The link retries a few times, then gives up.

After you fix the cause, end the session and resume it with the right variable. Its whole transcript then uploads. See [If you forgot the variable](/launch-a-session#if-you-forgot-the-variable).

### Cursor sessions are not captured

Reading Cursor's chats needs Node 22.5 or later. On older Node, sync skips Cursor and still syncs every other agent. Upgrade Node. See [Supported agents](/launch-a-session#supported-agents).

### The status line shows only the session cost

The daemon is not running. The cross-agent total comes from a file it keeps fresh. Start it in a terminal you keep open, or under a login agent:

```bash theme={"system"}
outerlayer daemon
```

### Hooks stopped firing after a Claude Code update

Run `outerlayer doctor` and read **Hooks installed** and **Settings JSON valid**. **Hooks installed** also fails when a hook runs a file that no longer exists, such as a cleared npx cache. Install the CLI globally, then reinstall the hooks. `init` backs the settings file up first.

```bash theme={"system"}
npm i -g @outerlayer/cli
outerlayer init --local
```

## Work items and review

### work build says the repository "is not a workpiece of this factory"

The error code is `repository_not_connected`. `outerlayer work build --issue <n>` uses the checkout's remote, and that repository must be linked to the factory. Link it on the factory's **Settings → General**, or from the setup panel on the Work page. Or pass `--repo owner/name` for a repository that is linked. See [Connect a repository](/connect-repository).

### `work claim` is refused with `work_item_not_requested`

An implement claim needs an unused build request and an item with no open pull request. Ask for a build request with `outerlayer work build --issue <n>`, then claim again. On an item with an open pull request, the request feeds an amend claim instead. An amend claim needs a thread waiting on an agent since the last attempt. Hand a thread to the agent on the item's page first. See [`work claim`](/reference/cli-work#outerlayer-work-claim-renew-release).

### `work comment` is refused with `verdict_needs_person`, `verdict_on_criterion` or `artifact_needs_attach`

A verdict, `--pass` or `--fail`, is a person's: run it yourself, outside the agent session, with your own login. [`work comment`](/reference/cli-work#outerlayer-work-comment) says what to do for the other codes.

### `emit criteria` is refused (409)

The item already has a recorded list, and only a person may replace it. When a build's list was refused because the issue's criteria changed after the first build, the build says so on the item's general thread. Replace the list from the acceptance file the build committed: `outerlayer emit criteria acceptance/<issue>-<name>.md --item <number>`. [`emit criteria`](/reference/cli-emit#outerlayer-emit-criteria) says who may replace a list, and how to let sessions do it.

### No checks run on your pull requests

The factory reads the policy and validators in `.outerlayer/` from each pull request's base branch. Until `init`'s files are merged there, no check runs. Commit `.outerlayer/` and merge it into that branch. See the [Quickstart](/quickstart).

### An artifact refuses to emit inside a session

The session has no launch record, so a spooled artifact would never upload. Start the session with `OUTERLAYER_WORK`, or run the emit from a plain shell with `--pr`.

### The evidence comment shows a policy error row

`.outerlayer/policy.yaml` or a validator file on the base branch failed to load. The row names the file and the problem. A validator loads whole or not at all. See [Policy and validators](/policy-and-validators).


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.