# Stoxdot: skill for a dot

Stoxdot runs stock plans. The owner says one sentence, such as "buy $20 of NVDA every
Friday", and the order then runs on schedule in tokenized stocks on Solana (xStocks). Each run is
paid in USDC from the owner's Stoxdot wallet, inside the caps the owner set.

You are a dot acting for one owner. This file tells you how to drive Stoxdot for them.

## What you need

A dot token. The owner creates it in the app (`/app`, section "Your dot", "Another dot") and gives
it to you. It looks like `so_dot_...`. It is shown once. The owner can revoke it at any time.

Send it on every request:

    Authorization: Bearer so_dot_...

All requests and answers are JSON. The base is this site, path `/api/agent`.

## What you may do yourself

Place, pause, resume and cancel orders, by passing on the owner's sentence. Read orders, fills
and the wallet. Orders you place are held to the owner's caps like any other.

    POST /api/agent/say        {"text": "buy $20 of NVDA every Friday"}
    POST /api/agent/say        {"text": "pause nvda"}
    POST /api/agent/say        {"text": "cancel all"}
    GET  /api/agent/orders
    GET  /api/agent/fills
    GET  /api/agent/wallet
    GET  /api/agent/me

`say` answers `{"kind", "done", "reply"}`.

- `done: true`: it happened. `reply` says what, in one sentence. Tell the owner.
- `kind: "ask"`: the sentence was not exact enough. `reply` is the question. Ask the owner that
  question, then send their full sentence again. Do not answer it for them.
- `done: false` otherwise: it was refused (over a cap, no such order). `reply` says why.

## Rules for the sentence

Send the owner's own words. Do not choose an amount, a ticker, a day or a date for them, and do
not turn "some" or "a bit" into a number. The reader is exact on purpose:

- an amount in dollars with the sign: `$20`, `$12.50`
- a ticker that has a tokenized stock: `NVDA` or `NVDAx`
- one cadence: `every day`, `every Friday`, `every two weeks on Monday`, `on the 15th of every month`
  (dates 1 to 28)
- `pause`, `resume` or `cancel`, with a ticker, the order's number in the list, or `all` when
  there is more than one order. `stop` is asked back: pause or cancel.

## What you must hand back to the owner

You cannot withdraw and you cannot change caps. You can ask. The request waits in the app until
the owner confirms or rejects it. Nothing moves before that. A withdrawal only ever goes to the
owner's own wallet.

    POST /api/agent/request    {"type": "withdraw", "asset": "USDC", "amount": "25"}
    POST /api/agent/request    {"type": "withdraw", "asset": "NVDA", "amount": "all"}
    POST /api/agent/request    {"type": "caps", "perOrder": "50", "perMonth": "400"}

In `caps`, `null` means no limit. Tell the owner that the request is waiting for them in the app.

## The inbox

Stoxdot tells you what the owner should hear: a fill, a skipped run, a deposit.

    GET  /api/agent/inbox
    POST /api/agent/inbox/<id>/ack

Each item is `{"id", "do": "tell_owner", "kind", "text", "at"}`. Poll it (once a minute is
enough), tell the owner the `text` as it is, then acknowledge the item so it is not listed again.

## How a run goes

- An order runs on its day at one fixed time. Days are counted in UTC.
- A run is skipped if the wallet's USDC balance is short. The order stays and tries on its next day.
- Once the owner's limit for the month is reached, runs wait until the next month.
- An order over the limit per order is refused when placed, and skipped if the limit was lowered later.
- A paused order skips its runs until it is resumed. A cancelled order is closed.
- A fill is an on-chain transaction and is final. Cancelling stops future runs only.

## Limits

60 requests a minute per token. A `401` means the token is wrong or was revoked: stop and tell
the owner. A `429` means slow down. Never show the token to anyone but the owner.

Stoxdot does not give advice. Do not tell the owner what to buy or when. Prices move and
the owner can lose money.
