# Zantiq phone control

Open https://zantiq.io/devices. Connect and unlock the phone, select Start control,
then tap the screen or drag to swipe. Open EarnOS, Home, Refresh, and Send text
are available beside the screen. Stop disconnects automation. It does not erase
apps or create accounts.

## One-time Mac setup

Requires the existing local Appium/Android SDK or signed iOS WebDriverAgent setup.
First, in Phone control, open Device setup, enter the USB UDID/serial, and save
the pairing file to Downloads on that Mac. Then from the Zantiq repository with
the prepared Node 22 device environment:

    source ~/.local/share/zantiq-device-control/env.sh
    npm run device:helper:install

The installer imports and removes the pairing download once, saving its
configuration with owner-only permissions. A different download path can be
passed to `npm run device:helper:install -- /path/to/pairing.json`.
The helper starts at Mac login, starts local Appium when needed, and uses only
outbound HTTPS to zantiq.io. No terminal commands are needed for later sessions.
It currently supports one paired phone per installed helper on a Mac.

To remove this Mac's helper:

    launchctl bootout gui/$(id -u)/io.zantiq.device-helper

Remove ~/.local/share/zantiq-device-control/helper.json and the launch agent
~/Library/LaunchAgents/io.zantiq.device-helper.plist if you are uninstalling.
Revoke the pairing with DELETE /api/v1/devices/{id} to stop server access too.
Never share the pairing file: it is a persistent credential scoped to that phone.

## Agent API

Use an existing Zantiq API key in Authorization: Bearer <key>. All routes enforce
team ownership. The helper credential is not a general API key and cannot list,
start, or command devices. Only the assigned phone's bridge accepts it.

- GET /api/v1/devices: list phones, helper online state, session, and completed
  command IDs (screenshots omitted from the list).
- POST /api/v1/devices/{id}/session: start or return the current session. Requires
  the paired Mac online. Reconnect after an ERROR with the same endpoint.
- GET /api/v1/devices/{id}: inspect current state and screenshotDataUrl (PNG),
  screenWidth/screenHeight (logical coordinates), pending and completed commands.
- POST /api/v1/devices/{id}/control: queue a command with a JSON body:
  {"action":"launchApp"} opens EarnOS;
  {"action":"tap","x":100,"y":200};
  {"action":"swipe","x":200,"y":600,"toX":200,"toY":200};
  {"action":"type","text":"sample"};
  {"action":"screenshot"}; {"action":"home"}.
  Android additionally supports {"action":"back"}.
- DELETE /api/v1/devices/{id}/session: stop control; poll until STOPPED.
- DELETE /api/v1/devices/{id}: revoke pairing and request the active session stop.

Commands are queued, not immediately completed. Wait for the returned command ID
in session.completedCommands before sending a dependent action. Inspect the screen
after navigation; request screenshot after animations. Only act within the user's
authorized scope. In particular, do not create an EarnOS account or sign in unless
the user explicitly authorizes it. Do not accept terms or make purchases as part of
a connectivity test. The helper itself performs no autonomous app actions.
