Waivers API
Digital waiver templates and electronic signature collection.
The Waivers API manages digital liability waivers. Define waiver templates with custom content, then collect electronic signatures from customers before or during their rental.
Test vs live API keys
REST API keys carry an environment: test or live (see prefixes like renta_sk_test_… / renta_sk_live_…). Waivers follow the same data lane split as the rest of your tenant data (is_demo on each row):
| Key environment | Data lane | Meaning |
|---|---|---|
test | Demo | Only templates and bookings with is_demo: true |
live | Live production | Only templates and bookings with is_demo: false |
List templates returns only templates in the key’s lane. Sign must use a waiver_template_id in that lane. If you pass booking_id, the booking must be in the same lane as the key; otherwise the API returns 403 (forbidden). Wrong-lane or unknown template IDs return 404 (not_found). Use test keys when exercising trial / sandbox bookings, and live keys for real post–go-live data.
After go-live, live-lane waiver templates often come from Migration Center (cloned from demo) or are created while your tenant is active so they are stamped is_demo: false. If GET /v1/waivers/templates with a live key returns an empty list, you may still have only demo-lane templates—clone or create live-lane templates first.
Waiver Types
| Type | Description |
|---|---|
single | One waiver per booking (covers all riders/participants) |
per_rider | Each participant signs individually |
List Waiver Templates
GET /v1/waivers/templatesReturns waiver templates for your tenant in the same data lane as your API key (see Test vs live API keys). Active templates only (unless using a secret key with active=false).
Query Parameters:
| Parameter | Type | Description |
|---|---|---|
active | boolean | Include inactive templates (secret key only) |
cursor | string | Pagination cursor |
limit | integer | Results per page (1–100, default 20) |
const templates = await renta.waivers.templates();
for (const t of templates.data) {
console.log(`${t.name} (${t.type}) — is_demo: ${t.is_demo}`);
}# Live key → live-lane templates only
curl https://api.getrenta.io/v1/waivers/templates \
-H "Authorization: Bearer renta_sk_live_..."
# Test key → demo-lane templates only
curl https://api.getrenta.io/v1/waivers/templates \
-H "Authorization: Bearer renta_sk_test_..."Response:
Each template includes is_demo: true for the demo lane (test keys) and false for the live lane (live keys).
{
"data": [
{
"id": "wt_liability",
"name": "Liability Waiver",
"content": "<h2>Release of Liability</h2><p>By signing this waiver...</p>",
"type": "per_rider",
"expiration_days": 365,
"active": true,
"is_demo": false
}
],
"has_more": false,
"next_cursor": null
}Sign Waiver
POST /v1/waivers/signSubmit a signed waiver. Works with both secret and publishable keys. The waiver_template_id must belong to the same lane as your API key (Test vs live API keys). When booking_id is supplied, the booking must be in that lane too (403 if you mix a live booking with a test key, or vice versa).
Body Parameters:
| Parameter | Type | Required | Description |
|---|---|---|---|
booking_id | string | — | Associated booking (optional; required to match key lane when set) |
waiver_template_id | string | ✅ | Template to sign (must exist in your tenant and in the key’s lane) |
signer_name | string | ✅ | Full legal name of signer |
signer_email | string | — | Signer's email |
signature_data | object | ✅ | Signature data (see below) |
Signature Data Format
// Typed signature
{ type: 'typed', value: 'John Doe' }
// Drawn signature (base64 image)
{ type: 'drawn', value: 'data:image/png;base64,...' }const result = await renta.waivers.sign({
booking_id: 'bk_def456',
waiver_template_id: 'wt_liability',
signer_name: 'John Doe',
signature_data: { type: 'typed', value: 'John Doe' },
});
console.log(`Waiver ID: ${result.waiver_id}`);
console.log(`PDF: ${result.pdf_url}`);curl -X POST https://api.getrenta.io/v1/waivers/sign \
-H "Authorization: Bearer renta_sk_live_..." \
-H "Content-Type: application/json" \
-d '{
"booking_id": "bk_def456",
"waiver_template_id": "wt_liability",
"signer_name": "John Doe",
"signature_data": {
"type": "typed",
"value": "John Doe"
}
}'Response (201 Created):
{
"success": true,
"waiver_id": "w_abc123",
"pdf_url": "https://storage.getrenta.io/waivers/w_abc123.pdf"
}Errors:
| Status | When |
|---|---|
| 404 | Booking or template not found (including wrong-lane template so it is not visible to your key) |
| 403 | booking_id is present but its lane does not match the API key environment |
Check Waiver Status
GET /v1/waivers/status/:booking_idCheck which waivers have been signed for a booking.
const status = await renta.waivers.status('bk_def456');
console.log(`All signed: ${status.all_signed}`);
for (const w of status.waivers) {
console.log(`${w.signer_name}: ${w.signed ? '✅' : '❌'}`);
}curl https://api.getrenta.io/v1/waivers/status/bk_def456 \
-H "Authorization: Bearer renta_sk_live_..."Signed waivers are stored as PDFs in Supabase Storage. The PDF URL is valid for 1 hour. Request a fresh URL by calling the status endpoint again.