Account API reference
Who the API key belongs to and how many credits are left.
Get the current API key's user and account
/api/v1/me- Read-only keys can call this
Returns the user and account the API key acts as, the environment (live or test) and
details of the key itself. Call it when setting up an integration to check you're using the
right key, or as a cheap health check for your stored credentials.
Request sample
curl https://app.signwith.co/api/v1/me \
-H "Authorization: Bearer $SIGNWITH_API_KEY"const response = await fetch('https://app.signwith.co/api/v1/me', {
headers: {
Authorization: `Bearer ${process.env.SIGNWITH_API_KEY}`,
},
})
console.log(response.status, await response.json())import os
import requests
response = requests.get(
"https://app.signwith.co/api/v1/me",
headers={
"Authorization": f"Bearer {os.environ['SIGNWITH_API_KEY']}",
},
)
print(response.status_code, response.json())Response 200
The key's user, account and environment. Returns a me object.
Example response: see the example object below.
Errors
| 401 | The API key is missing, invalid or expired, or its account has been archived. (unauthenticated, api_key_expired) |
| 429 | Rate limit exceeded (rate_limited, with Retry-After); more than 20 POST /feedback
messages in an hour (rate_limited, with Retry-After: seconds until the next clock hour); or — for
POST /signature_requests/{id}/remind — signers were reminded less than an hour ago
(remind_too_soon, with Retry-After). (rate_limited, remind_too_soon) |
| 500 | Something went wrong on SignWith's side. It's safe to retry with the same Idempotency-Key. (internal_error) |
Codes listed are the examples the spec gives; see all error codes.
Get the credit balance
/api/v1/credits- Read-only keys can call this
Returns how many credits the key's user has and whether they can send another document.
One credit per signed document: a document (template) uses a credit the first time it is
signed; sending the same document again doesn't use another. Check can_send before creating signature
requests in bulk so you can prompt users to top up instead of hitting 402 insufficient_credits.
Users on a lifetime plan have unlimited: true and available: null. To buy more credits
from the API see GET /credit_packs; purchase_url is the
equivalent page in the SignWith dashboard.
Request sample
curl https://app.signwith.co/api/v1/credits \
-H "Authorization: Bearer $SIGNWITH_API_KEY"const response = await fetch('https://app.signwith.co/api/v1/credits', {
headers: {
Authorization: `Bearer ${process.env.SIGNWITH_API_KEY}`,
},
})
console.log(response.status, await response.json())import os
import requests
response = requests.get(
"https://app.signwith.co/api/v1/credits",
headers={
"Authorization": f"Bearer {os.environ['SIGNWITH_API_KEY']}",
},
)
print(response.status_code, response.json())Response 200
The credit balance. Returns a credits object.
{
"object": "credits",
"unlimited": true,
"available": null,
"overdraft_limit": -3,
"can_send": true,
"billing": "One credit per signed document: a document (template) uses a credit the first time it is signed; sending the same document again doesn't use another.",
"purchase_url": "https://app.signwith.co/credit_plans"
}Example response: see the example object below.
Errors
| 401 | The API key is missing, invalid or expired, or its account has been archived. (unauthenticated, api_key_expired) |
| 429 | Rate limit exceeded (rate_limited, with Retry-After); more than 20 POST /feedback
messages in an hour (rate_limited, with Retry-After: seconds until the next clock hour); or — for
POST /signature_requests/{id}/remind — signers were reminded less than an hour ago
(remind_too_soon, with Retry-After). (rate_limited, remind_too_soon) |
| 500 | Something went wrong on SignWith's side. It's safe to retry with the same Idempotency-Key. (internal_error) |
Codes listed are the examples the spec gives; see all error codes.
The me object
objectstringRequiredAlwaysmeuserobjectRequiredA SignWith user (a member of your team).
3 child fields
idintegerRequiredemailstringRequiredemail addressnamestring or nullRequiredFirst and last name, or
nullif not set.
accountobjectRequired2 child fields
idintegerRequirednamestring or nullRequired
environmentstringRequiredtestfor keys issued from your test account (sw_test_), otherwiselive.One oflive,testapi_keyobjectRequired4 child fields
idintegerRequirednamestringRequiredThe name you gave the key, or
Default key.permissionstringRequiredreadkeys can only callGETendpoints,POST /documents/verifyandPOST /feedback.One offull,readexpires_atstring (date-time) or nullRequiredWhen the key stops working, or
nullif it never expires.
{
"object": "me",
"user": {
"id": 42,
"email": "[email protected]",
"name": "Ada Lovelace"
},
"account": {
"id": 7,
"name": "Acme Inc."
},
"environment": "live",
"api_key": {
"id": 118,
"name": "Production CRM",
"permission": "full",
"expires_at": null
}
}The credits object
objectstringRequiredAlwayscreditsunlimitedbooleanRequiredtruefor lifetime plans, which never run out of credits.availableinteger or nullRequiredCredits left. Can be slightly negative (see
overdraft_limit).nullwhenunlimited.overdraft_limitintegerRequiredHow far below zero the balance may go before sending is blocked.
can_sendbooleanRequiredWhether a signature request that needs a new credit can be sent right now.
billingstringRequiredPlain-language summary of how credits are used.
purchase_urlstringRequiredPage in the SignWith dashboard where the user can buy credits. To buy from the API instead, use
GET /credit_packsandPOST /checkouts.URL
{
"object": "credits",
"unlimited": false,
"available": 12,
"overdraft_limit": -3,
"can_send": true,
"billing": "One credit per signed document: a document (template) uses a credit the first time it is signed; sending the same document again doesn't use another.",
"purchase_url": "https://app.signwith.co/credit_plans"
}Base URL, pagination and idempotency work the same on every endpoint: see making requests. Every error code is on errors.
Start building
The API and MCP server come with every account. 3 free documents a month, then pay per document.