# Mint CLI Signup Token

**POST** `/v1/sign_up`

Mints a one-shot `cli_token` and returns a prefilled signup URL. The user opens the URL, clears the captcha, accepts the Terms of Service and creates the account. The CLI then polls `GET /sign_up/{cli_token}` until the accounts service has propagated the new user and its first API key, at which point the API returns the credentials exactly once.

The API does not store the `cli_token` when it mints it. The token becomes known to the API only once the accounts service propagates the new user, so the CLI must set its own polling deadline. If the user never completes signup, `GET /sign_up/{cli_token}` returns `202 Accepted` indefinitely.

## Example request

**curl**

```bash
curl -X POST 'https://api.ideal-postcodes.co.uk/v1/sign_up' \
  -H 'Content-Type: application/json' \
  -d '{
    "email": "user@example.com",
    "name": "Jane Smith",
    "org_name": "Example Corp",
    "org_address_line_one": "10 Example Street",
    "org_post_town": "London",
    "org_postcode": "SW1A 1AA",
    "org_country_code": "GB"
  }'
```

**JavaScript**

```javascript
const response = await fetch('https://api.ideal-postcodes.co.uk/v1/sign_up', {
  method: 'POST',
  headers: { 'Content-Type': 'application/json' },
  body: JSON.stringify({
    email: 'user@example.com',
    name: 'Jane Smith',
    org_name: 'Example Corp',
    org_address_line_one: '10 Example Street',
    org_post_town: 'London',
    org_postcode: 'SW1A 1AA',
    org_country_code: 'GB',
  }),
});

const { result } = await response.json();
```

**Python**

```python
import requests

response = requests.post(
    "https://api.ideal-postcodes.co.uk/v1/sign_up",
    json={
        "email": "user@example.com",
        "name": "Jane Smith",
        "org_name": "Example Corp",
        "org_address_line_one": "10 Example Street",
        "org_post_town": "London",
        "org_postcode": "SW1A 1AA",
        "org_country_code": "GB",
    },
)
result = response.json()["result"]
```

**Ruby**

```ruby
require "net/http"
require "json"

uri = URI("https://api.ideal-postcodes.co.uk/v1/sign_up")
body = {
  email: "user@example.com",
  name: "Jane Smith",
  org_name: "Example Corp",
  org_address_line_one: "10 Example Street",
  org_post_town: "London",
  org_postcode: "SW1A 1AA",
  org_country_code: "GB",
}
response = Net::HTTP.post(uri, body.to_json, "Content-Type" => "application/json")
result = JSON.parse(response.body)["result"]
```

**PHP**

```php
<?php
$ch = curl_init("https://api.ideal-postcodes.co.uk/v1/sign_up");
curl_setopt_array($ch, [
  CURLOPT_POST => true,
  CURLOPT_HTTPHEADER => ["Content-Type: application/json"],
  CURLOPT_POSTFIELDS => json_encode([
    "email" => "user@example.com",
    "name" => "Jane Smith",
    "org_name" => "Example Corp",
    "org_address_line_one" => "10 Example Street",
    "org_post_town" => "London",
    "org_postcode" => "SW1A 1AA",
    "org_country_code" => "GB",
  ]),
  CURLOPT_RETURNTRANSFER => true,
]);
$result = json_decode(curl_exec($ch), true)["result"];
```

## Example body

```json
{
  "email": "",
  "name": "",
  "org_name": "",
  "org_address_line_one": "",
  "org_address_line_two": "",
  "org_address_line_three": "",
  "org_post_town": "",
  "org_postcode": "",
  "org_country_code": ""
}
```

## Example response

**200 OK**

```json
{
  "code": 2000,
  "message": "Success",
  "result": {
    "cli_token": "",
    "signup_url": ""
  }
}
```

**400 Bad Request**

response.json

```json
{
  "code": 4000,
  "message": "Invalid Request"
}
```

## Request body

Send a JSON object with the following fields. Account holder and organisation details are required:

* `body` object

  | Field                    | Type            | Description                                     |
  | ------------------------ | --------------- | ----------------------------------------------- |
  | `email`                  | string required | Account holder's email address. Format: `email` |
  | `name`                   | string required | Account holder's full name.                     |
  | `org_name`               | string required | Organisation name.                              |
  | `org_address_line_one`   | string required |                                                 |
  | `org_address_line_two`   | string optional |                                                 |
  | `org_address_line_three` | string optional |                                                 |
  | `org_post_town`          | string required |                                                 |
  | `org_postcode`           | string required |                                                 |
  | `org_country_code`       | string required | ISO 3166-1 alpha-2 country code.                |

## Response

`result` contains a `cli_token` (for polling) and a `signup_url` (for the user to complete signup).

* `result` object

  * `cli_token` string

    Random URL-safe token (base64url). Used by the CLI to poll for credentials.

  * `signup_url` string

    Prefilled accounts web URL. The user opens this in a browser to complete signup.

    Format: `uri`

The `result` sits inside the standard `{ result, code, message }` envelope — see the [API reference](/docs/api/api-reference.md) for the wrapper format.

## Flow

1. CLI calls `POST /sign_up` with account holder and organisation details
2. API returns `cli_token` and `signup_url`
3. CLI directs user to open `signup_url` in browser
4. User completes captcha, accepts Terms of Service, and creates account
5. Rails propagates new user to the API
6. CLI polls `GET /sign_up/{cli_token}` until credentials are returned
7. Credentials are returned exactly once; subsequent polls return `410 Gone`
