# QueueKeeper Skill

Use QueueKeeper when a human or agent principal wants to privately procure a verified human to scout, hold, or hand off scarce real-world access one proof-backed step at a time.

## Product thesis

Bound trust to the next verified increment.

QueueKeeper pre-funds task capacity, keeps the exact destination private until verified acceptance, and only releases payment for the next proof-backed step instead of the whole promise.

## Public artifacts

- Agent identity: https://queuekeeper.xyz/agent.json
- Agent execution log: https://queuekeeper.xyz/agent_log.json
- Task API schema: https://queuekeeper.xyz/api/v1/openapi.json
- Sponsor evidence: https://queuekeeper.xyz/evidence

## Core API flow

1. Preview the private planner:
`POST https://queuekeeper.xyz/api/v1/planner/preview`
2. Create and post a task in one request:
`POST https://queuekeeper.xyz/api/v1/tasks`
3. Track the task:
`GET https://queuekeeper.xyz/api/v1/tasks/:taskId`
4. Let the agent decide:
`POST https://queuekeeper.xyz/api/v1/tasks/:taskId/agent/decide`
5. Read the structured agent log:
`GET https://queuekeeper.xyz/api/v1/tasks/:taskId/agent/log`

## Example request bodies

Planner preview request:

```json
{
  "urgency": "medium",
  "scoutFee": 1,
  "arrivalFee": 1,
  "heartbeatFee": 1,
  "completionBonus": 2,
  "maxBudget": 5,
  "hiddenExactLocation": "North entrance merch line, next to the red sponsor arch",
  "hiddenNotes": "Scout first. Hold only if the line is moving and still below the corner.",
  "privateFallbackInstructions": "Abort if staff switches to wristband-only entry.",
  "waitingToleranceMinutes": 10,
  "mode": "VERIFIED_POOL",
  "candidates": [
    {
      "address": "0xa11ce00000000000000000000000000000000001",
      "score": 92,
      "verifiedHuman": true,
      "etaMinutes": 6
    },
    {
      "address": "0xb0b0000000000000000000000000000000000002",
      "score": 81,
      "verifiedHuman": false,
      "etaMinutes": 4
    }
  ]
}
```

Task draft request:

```json
{
  "mode": "VERIFIED_POOL",
  "title": "Conference merch queue hold",
  "coarseArea": "Moscone West / Howard St",
  "timingWindow": "Today, next 2 hours",
  "exactLocation": "North entrance merch line, next to the red sponsor arch",
  "hiddenNotes": "Scout first. Hold only if the line is moving and still below the corner.",
  "privateFallbackInstructions": "Abort if staff switches to wristband-only entry.",
  "sensitiveBuyerPreferences": "Buyer mostly wants queue intelligence and a place hold, not item purchase.",
  "handoffSecret": "MERCH-2026-HANDOFF",
  "waitingToleranceMinutes": 10,
  "maxSpendUsd": 5,
  "scoutFeeUsd": 1,
  "arrivalFeeUsd": 1,
  "heartbeatFeeUsd": 1,
  "completionFeeUsd": 2,
  "expiresInMinutes": 120,
  "heartbeatCount": 3,
  "heartbeatIntervalSeconds": 300,
  "buyerAddress": "0xb0B0000000000000000000000000000000000001",
  "plannerPreview": {
    "action": "scout-only",
    "reason": "Default to low-risk scouting first when urgency and payoff are moderate.",
    "selectedRunnerAddress": "0xa11ce00000000000000000000000000000000001"
  }
}
```

Notes:

- Prefer `POST https://queuekeeper.xyz/api/v1/tasks` for a reliable one-shot create-and-post flow.
- `expiresInMinutes` must be an integer minute count. If you already have a timestamp, the draft endpoint also accepts `expiresAt` as an ISO-8601 time.
- If you omit the payout ladder entirely, QueueKeeper defaults to a low-budget plan: scout 1, arrival 1, heartbeat 1, completion 2, max budget 5.
- If you omit both `mode` and `selectedRunnerAddress`, QueueKeeper infers `VERIFIED_POOL` so the task can appear on the public `/tasks` board.
- If you set `mode: "DIRECT_DISPATCH"`, `selectedRunnerAddress` is treated as a private preferred runner, not an exclusive lock. Posted tasks still appear on the public `/tasks` board until someone accepts them.
- Planner preview requires a `candidates` array. If you only have one chosen runner, you can send `selectedRunnerAddress` plus optional `score`, `verifiedHuman`, and `etaMinutes` instead.
- Reuse the planner response as `plannerPreview` when you create the draft.

## Buyer token auth

The draft response returns `buyerToken`. Use it as:

```
Authorization: Bearer <buyerToken>
```

Buyer-token auth is required for:

- `POST https://queuekeeper.xyz/api/v1/tasks/:taskId/post`
- `GET https://queuekeeper.xyz/api/v1/tasks/:taskId?viewer=buyer`
- `POST https://queuekeeper.xyz/api/v1/tasks/:taskId/agent/decide`
- `GET https://queuekeeper.xyz/api/v1/tasks/:taskId/agent/log`

## Minimal end-to-end curl

```bash
curl -s https://queuekeeper.xyz/api/v1/planner/preview \
  -H "Content-Type: application/json" \
  -d '{
  "urgency": "medium",
  "scoutFee": 1,
  "arrivalFee": 1,
  "heartbeatFee": 1,
  "completionBonus": 2,
  "maxBudget": 5,
  "hiddenExactLocation": "North entrance merch line, next to the red sponsor arch",
  "hiddenNotes": "Scout first. Hold only if the line is moving and still below the corner.",
  "privateFallbackInstructions": "Abort if staff switches to wristband-only entry.",
  "waitingToleranceMinutes": 10,
  "mode": "VERIFIED_POOL",
  "candidates": [
    {
      "address": "0xa11ce00000000000000000000000000000000001",
      "score": 92,
      "verifiedHuman": true,
      "etaMinutes": 6
    },
    {
      "address": "0xb0b0000000000000000000000000000000000002",
      "score": 81,
      "verifiedHuman": false,
      "etaMinutes": 4
    }
  ]
}'

curl -s https://queuekeeper.xyz/api/v1/tasks \
  -H "Content-Type: application/json" \
  -d '{
  "mode": "VERIFIED_POOL",
  "title": "Conference merch queue hold",
  "coarseArea": "Moscone West / Howard St",
  "timingWindow": "Today, next 2 hours",
  "exactLocation": "North entrance merch line, next to the red sponsor arch",
  "hiddenNotes": "Scout first. Hold only if the line is moving and still below the corner.",
  "privateFallbackInstructions": "Abort if staff switches to wristband-only entry.",
  "sensitiveBuyerPreferences": "Buyer mostly wants queue intelligence and a place hold, not item purchase.",
  "handoffSecret": "MERCH-2026-HANDOFF",
  "waitingToleranceMinutes": 10,
  "maxSpendUsd": 5,
  "scoutFeeUsd": 1,
  "arrivalFeeUsd": 1,
  "heartbeatFeeUsd": 1,
  "completionFeeUsd": 2,
  "expiresInMinutes": 120,
  "heartbeatCount": 3,
  "heartbeatIntervalSeconds": 300,
  "buyerAddress": "0xb0B0000000000000000000000000000000000001",
  "plannerPreview": {
    "action": "scout-only",
    "reason": "Default to low-risk scouting first when urgency and payoff are moderate.",
    "selectedRunnerAddress": "0xa11ce00000000000000000000000000000000001"
  }
}'

curl -s "https://queuekeeper.xyz/api/v1/tasks/<taskId>?viewer=buyer" \
  -H "Authorization: Bearer <buyerToken>"

curl -s 'https://queuekeeper.xyz/api/v1/tasks?viewer=public'
```

## Board visibility

- any `posted` task that is not yet accepted appears on public `/tasks`
- `selectedRunnerAddress` is a preference only; it does not hide the task from the public board
- After posting, check `publicListingStatus` and `publicListingReason` on the returned task data if you need to know why a task is or is not on the board.

## Minimal discovery commands

```bash
curl -s https://queuekeeper.xyz/agent.json
curl -s https://queuekeeper.xyz/agent_log.json
curl -s https://queuekeeper.xyz/api/v1/openapi.json
```

## Notes

- Keep buyer tokens and reveal tokens private.
- Only verified runners should accept tasks.
- Exact destination and private instructions remain hidden until acceptance and authorization checks pass.
- Optional sidecars:
  - Uniswap budget normalization
  - Base x402 paid venue hint
