# Troubleshooting

Source: https://pushary.com/docs/agents/reference/troubleshooting
Last updated: 2026-10-19

> Fix Pushary agent notifications that do not arrive. What to do when your phone does not buzz, the agent does not ask, or doctor reports a failed check.

Most problems with agent notifications come down to three things: no phone is paired, the agent's hook is not running, or a rule decided the call without asking you. Each section below starts with the fix, then the reasons behind it. Start by running the health check on the machine where your agent runs:

```bash
npx pushary@latest doctor
```

Doctor checks every configured agent, the connection to Pushary, your key and your plan, then sends a real test push to your phone. On Windows PowerShell, type `npx.cmd pushary@latest doctor`.

If Claude Code runs but nothing reaches your phone, [Claude Code notifications not working](/claude-code-notifications-not-working) walks through the Claude Code side.

## My phone did not buzz [#my-phone-did-not-buzz]

**Fix:** run `npx pushary@latest doctor` and read the **Phone reachable** and **Push notification sent** lines. If no phone is paired, pair the Pushary app:

```bash
npx pushary@latest setup --connect app
```

Get the app from the [App Store](https://apps.apple.com/us/app/pushary/id6785677563) or [Google Play](https://play.google.com/store/apps/details?id=com.pushary.app) first, and sign in with the same account. Other reasons the phone stays quiet:

* **You were at the machine.** In When away, presence can hold back a bounded approval's phone push while the decision waits in the agent or on the Mac app. Ordinary full-access MCP questions without a host deadline can reach both Mac and phone. To test the phone, switch to Always for a while in the app or the dashboard.
* **Your mode sends no approval push.** In agent sends no approval alert. Alert only sends an alert with no approve or deny. See [the four approval modes](/docs/agents/policies#the-four-approval-modes).
* **A rule approved the call.** Read-only commands such as `ls` and `git status`, built-in `Read`, and anything you tapped **Always allow** on run without asking. Check your rules at [Dashboard > Agent > Policies](https://pushary.com/dashboard/agent/policies).
* **Notifications are off on the phone.** On iPhone, open Settings > Notifications > Pushary and turn on Allow Notifications. On Android, open the app's notification settings and allow them.
* **The push was held back.** The kill switch, a snooze, your task update setting or In agent mode hold back notifications. `send_notification` then returns `"sent": 0` and a `suppressed` line that says why. The notification is still in your activity feed.
* **The call targeted subscribers.** `send_notification` with `subscriberIds`, `externalIds` or `tags`, and the REST endpoint `POST /api/v1/server/send`, reach browser push subscribers only, never the phone app.

## The agent did not ask me [#the-agent-did-not-ask-me]

**Fix:** confirm the agent runs a Pushary hook, then check what decided the call. Run `npx pushary@latest doctor` and look for a failed line under that agent.

* **The agent has no hook.** Windsurf, Claude Desktop, Cowork, ChatGPT and other MCP-only agents choose when to ask. Their tool calls are not gated. [Supported agents](/docs/agents/supported-agents) shows which agents enforce.
* **Claude Code's permission mode decided.** In plan, auto and dontAsk modes, Pushary leaves tool calls to Claude Code. In acceptEdits, file edits are left to Claude Code, and shell commands still come to Pushary. The kill switch and deny rules still apply in every mode. Set `PUSHARY_RESPECT_PERMISSION_MODE=0` to gate calls in every mode.
* **Claude Code's own allowlist approved it.** A command your Claude Code settings already allow runs without asking Pushary.
* **A Pushary rule approved it.** Read-only commands, built-in `Read` and Always allow rules run silently. See [the auto-approve shortcut](/docs/agents/policies#the-auto-approve-shortcut).
* **The agent started before setup.** Restart the agent after you run setup so it loads the hooks.
* **Codex has not trusted the hooks.** See [doctor says "Codex: hooks trusted" failed](#doctor-says-codex-hooks-trusted-failed).

## The agent cannot see the Pushary tools [#the-agent-cannot-see-the-pushary-tools]

**Fix:** restart the agent after setup, then check that the MCP server is configured.

* In Claude Code, run `claude mcp list` and look for `pushary`.
* In Cursor, open Cursor Settings and check that Pushary is listed and connected under MCP.
* The server URL must be exactly `https://pushary.com/api/mcp/mcp`.
* For a stdio client, check that `npx` is on your `PATH`.

## The agent says "Not authenticated" or a call returns 401 [#the-agent-says-not-authenticated-or-a-call-returns-401]

**Fix:** run `npx pushary@latest status` to see which key is in use and whether pushary.com accepts it.

* A key looks like `pk_xxx.xxx`: `pk_`, 24 hex characters, a dot, and a 48 hex character secret. Copy the whole key.
* The header must be `Authorization: Bearer pk_xxx.xxx`.
* If `PUSHARY_API_KEY` is set in your shell, it wins over the key in `~/.pushary/config.json`, and the CLI warns when they differ. Check it with `echo $PUSHARY_API_KEY`.
* Keys belong to one site. With several sites, use the key for the right one.
* A revoked key stops working at once. Create a new one at [Settings > API keys](https://pushary.com/dashboard/agent/settings).

## doctor says "Phone reachable: no phone paired" [#doctor-says-phone-reachable-no-phone-paired]

**Fix:** pair the Pushary app with `npx pushary@latest setup --connect app`, then run doctor again.

The key works, but nothing is paired that can receive an approval. If doctor says another device on the site is paired but not yours, the same command pairs your own phone.

## doctor says "Plan active" failed [#doctor-says-plan-active-failed]

**Fix:** activate your plan at the link doctor prints, then run `npx pushary@latest doctor`.

Doctor prints "Your Pushary plan is not active, so approvals will not deliver yet." Your key is valid, and activating the plan does not require a new one. Until then, `ask_user`, `send_notification` and `propose_scope` return a 403 with the code `subscription_required`.

## doctor says "hook command resolves" failed [#doctor-says-hook-command-resolves-failed]

**Fix:** run `npx pushary@latest setup` again. It installs the hook commands globally.

The agent's settings point at a Pushary hook command, such as `pushary-hook` for Claude Code, that is not on your `PATH`. Check with `which pushary-hook`. For Claude Code, the hooks live in `~/.claude/settings.json` under `hooks.PreToolUse`, and the MCP server in `~/.claude.json` under `mcpServers.pushary`.

## doctor says "Codex: hooks trusted" failed [#doctor-says-codex-hooks-trusted-failed]

**Fix:** type `/hooks` in Codex to enable and trust the Pushary hooks, or run `npx pushary@latest setup` again to repair them.

Codex runs a hook only after you trust it. Setup writes the hooks to `~/.codex/hooks.json` and pre-trusts them in `~/.codex/config.toml`. Native hooks need Codex 0.122.0 or newer. On an older Codex, setup installs the deprecated notify handler instead: it needs `pushary-codex` on your `PATH` and an absolute path in the `notify` entry of `~/.codex/config.toml`. Upgrade Codex and run setup again to get approvals.

## doctor says "MCP server reachable" failed [#doctor-says-mcp-server-reachable-failed]

**Fix:** check that this machine can reach pushary.com:

```bash
curl -sS -o /dev/null -w '%{http_code}\n' https://pushary.com/api/mcp/mcp
```

Any status code, such as 401, means the server is reachable. A timeout or connection error means something on your network blocks it. Behind a corporate proxy, set `HTTPS_PROXY`; CLI commands such as `setup` and `doctor` honor it. The proxy must also allow streaming HTTP responses.

## The approval timed out before I answered [#the-approval-timed-out-before-i-answered]

**Fix:** give yourself longer in [Dashboard > Agent > Policies](https://pushary.com/dashboard/agent/policies). Raise **Timeout** for Always or **Push window** for When away, up to 300 seconds.

New workspaces start on Always with a 60 second timeout. Switched to When away, the push window starts at 20 seconds. When time runs out, the rule's **If you don't respond** action applies: auto approve, auto deny, ask in the terminal, or keep waiting for your phone. Your phone also needs a network connection to send the answer.

## A question expired before I could answer [#a-question-expired-before-i-could-answer]

**Fix:** read the returned state and handoff instructions. If the question expired, continue only through the agent's current approval flow.

Ordinary full-access MCP questions without a host deadline do not expire after ten minutes. Restricted connectors, REST asks and native permission hooks retain their existing deadlines. A saved answer does not restart a closed agent or authorize a different request.

## I get "Rate limit exceeded" [#i-get-rate-limit-exceeded]

**Fix:** answer or cancel open questions, or wait a few minutes before sending more notifications.

| Limit                               | Value              |
| ----------------------------------- | ------------------ |
| Pending questions per agent session | 8                  |
| Pending questions per site          | 25                 |
| MCP notifications per site          | 10 every 5 minutes |

The REST API has its own per-workspace limits by plan; see [Pricing and limits](/docs/pricing-and-limits). A REST 429 carries a `Retry-After` header.

## Hermes is not sending anything [#hermes-is-not-sending-anything]

**Fix:** check that the plugin is in Hermes's plugins folder, enabled, and loaded by the running Hermes.

```bash
ls ~/.hermes/plugins/pushary
hermes config get plugins.enabled
npx pushary@latest doctor
```

* Enable it with `hermes plugins enable pushary`. Running `npx pushary@latest setup --agents hermes` writes the plugin and enables it for you.
* Restart Hermes after installing, so it loads the plugin: `hermes gateway restart`. Doctor says whether the running Hermes has loaded it.
* Set `PUSHARY_API_KEY` in the shell where Hermes runs.
* Using the MCP server instead? Check that `config.yaml` has a `mcp_servers.pushary` entry.
* The "Hermes run failed" push comes only from the native plugin, not the MCP server. A tool call that fails along the way never pushes, because Hermes recovers from it.

See the [Hermes guide](/docs/agents/guides/hermes) for the full setup.

<Callout type="info">
  Still stuck? Run `npx pushary@latest doctor --bundle`. It writes a redacted diagnostics file you can attach when you contact support.
</Callout>

## Next steps [#next-steps]

<Cards>
  <Card title="Run the quickstart again" description="Set up your agents and pair your phone with one command." href="/docs/agents/quickstart" />

  <Card title="Check every CLI flag" description="Every command and flag in the Pushary CLI, including doctor and status." href="/docs/agents/reference/cli" />
</Cards>