{"openapi":"3.1.0","info":{"title":"Servicebay API","description":"The Servicebay API provides programmatic access to your organisation's data including \ncustomers, tickets, and calendar events.\n\n## Authentication\n\nAll API requests require authentication using an API key. Include your API key in the \n`X-API-Key` header with every request:\n\n```\nX-API-Key: sk_live_your_api_key_here\n```\n\nAPI keys are scoped to a single organisation. You can create and manage API keys from \nthe [Developer Dashboard](/develop).\n\n## Rate Limiting\n\nAPI requests are rate limited to **100 requests per minute** per API key. Rate limit \ninformation is included in response headers:\n\n- `X-RateLimit-Limit`: Maximum requests per minute\n- `X-RateLimit-Remaining`: Remaining requests in the current window\n- `X-RateLimit-Reset`: Unix timestamp when the rate limit resets\n\n## Errors\n\nThe API uses standard HTTP status codes to indicate success or failure:\n\n| Status Code | Description |\n|-------------|-------------|\n| 200 | Success |\n| 201 | Created |\n| 400 | Bad Request - Invalid parameters |\n| 401 | Unauthorized - Invalid or missing API key |\n| 403 | Forbidden - No access to this resource, insufficient OAuth scope, or organisation is not on an active Pro subscription |\n| 404 | Not Found |\n| 409 | Conflict - e.g. a second calendar event for a ticket that already has one |\n| 429 | Too Many Requests - Rate limit exceeded |\n| 500 | Internal Server Error |\n\n### Pro subscription required\n\nThe API (and the developer portal) is a **Pro** feature. Requests for an\norganisation without an active Pro subscription (`subscriptionStatus` in\n`active` / `trialing` / `past_due` **and** `subscriptionTier === 'pro'`)\nreturn **403** with:\n\n```json\n{\n  \"success\": false,\n  \"error\": \"This organisation does not have an active Pro subscription. Upgrade to Pro to use the Servicebay API.\"\n}\n```\n","version":"1.0.0","contact":{"name":"Servicebay Support","url":"https://servicebay.io/support","email":"support@servicebay.io"}},"servers":[{"url":"https://developer.servicebay.io/api/v1","description":"Production API"},{"url":"http://localhost:3000/api/v1","description":"Local development"}],"security":[{"apiKey":[]},{"oauth2":[]}],"tags":[{"name":"Organisations","description":"Organisation management endpoints"},{"name":"Customers","description":"Customer management and lookup endpoints"},{"name":"Tickets","description":"Service jobs (a.k.a. tickets) — create, schedule, and update jobs"},{"name":"Services","description":"Reusable service templates (pricing, warranty defaults)"},{"name":"Inventory","description":"Stock items and parts catalogue"},{"name":"Quotes","description":"Customer quotes"},{"name":"Invoices","description":"Customer invoices"},{"name":"Calendar Events","description":"Calendar events — standalone or linked to a job"},{"name":"Devices","description":"Customer devices/assets (subcollection of a customer)"},{"name":"Payments","description":"Payments and refunds recorded against invoices"},{"name":"Stations","description":"Workstations/bays that jobs can be assigned to"},{"name":"Tax Rates","description":"Tax rates used on services, inventory, quotes, and invoices"},{"name":"Job Statuses","description":"Configurable job status values (a.k.a. ticket statuses)"},{"name":"API Keys","description":"API key management (requires Firebase Auth)"}],"paths":{"/organisations/{orgId}":{"get":{"tags":["Organisations"],"summary":"Get organisation details","description":"Retrieve details for the organisation associated with your API key.","operationId":"getOrganisation","parameters":[{"$ref":"#/components/parameters/orgId"}],"responses":{"200":{"description":"Organisation details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrganisationResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Organisations"],"summary":"Update organisation","description":"Update organisation details.","operationId":"updateOrganisation","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrganisationUpdate"}}}},"responses":{"200":{"description":"Updated organisation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrganisationResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/customers":{"get":{"tags":["Customers"],"summary":"List customers","description":"Retrieve a paginated list of customers for the organisation.","operationId":"listCustomers","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"search","in":"query","description":"Search customers by name, email, or business name","schema":{"type":"string"}}],"responses":{"200":{"description":"List of customers","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Customers"],"summary":"Create customer","description":"Create a new customer in the organisation.","operationId":"createCustomer","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerCreate"},"example":{"firstName":"John","lastName":"Doe","email":"john.doe@example.com","phone":"+1234567890","businessName":"Acme Corp"}}}},"responses":{"201":{"description":"Created customer","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/customers/lookup":{"get":{"tags":["Customers"],"summary":"Look up customer by phone or email","description":"Server-side exact-match customer lookup. Provide `phone`, `email`, or\nboth. Returns up to 10 matches per identifier (deduplicated). Designed\nfor customer-facing intake forms that need to find an existing record\nbefore booking a job.\n\nReturns `404` when no customer matches.\n","operationId":"lookupCustomer","parameters":[{"$ref":"#/components/parameters/orgId"},{"name":"phone","in":"query","description":"Exact phone number to match","schema":{"type":"string"}},{"name":"email","in":"query","description":"Exact email address to match","schema":{"type":"string","format":"email"}}],"responses":{"200":{"description":"One or more matching customers","content":{"application/json":{"schema":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"matches":{"type":"array","items":{"$ref":"#/components/schemas/Customer"}},"count":{"type":"integer"}}}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/customers/{customerId}":{"get":{"tags":["Customers"],"summary":"Get customer","description":"Retrieve a specific customer by ID.","operationId":"getCustomer","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"}],"responses":{"200":{"description":"Customer details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Customers"],"summary":"Update customer","description":"Update an existing customer.","operationId":"updateCustomer","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerUpdate"}}}},"responses":{"200":{"description":"Updated customer","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CustomerResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Customers"],"summary":"Delete customer","description":"Delete a customer from the organisation.","operationId":"deleteCustomer","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"}],"responses":{"200":{"description":"Customer deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/calendar-events":{"get":{"tags":["Calendar Events"],"summary":"List calendar events","description":"Retrieve a paginated list of calendar events.","operationId":"listCalendarEvents","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"from","in":"query","description":"Filter events starting from this date (ISO 8601)","schema":{"type":"string","format":"date-time"}},{"name":"to","in":"query","description":"Filter events ending before this date (ISO 8601)","schema":{"type":"string","format":"date-time"}},{"name":"assignedToId","in":"query","description":"Filter by assigned user ID","schema":{"type":"string"}},{"name":"ticketId","in":"query","description":"Filter by associated ticket ID","schema":{"type":"string"}}],"responses":{"200":{"description":"List of calendar events","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarEventListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Calendar Events"],"summary":"Create calendar event","description":"Create a new calendar event. If `ticketId` is set, the ticket must not\nalready have a linked event (one event per job — prefer the jobs API\nfor schedule changes). A conflict returns **409**.\n","operationId":"createCalendarEvent","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarEventCreate"},"example":{"title":"Service Appointment","from":"2025-01-15T10:00:00Z","to":"2025-01-15T11:00:00Z","allDay":false,"assignedToId":"user123","ticketId":"1"}}}},"responses":{"201":{"description":"Created calendar event","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarEventResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"409":{"$ref":"#/components/responses/Conflict"}}}},"/organisations/{orgId}/calendar-events/{eventId}":{"get":{"tags":["Calendar Events"],"summary":"Get calendar event","description":"Retrieve a specific calendar event by ID.","operationId":"getCalendarEvent","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/eventId"}],"responses":{"200":{"description":"Calendar event details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarEventResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Calendar Events"],"summary":"Update calendar event","description":"Update an existing calendar event. Re-linking to a `ticketId` that\nalready has a different event returns **409**.\n","operationId":"updateCalendarEvent","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/eventId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarEventUpdate"}}}},"responses":{"200":{"description":"Updated calendar event","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CalendarEventResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}},"delete":{"tags":["Calendar Events"],"summary":"Delete calendar event","description":"Delete a calendar event.","operationId":"deleteCalendarEvent","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/eventId"}],"responses":{"200":{"description":"Calendar event deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/tickets":{"get":{"tags":["Tickets"],"summary":"List tickets","description":"Retrieve a paginated list of tickets.","operationId":"listTickets","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"status","in":"query","description":"Filter by ticket status","schema":{"type":"string","enum":["Open","In Progress","Closed"]}},{"name":"customerId","in":"query","description":"Filter by customer ID","schema":{"type":"string"}},{"name":"assignedTechnician","in":"query","description":"Filter by assigned technician ID","schema":{"type":"string"}}],"responses":{"200":{"description":"List of tickets","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Tickets"],"summary":"Create ticket","description":"Create a new service ticket.","operationId":"createTicket","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketCreate"},"example":{"customerId":"customer123","customerName":"John Doe","customerEmail":"john@example.com","serviceRequired":"Device Repair","status":"Open"}}}},"responses":{"201":{"description":"Created ticket","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/tickets/{ticketId}":{"get":{"tags":["Tickets"],"summary":"Get ticket","description":"Retrieve a specific ticket by ID.","operationId":"getTicket","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/ticketId"}],"responses":{"200":{"description":"Ticket details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Tickets"],"summary":"Update ticket","description":"Update an existing ticket.","operationId":"updateTicket","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/ticketId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketUpdate"}}}},"responses":{"200":{"description":"Updated ticket","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Tickets"],"summary":"Delete ticket","description":"Delete a ticket.","operationId":"deleteTicket","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/ticketId"}],"responses":{"200":{"description":"Ticket deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/services":{"get":{"tags":["Services"],"summary":"List services","description":"Retrieve a paginated list of service templates.","operationId":"listServices","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"search","in":"query","schema":{"type":"string"}}],"responses":{"200":{"description":"List of services","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ServiceListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Services"],"summary":"Create service","operationId":"createService","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ServiceCreate"}}}},"responses":{"201":{"description":"Created service","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ServiceResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/services/{serviceId}":{"parameters":[{"$ref":"#/components/parameters/orgId"},{"name":"serviceId","in":"path","required":true,"schema":{"type":"string"}}],"get":{"tags":["Services"],"summary":"Get service","operationId":"getService","responses":{"200":{"description":"Service details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ServiceResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Services"],"summary":"Update service","operationId":"updateService","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ServiceUpdate"}}}},"responses":{"200":{"description":"Updated service","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ServiceResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Services"],"summary":"Delete service","operationId":"deleteService","responses":{"200":{"description":"Service deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/inventory":{"get":{"tags":["Inventory"],"summary":"List inventory items","operationId":"listInventory","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"categoryId","in":"query","schema":{"type":"string"}},{"name":"sku","in":"query","description":"Exact SKU lookup","schema":{"type":"string"}},{"name":"search","in":"query","schema":{"type":"string"}}],"responses":{"200":{"description":"List of inventory items","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InventoryListResponse"}}}}}},"post":{"tags":["Inventory"],"summary":"Create inventory item","operationId":"createInventoryItem","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InventoryItemCreate"}}}},"responses":{"201":{"description":"Created inventory item","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InventoryItemResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"}}}},"/organisations/{orgId}/inventory/{itemId}":{"parameters":[{"$ref":"#/components/parameters/orgId"},{"name":"itemId","in":"path","required":true,"schema":{"type":"string"}}],"get":{"tags":["Inventory"],"summary":"Get inventory item","operationId":"getInventoryItem","responses":{"200":{"description":"Inventory item details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InventoryItemResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Inventory"],"summary":"Update inventory item","operationId":"updateInventoryItem","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InventoryItemUpdate"}}}},"responses":{"200":{"description":"Updated inventory item","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InventoryItemResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Inventory"],"summary":"Delete inventory item","operationId":"deleteInventoryItem","responses":{"200":{"description":"Inventory item deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/quotes":{"get":{"tags":["Quotes"],"summary":"List quotes","operationId":"listQuotes","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"customerId","in":"query","schema":{"type":"string"}},{"name":"ticketId","in":"query","schema":{"type":"string"}},{"name":"accepted","in":"query","schema":{"type":"boolean"}}],"responses":{"200":{"description":"List of quotes","content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteListResponse"}}}}}},"post":{"tags":["Quotes"],"summary":"Create quote","operationId":"createQuote","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteCreate"}}}},"responses":{"201":{"description":"Created quote","content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"}}}},"/organisations/{orgId}/quotes/{quoteId}":{"parameters":[{"$ref":"#/components/parameters/orgId"},{"name":"quoteId","in":"path","required":true,"schema":{"type":"string"}}],"get":{"tags":["Quotes"],"summary":"Get quote","operationId":"getQuote","responses":{"200":{"description":"Quote details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Quotes"],"summary":"Update quote","operationId":"updateQuote","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteUpdate"}}}},"responses":{"200":{"description":"Updated quote","content":{"application/json":{"schema":{"$ref":"#/components/schemas/QuoteResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Quotes"],"summary":"Delete quote","operationId":"deleteQuote","responses":{"200":{"description":"Quote deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/invoices":{"get":{"tags":["Invoices"],"summary":"List invoices","operationId":"listInvoices","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"customerId","in":"query","schema":{"type":"string"}},{"name":"ticketId","in":"query","schema":{"type":"string"}},{"name":"paid","in":"query","schema":{"type":"boolean"}}],"responses":{"200":{"description":"List of invoices","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvoiceListResponse"}}}}}},"post":{"tags":["Invoices"],"summary":"Create invoice","operationId":"createInvoice","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvoiceCreate"}}}},"responses":{"201":{"description":"Created invoice","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvoiceResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"}}}},"/organisations/{orgId}/invoices/{invoiceId}":{"parameters":[{"$ref":"#/components/parameters/orgId"},{"name":"invoiceId","in":"path","required":true,"schema":{"type":"string"}}],"get":{"tags":["Invoices"],"summary":"Get invoice","operationId":"getInvoice","responses":{"200":{"description":"Invoice details","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvoiceResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Invoices"],"summary":"Update invoice","operationId":"updateInvoice","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvoiceUpdate"}}}},"responses":{"200":{"description":"Updated invoice","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InvoiceResponse"}}}},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Invoices"],"summary":"Delete invoice","operationId":"deleteInvoice","responses":{"200":{"description":"Invoice deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/customers/{customerId}/devices":{"get":{"tags":["Devices"],"summary":"List customer devices","description":"List the devices/assets belonging to a customer, newest first.","operationId":"listDevices","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"}],"responses":{"200":{"description":"List of devices","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"post":{"tags":["Devices"],"summary":"Create customer device","description":"Add a device/asset to a customer.","operationId":"createDevice","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceCreate"},"example":{"type":"Laptop","brand":"Dell","make":"XPS","model":"13 9310","identifier":"SN-12345"}}}},"responses":{"201":{"description":"Created device","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/customers/{customerId}/devices/{deviceId}":{"get":{"tags":["Devices"],"summary":"Get customer device","operationId":"getDevice","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"},{"$ref":"#/components/parameters/deviceId"}],"responses":{"200":{"description":"Device","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Devices"],"summary":"Update customer device","description":"Update a device. Changes to the type/name are propagated to any job\nthat references this device (the denormalised `customerDeviceType` /\n`customerDeviceName` fields).\n","operationId":"updateDevice","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"},{"$ref":"#/components/parameters/deviceId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceUpdate"}}}},"responses":{"200":{"description":"Updated device","content":{"application/json":{"schema":{"$ref":"#/components/schemas/DeviceResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Devices"],"summary":"Delete customer device","description":"Delete a device. The `deviceId` reference is cleared from any job that used it.","operationId":"deleteDevice","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/customerId"},{"$ref":"#/components/parameters/deviceId"}],"responses":{"200":{"description":"Device deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/payments":{"get":{"tags":["Payments"],"summary":"List payments","description":"List payments, optionally filtered by invoice, newest first.","operationId":"listPayments","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/limit"},{"$ref":"#/components/parameters/startAfter"},{"name":"invoiceId","in":"query","description":"Only return payments for this invoice","schema":{"type":"string"}}],"responses":{"200":{"description":"List of payments","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PaymentListResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Payments"],"summary":"Record a payment","description":"Record a payment (or a refund, using a negative `amount`) against an\ninvoice. The invoice's paid/deposit/balance flags are recalculated\nautomatically. The referenced invoice must exist.\n","operationId":"createPayment","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PaymentCreate"},"example":{"invoiceId":"abc123","amount":150,"paymentMethod":"card","notes":"Paid in full"}}}},"responses":{"201":{"description":"Created payment","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PaymentResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/payments/{paymentId}":{"get":{"tags":["Payments"],"summary":"Get payment","operationId":"getPayment","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/paymentId"}],"responses":{"200":{"description":"Payment","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PaymentResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Payments"],"summary":"Update payment","description":"Update a manual payment. The parent invoice's paid status is\nrecalculated. Payments linked to Stripe cannot be modified (`409`).\n","operationId":"updatePayment","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/paymentId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PaymentUpdate"}}}},"responses":{"200":{"description":"Updated payment","content":{"application/json":{"schema":{"$ref":"#/components/schemas/PaymentResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}},"delete":{"tags":["Payments"],"summary":"Delete payment","description":"Delete a manual payment. The parent invoice's paid status is\nrecalculated. Payments linked to Stripe cannot be deleted (`409`).\n","operationId":"deletePayment","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/paymentId"}],"responses":{"200":{"description":"Payment deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}}},"/organisations/{orgId}/stations":{"get":{"tags":["Stations"],"summary":"List stations","operationId":"listStations","parameters":[{"$ref":"#/components/parameters/orgId"}],"responses":{"200":{"description":"List of stations","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StationListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Stations"],"summary":"Create station","operationId":"createStation","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StationCreate"},"example":{"name":"Bench 1","index":0,"capacity":1}}}},"responses":{"201":{"description":"Created station","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StationResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/stations/{stationId}":{"get":{"tags":["Stations"],"summary":"Get station","operationId":"getStation","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/stationId"}],"responses":{"200":{"description":"Station","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StationResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Stations"],"summary":"Update station","operationId":"updateStation","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/stationId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/StationUpdate"}}}},"responses":{"200":{"description":"Updated station","content":{"application/json":{"schema":{"$ref":"#/components/schemas/StationResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Stations"],"summary":"Delete station","description":"Delete a station. Blocked (`409`) while any active (non-closed) job is assigned to it.","operationId":"deleteStation","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/stationId"}],"responses":{"200":{"description":"Station deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}}},"/organisations/{orgId}/tax-rates":{"get":{"tags":["Tax Rates"],"summary":"List tax rates","operationId":"listTaxRates","parameters":[{"$ref":"#/components/parameters/orgId"}],"responses":{"200":{"description":"List of tax rates","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaxRateListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Tax Rates"],"summary":"Create tax rate","description":"Create a tax rate. Setting `defaultEnabled` clears the default flag on all other rates.","operationId":"createTaxRate","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaxRateCreate"},"example":{"name":"GST","rate":10,"isInclusive":false,"defaultEnabled":true}}}},"responses":{"201":{"description":"Created tax rate","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaxRateResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/tax-rates/{taxRateId}":{"get":{"tags":["Tax Rates"],"summary":"Get tax rate","operationId":"getTaxRate","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/taxRateId"}],"responses":{"200":{"description":"Tax rate","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaxRateResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Tax Rates"],"summary":"Update tax rate","description":"Update a tax rate. Setting `defaultEnabled` clears the default flag on all other rates.","operationId":"updateTaxRate","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/taxRateId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaxRateUpdate"}}}},"responses":{"200":{"description":"Updated tax rate","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TaxRateResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Tax Rates"],"summary":"Delete tax rate","operationId":"deleteTaxRate","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/taxRateId"}],"responses":{"200":{"description":"Tax rate deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/organisations/{orgId}/ticket-statuses":{"get":{"tags":["Job Statuses"],"summary":"List job statuses","operationId":"listTicketStatuses","parameters":[{"$ref":"#/components/parameters/orgId"}],"responses":{"200":{"description":"List of job statuses","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketStatusListResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Job Statuses"],"summary":"Create job status","description":"Create a custom job status. API-created statuses are always `type: custom`.","operationId":"createTicketStatus","parameters":[{"$ref":"#/components/parameters/orgId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketStatusCreate"},"example":{"name":"Awaiting Parts","color":4283215696,"index":4}}}},"responses":{"201":{"description":"Created job status","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketStatusResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/organisations/{orgId}/ticket-statuses/{statusId}":{"get":{"tags":["Job Statuses"],"summary":"Get job status","operationId":"getTicketStatus","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/statusId"}],"responses":{"200":{"description":"Job status","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketStatusResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Job Statuses"],"summary":"Update job status","description":"Update a job status. `type` cannot be changed via the API.","operationId":"updateTicketStatus","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/statusId"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketStatusUpdate"}}}},"responses":{"200":{"description":"Updated job status","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TicketStatusResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Job Statuses"],"summary":"Delete job status","description":"Delete a custom job status. Built-in (`type: default`) statuses\ncannot be deleted (`400`), and a status in use by any job cannot be\ndeleted (`409`).\n","operationId":"deleteTicketStatus","parameters":[{"$ref":"#/components/parameters/orgId"},{"$ref":"#/components/parameters/statusId"}],"responses":{"200":{"description":"Job status deleted","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SuccessMessage"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}}}},"components":{"securitySchemes":{"apiKey":{"type":"apiKey","in":"header","name":"X-API-Key","description":"API key for authentication. Get your key from the Developer Dashboard."},"bearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"JWT","description":"Firebase ID token for dashboard authentication"},"oauth2":{"type":"oauth2","description":"OAuth 2.1 authorization-code flow with PKCE (S256, required). Tokens are bound to one organisation, chosen by the user at consent. GET endpoints require the entity's `:read` scope; POST/PUT/DELETE require `:write` (which implies `:read`). See /docs/oauth.","flows":{"authorizationCode":{"authorizationUrl":"https://oauth.servicebay.io/authorize","tokenUrl":"https://oauth.servicebay.io/token","refreshUrl":"https://oauth.servicebay.io/token","scopes":{"organisation:read":"Read the organisation profile","organisation:write":"Read and write the organisation profile","tickets:read":"Read jobs (tickets)","tickets:write":"Read and write jobs (tickets)","customers:read":"Read customers","customers:write":"Read and write customers","devices:read":"Read customer devices","devices:write":"Read and write customer devices","services:read":"Read services","services:write":"Read and write services","inventory:read":"Read inventory","inventory:write":"Read and write inventory","quotes:read":"Read quotes","quotes:write":"Read and write quotes","invoices:read":"Read invoices","invoices:write":"Read and write invoices","payments:read":"Read payments","payments:write":"Read and write payments","calendar:read":"Read calendar events","calendar:write":"Read and write calendar events","stations:read":"Read stations","stations:write":"Read and write stations","tax-rates:read":"Read tax rates","tax-rates:write":"Read and write tax rates","ticket-statuses:read":"Read job status values","ticket-statuses:write":"Read and write job status values","read":"Read all data in the organisation","write":"Read and write all data in the organisation"}}}}},"parameters":{"orgId":{"name":"orgId","in":"path","required":true,"description":"Organisation ID","schema":{"type":"string"}},"customerId":{"name":"customerId","in":"path","required":true,"description":"Customer ID","schema":{"type":"string"}},"eventId":{"name":"eventId","in":"path","required":true,"description":"Calendar event ID","schema":{"type":"string"}},"ticketId":{"name":"ticketId","in":"path","required":true,"description":"Ticket ID","schema":{"type":"string"}},"deviceId":{"name":"deviceId","in":"path","required":true,"description":"Customer device ID","schema":{"type":"string"}},"paymentId":{"name":"paymentId","in":"path","required":true,"description":"Payment ID","schema":{"type":"string"}},"stationId":{"name":"stationId","in":"path","required":true,"description":"Station ID","schema":{"type":"string"}},"taxRateId":{"name":"taxRateId","in":"path","required":true,"description":"Tax rate ID","schema":{"type":"string"}},"statusId":{"name":"statusId","in":"path","required":true,"description":"Job status ID","schema":{"type":"string"}},"limit":{"name":"limit","in":"query","description":"Maximum number of items to return (max 100)","schema":{"type":"integer","minimum":1,"maximum":100,"default":50}},"startAfter":{"name":"startAfter","in":"query","description":"Cursor for pagination - ID of the last item from previous page","schema":{"type":"string"}}},"responses":{"BadRequest":{"description":"Bad Request - Invalid parameters","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"Unauthorized":{"description":"Unauthorized - Invalid or missing API key","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"Forbidden":{"description":"Forbidden — one of:\n- API key / token is valid but not scoped to this organisation\n- OAuth grant lacks the required `entity:action` scope\n- Organisation is not on an active Pro subscription (see error body)\n","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"},"examples":{"wrongOrg":{"summary":"Cross-organisation access","value":{"success":false,"error":"You do not have access to this organisation"}},"insufficientScope":{"summary":"OAuth missing scope","value":{"success":false,"error":"Insufficient scope. This request requires 'invoices:write'."}},"proRequired":{"summary":"Pro subscription required","value":{"success":false,"error":"This organisation does not have an active Pro subscription. Upgrade to Pro to use the Servicebay API."}}}}}},"NotFound":{"description":"Not Found","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"RateLimitExceeded":{"description":"Too Many Requests - Rate limit exceeded","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"Conflict":{"description":"Conflict - The request could not be completed because the resource is in use or managed elsewhere","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"schemas":{"Error":{"type":"object","required":["success","error"],"properties":{"success":{"type":"boolean","example":false},"error":{"type":"string","example":"An error occurred"}}},"SuccessMessage":{"type":"object","required":["success","data"],"properties":{"success":{"type":"boolean","example":true},"data":{"type":"object","properties":{"message":{"type":"string","example":"Operation completed successfully"}}}}},"Pagination":{"type":"object","properties":{"limit":{"type":"integer"},"hasMore":{"type":"boolean"},"nextCursor":{"type":"string","nullable":true}}},"Organisation":{"type":"object","description":"Organisation profile. Note: the `members` map and `teamAccessCode` field\nare persisted in Firestore but deliberately stripped from API responses\nfor privacy — they do not appear here.\n","properties":{"id":{"type":"string"},"name":{"type":"string"},"email":{"type":"string","format":"email"},"phone":{"type":"string"},"phoneCountryCode":{"type":"string","description":"ISO country code for the phone number (e.g. `AU`)."},"phoneCountryDialCode":{"type":"string","description":"International dial code for the phone number (e.g. `+61`)."},"website":{"type":"string","format":"uri"},"addressLine1":{"type":"string"},"addressLine2":{"type":"string"},"city":{"type":"string"},"state":{"type":"string"},"zip":{"type":"string"},"country":{"type":"string"},"noPhysicalLocation":{"type":"boolean","description":"Set when the organisation has no physical premises (e.g. mobile-only operators)."},"taxId":{"type":"string"},"taxIdLabel":{"type":"string","description":"Label shown alongside `taxId` on invoices and quotes (e.g. `ABN`, `VAT`)."},"registrationNumber":{"type":"string"},"registrationNumberLabel":{"type":"string","description":"Label shown alongside `registrationNumber` (e.g. `ACN`, `Company No.`)."},"defaultInvoiceMessage":{"type":"string","description":"Default message prefilled on new invoices."},"defaultInvoicePaymentAdvice":{"type":"string","description":"Default payment advice prefilled on new invoices."},"defaultInvoiceTerms":{"type":"string","description":"Default terms prefilled on new invoices."},"defaultQuoteMessage":{"type":"string","description":"Default message prefilled on new quotes."},"defaultQuoteTerms":{"type":"string","description":"Default terms prefilled on new quotes."},"termsOfServiceDocument":{"type":"string","description":"URL or path to the organisation-level terms of service document."},"userTermsOfServiceDocument":{"type":"string","description":"URL or path to a user-specific terms of service document."},"defaultInvoiceRemindersEnabled":{"type":"boolean","description":"Whether new invoices default to having payment reminders enabled."},"defaultInvoiceReminders":{"type":"array","description":"Default set of invoice payment reminders applied to new invoices.","items":{"type":"object","additionalProperties":true}},"stripeDefaultCurrency":{"type":"string","description":"Read-only. Default 3-letter ISO currency for Stripe customer payments."},"onboardingComplete":{"type":"boolean","description":"Read-only. Whether the organisation has finished onboarding."},"customerAssetLabel":{"type":"string","description":"Read-only. Label the organisation uses for a customer's devices/assets."},"createdAt":{"type":"string","format":"date-time"}}},"OrganisationUpdate":{"type":"object","properties":{"name":{"type":"string"},"email":{"type":"string","format":"email"},"phone":{"type":"string"},"phoneCountryCode":{"type":"string"},"phoneCountryDialCode":{"type":"string"},"website":{"type":"string"},"addressLine1":{"type":"string"},"addressLine2":{"type":"string"},"city":{"type":"string"},"state":{"type":"string"},"zip":{"type":"string"},"country":{"type":"string"},"noPhysicalLocation":{"type":"boolean"},"taxId":{"type":"string"},"taxIdLabel":{"type":"string"},"registrationNumber":{"type":"string"},"registrationNumberLabel":{"type":"string"},"defaultInvoiceMessage":{"type":"string"},"defaultInvoicePaymentAdvice":{"type":"string"},"defaultInvoiceTerms":{"type":"string"},"defaultQuoteMessage":{"type":"string"},"defaultQuoteTerms":{"type":"string"},"termsOfServiceDocument":{"type":"string"},"userTermsOfServiceDocument":{"type":"string"},"defaultInvoiceRemindersEnabled":{"type":"boolean"},"defaultInvoiceReminders":{"type":"array","items":{"type":"object","additionalProperties":true}}}},"OrganisationResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Organisation"}}},"Customer":{"type":"object","properties":{"id":{"type":"string"},"firstName":{"type":"string"},"lastName":{"type":"string"},"email":{"type":"string","format":"email"},"phone":{"type":"string"},"secondaryPhone":{"type":"string"},"businessName":{"type":"string"},"businessTaxId":{"type":"string"},"addressLine1":{"type":"string"},"addressLine2":{"type":"string"},"city":{"type":"string"},"state":{"type":"string"},"zip":{"type":"string"},"country":{"type":"string"},"latitude":{"type":"number"},"longitude":{"type":"number"},"notes":{"type":"string"},"customerType":{"type":"string"},"preferredContactMethod":{"type":"string"},"createdAt":{"type":"string","format":"date-time"}}},"CustomerCreate":{"type":"object","required":["firstName","lastName","email"],"properties":{"firstName":{"type":"string"},"lastName":{"type":"string"},"email":{"type":"string","format":"email"},"phone":{"type":"string"},"secondaryPhone":{"type":"string"},"businessName":{"type":"string"},"businessTaxId":{"type":"string"},"addressLine1":{"type":"string"},"addressLine2":{"type":"string"},"city":{"type":"string"},"state":{"type":"string"},"zip":{"type":"string"},"country":{"type":"string"},"latitude":{"type":"number"},"longitude":{"type":"number"},"notes":{"type":"string"},"customerType":{"type":"string"},"preferredContactMethod":{"type":"string"}}},"CustomerUpdate":{"type":"object","properties":{"firstName":{"type":"string"},"lastName":{"type":"string"},"email":{"type":"string","format":"email"},"phone":{"type":"string"},"secondaryPhone":{"type":"string"},"businessName":{"type":"string"},"businessTaxId":{"type":"string"},"addressLine1":{"type":"string"},"addressLine2":{"type":"string"},"city":{"type":"string"},"state":{"type":"string"},"zip":{"type":"string"},"country":{"type":"string"},"latitude":{"type":"number"},"longitude":{"type":"number"},"notes":{"type":"string"},"customerType":{"type":"string"},"preferredContactMethod":{"type":"string"}}},"CustomerResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Customer"}}},"CustomerListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"customers":{"type":"array","items":{"$ref":"#/components/schemas/Customer"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"CalendarEvent":{"type":"object","properties":{"id":{"type":"string"},"title":{"type":"string"},"description":{"type":"string"},"notes":{"type":"string"},"from":{"type":"string","format":"date-time"},"to":{"type":"string","format":"date-time"},"allDay":{"type":"boolean"},"assignedTo":{"type":"string"},"assignedToId":{"type":"string"},"ticketId":{"type":"string"},"ticketLocation":{"type":"string"},"color":{"type":"integer"}}},"CalendarEventCreate":{"type":"object","required":["title","from","to"],"properties":{"title":{"type":"string"},"description":{"type":"string"},"notes":{"type":"string"},"from":{"type":"string","format":"date-time"},"to":{"type":"string","format":"date-time"},"allDay":{"type":"boolean","default":false},"assignedTo":{"type":"string"},"assignedToId":{"type":"string"},"ticketId":{"type":"string"},"ticketLocation":{"type":"string"},"color":{"type":"integer"}}},"CalendarEventUpdate":{"type":"object","properties":{"title":{"type":"string"},"description":{"type":"string"},"notes":{"type":"string"},"from":{"type":"string","format":"date-time"},"to":{"type":"string","format":"date-time"},"allDay":{"type":"boolean"},"assignedTo":{"type":"string"},"assignedToId":{"type":"string"},"ticketId":{"type":"string"},"ticketLocation":{"type":"string"},"color":{"type":"integer"}}},"CalendarEventResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/CalendarEvent"}}},"CalendarEventListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"events":{"type":"array","items":{"$ref":"#/components/schemas/CalendarEvent"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"Ticket":{"type":"object","properties":{"id":{"type":"string"},"ticketId":{"type":"integer","description":"Sequential numeric job/ticket ID, auto-assigned on create."},"status":{"type":"string","description":"Free-form status string. The Servicebay app commonly uses\n`Open`, `In Progress`, and `Closed`, but any string is accepted\nso integrators can define their own workflow states.\n","default":"Open"},"timestamp":{"type":"string","format":"date-time"},"ticketClosedTimestamp":{"type":"string","format":"date-time","nullable":true},"customerId":{"type":"string"},"customerName":{"type":"string"},"customerEmail":{"type":"string","format":"email"},"customerPhone":{"type":"string"},"customerDeviceName":{"type":"string"},"customerDeviceType":{"type":"string"},"deviceId":{"type":"string"},"assignedTechnician":{"type":"string"},"serviceRequired":{"type":"string"},"serviceNotes":{"type":"string"},"serviceTime":{"type":"string","format":"date-time"},"endTime":{"type":"string","format":"date-time"},"serviceAddress":{"type":"string"},"serviceLocation":{"type":"string","enum":["instore","offsite","remote"],"description":"Where the job is performed. instore = on-premises, offsite = at the customer's address, remote = handled remotely."},"warrantyRepair":{"type":"boolean"},"alternativeCustomerAddress":{"type":"boolean"},"additionalItems":{"type":"array","description":"Opaque, unstructured list used by the Servicebay app for extra line items attached to the job.","items":{"type":"object","additionalProperties":true}},"messageRooms":{"description":"Opaque container for in-app message-room metadata linked to this job. Structure is not stable.","type":"object","additionalProperties":true},"stationId":{"type":"string","description":"ID of the workstation/bay this job is assigned to (see Stations)."}}},"TicketCreate":{"type":"object","required":["customerId","customerName"],"properties":{"status":{"type":"string","description":"Free-form status string. Common values used by the Servicebay app\nare `Open`, `In Progress`, and `Closed`, but any string is\naccepted.\n","default":"Open"},"customerId":{"type":"string"},"customerName":{"type":"string"},"customerEmail":{"type":"string","format":"email"},"customerPhone":{"type":"string"},"customerDeviceName":{"type":"string"},"customerDeviceType":{"type":"string"},"deviceId":{"type":"string"},"assignedTechnician":{"type":"string"},"serviceRequired":{"type":"string"},"serviceNotes":{"type":"string"},"serviceTime":{"type":"string","format":"date-time"},"endTime":{"type":"string","format":"date-time"},"serviceAddress":{"type":"string"},"serviceLocation":{"type":"string","enum":["instore","offsite","remote"],"description":"Where the job is performed."},"warrantyRepair":{"type":"boolean","default":false},"alternativeCustomerAddress":{"type":"boolean","default":false},"additionalItems":{"type":"array","items":{"type":"object","additionalProperties":true}},"messageRooms":{"type":"object","additionalProperties":true},"stationId":{"type":"string","description":"ID of the workstation/bay this job is assigned to (see Stations)."}}},"TicketUpdate":{"type":"object","properties":{"status":{"type":"string","description":"Free-form status string (e.g. `Open`, `In Progress`, `Closed`)."},"customerName":{"type":"string"},"customerEmail":{"type":"string","format":"email"},"customerPhone":{"type":"string"},"customerDeviceName":{"type":"string"},"customerDeviceType":{"type":"string"},"assignedTechnician":{"type":"string"},"serviceRequired":{"type":"string"},"serviceNotes":{"type":"string"},"serviceTime":{"type":"string","format":"date-time"},"endTime":{"type":"string","format":"date-time"},"serviceAddress":{"type":"string"},"serviceLocation":{"type":"string","enum":["instore","offsite","remote"],"description":"Where the job is performed."},"warrantyRepair":{"type":"boolean"},"alternativeCustomerAddress":{"type":"boolean"},"additionalItems":{"type":"array","items":{"type":"object","additionalProperties":true}},"messageRooms":{"type":"object","additionalProperties":true},"stationId":{"type":"string","description":"ID of the workstation/bay this job is assigned to (see Stations)."}}},"TicketResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Ticket"}}},"TicketListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"tickets":{"type":"array","items":{"$ref":"#/components/schemas/Ticket"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"Service":{"type":"object","properties":{"id":{"type":"string"},"title":{"type":"string"},"description":{"type":"string"},"notes":{"type":"string"},"priceType":{"type":"string","enum":["fixed","rate","variable"]},"price":{"type":"number"},"costPrice":{"type":"number"},"priceTimeRate":{"type":"string","enum":["hour","day","week","month"]},"warranty":{"type":"boolean"},"warrantyDuration":{"type":"integer"},"warrantyPeriod":{"type":"string","enum":["day","week","month","year"]},"quantity":{"type":"number"},"taxRateId":{"type":"string"},"index":{"type":"integer"},"createdAt":{"type":"string","format":"date-time"}}},"ServiceCreate":{"type":"object","required":["title"],"properties":{"title":{"type":"string"},"description":{"type":"string"},"notes":{"type":"string"},"priceType":{"type":"string","enum":["fixed","rate","variable"]},"price":{"type":"number"},"costPrice":{"type":"number"},"priceTimeRate":{"type":"string","enum":["hour","day","week","month"]},"warranty":{"type":"boolean"},"warrantyDuration":{"type":"integer"},"warrantyPeriod":{"type":"string","enum":["day","week","month","year"]},"quantity":{"type":"number"},"taxRateId":{"type":"string"},"index":{"type":"integer"}}},"ServiceUpdate":{"allOf":[{"$ref":"#/components/schemas/ServiceCreate"}]},"ServiceResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Service"}}},"ServiceListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"services":{"type":"array","items":{"$ref":"#/components/schemas/Service"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"InventoryItem":{"type":"object","properties":{"id":{"type":"string"},"itemName":{"type":"string"},"description":{"type":"string"},"categoryId":{"type":"string"},"gtin":{"type":"string"},"sku":{"type":"string"},"price":{"type":"number"},"costPrice":{"type":"number"},"weight":{"type":"number"},"weightUnit":{"type":"string","enum":["g","kg","oz","lb"]},"stockCount":{"type":"integer"},"tracksStock":{"type":"boolean"},"warranty":{"type":"boolean"},"warrantyPeriod":{"type":"string","enum":["day","week","month","year"]},"warrantyDuration":{"type":"integer"},"quantity":{"type":"number"},"taxRateId":{"type":"string"},"index":{"type":"integer"},"createdAt":{"type":"string","format":"date-time"}}},"InventoryItemCreate":{"type":"object","required":["itemName"],"properties":{"itemName":{"type":"string"},"description":{"type":"string"},"categoryId":{"type":"string"},"gtin":{"type":"string"},"sku":{"type":"string"},"price":{"type":"number"},"costPrice":{"type":"number"},"weight":{"type":"number"},"weightUnit":{"type":"string","enum":["g","kg","oz","lb"]},"stockCount":{"type":"integer"},"tracksStock":{"type":"boolean"},"warranty":{"type":"boolean"},"warrantyPeriod":{"type":"string","enum":["day","week","month","year"]},"warrantyDuration":{"type":"integer"},"quantity":{"type":"number"},"taxRateId":{"type":"string"},"index":{"type":"integer"}}},"InventoryItemUpdate":{"allOf":[{"$ref":"#/components/schemas/InventoryItemCreate"}]},"InventoryItemResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/InventoryItem"}}},"InventoryListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"items":{"type":"array","items":{"$ref":"#/components/schemas/InventoryItem"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"LineItem":{"type":"object","properties":{"id":{"type":"string"},"title":{"type":"string"},"description":{"type":"string"},"price":{"type":"number"},"quantity":{"type":"number"},"taxRateId":{"type":"string"}},"additionalProperties":true},"Discount":{"type":"object","properties":{"type":{"type":"string","enum":["percentage","fixed"]},"value":{"type":"number"},"reason":{"type":"string"}},"additionalProperties":true},"Quote":{"type":"object","properties":{"id":{"type":"string"},"index":{"type":"integer"},"ticketId":{"type":"string"},"customerId":{"type":"string"},"customerName":{"type":"string"},"title":{"type":"string"},"message":{"type":"string"},"terms":{"type":"string"},"totalPrice":{"type":"number"},"depositRequest":{"type":"boolean"},"depositAmount":{"type":"number"},"depositDueDays":{"type":"integer"},"balanceAmount":{"type":"number"},"balanceDueDays":{"type":"integer"},"dueDays":{"type":"integer"},"expirationDays":{"type":"integer"},"expirationDate":{"type":"string","format":"date-time"},"neverExpires":{"type":"boolean"},"accepted":{"type":"boolean"},"invoiced":{"type":"boolean"},"sent":{"type":"boolean"},"viewedByCustomer":{"type":"boolean"},"viewedDate":{"type":"string","format":"date-time"},"acceptedDate":{"type":"string","format":"date-time"},"invoicedDate":{"type":"string","format":"date-time"},"sentDate":{"type":"string","format":"date-time"},"createdOn":{"type":"string","format":"date-time"},"services":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"inventoryItems":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"discount":{"$ref":"#/components/schemas/Discount"}}},"QuoteCreate":{"type":"object","required":["customerId"],"properties":{"ticketId":{"type":"string"},"customerId":{"type":"string"},"customerName":{"type":"string"},"title":{"type":"string"},"message":{"type":"string"},"terms":{"type":"string"},"totalPrice":{"type":"number"},"depositRequest":{"type":"boolean"},"depositAmount":{"type":"number"},"depositDueDays":{"type":"integer"},"balanceAmount":{"type":"number"},"balanceDueDays":{"type":"integer"},"dueDays":{"type":"integer"},"expirationDays":{"type":"integer"},"expirationDate":{"type":"string","format":"date-time"},"neverExpires":{"type":"boolean"},"sent":{"type":"boolean"},"services":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"inventoryItems":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"discount":{"$ref":"#/components/schemas/Discount"}}},"QuoteUpdate":{"allOf":[{"$ref":"#/components/schemas/QuoteCreate"}]},"QuoteResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Quote"}}},"QuoteListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"quotes":{"type":"array","items":{"$ref":"#/components/schemas/Quote"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"Invoice":{"type":"object","properties":{"id":{"type":"string"},"index":{"type":"integer"},"ticketId":{"type":"string"},"customerId":{"type":"string"},"customerName":{"type":"string"},"title":{"type":"string"},"message":{"type":"string"},"terms":{"type":"string"},"paymentAdvice":{"type":"string"},"totalPrice":{"type":"number"},"depositRequested":{"type":"boolean"},"depositAmount":{"type":"number"},"depositPaid":{"type":"boolean"},"balanceAmount":{"type":"number"},"balancePaid":{"type":"boolean"},"paid":{"type":"boolean"},"sent":{"type":"boolean"},"remindersEnabled":{"type":"boolean"},"dueDate":{"type":"string","format":"date-time"},"depositDueDate":{"type":"string","format":"date-time"},"balanceDueDate":{"type":"string","format":"date-time"},"invoiceDate":{"type":"string","format":"date-time"},"createdOn":{"type":"string","format":"date-time"},"sentDate":{"type":"string","format":"date-time"},"paidDate":{"type":"string","format":"date-time"},"viewedByCustomer":{"type":"boolean"},"viewedDate":{"type":"string","format":"date-time"},"services":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"inventoryItems":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"discount":{"$ref":"#/components/schemas/Discount"}}},"InvoiceCreate":{"type":"object","required":["customerId"],"properties":{"ticketId":{"type":"string"},"customerId":{"type":"string"},"customerName":{"type":"string"},"title":{"type":"string"},"message":{"type":"string"},"terms":{"type":"string"},"paymentAdvice":{"type":"string"},"totalPrice":{"type":"number"},"depositRequested":{"type":"boolean"},"depositAmount":{"type":"number"},"balanceAmount":{"type":"number"},"dueDate":{"type":"string","format":"date-time"},"depositDueDate":{"type":"string","format":"date-time"},"balanceDueDate":{"type":"string","format":"date-time"},"invoiceDate":{"type":"string","format":"date-time"},"remindersEnabled":{"type":"boolean"},"sent":{"type":"boolean"},"services":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"inventoryItems":{"type":"array","items":{"$ref":"#/components/schemas/LineItem"}},"discount":{"$ref":"#/components/schemas/Discount"}}},"InvoiceUpdate":{"allOf":[{"$ref":"#/components/schemas/InvoiceCreate"}]},"InvoiceResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Invoice"}}},"InvoiceListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"invoices":{"type":"array","items":{"$ref":"#/components/schemas/Invoice"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"Device":{"type":"object","description":"A customer's device/asset. Open schema — beyond the fixed fields below,\nany additional keys sent on create/update are stored and returned as-is\n(used for custom attributes like a serial/identifier).\n","additionalProperties":true,"properties":{"id":{"type":"string"},"type":{"type":"string"},"brand":{"type":"string"},"make":{"type":"string"},"model":{"type":"string"},"createdAt":{"type":"string","format":"date-time"}}},"DeviceCreate":{"type":"object","additionalProperties":true,"properties":{"type":{"type":"string"},"brand":{"type":"string"},"make":{"type":"string"},"model":{"type":"string"}}},"DeviceUpdate":{"allOf":[{"$ref":"#/components/schemas/DeviceCreate"}]},"DeviceResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Device"}}},"DeviceListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"devices":{"type":"array","items":{"$ref":"#/components/schemas/Device"}}}}}},"Payment":{"type":"object","properties":{"id":{"type":"string"},"invoiceId":{"type":"string"},"amount":{"type":"number","description":"Payment amount. Negative values represent a refund."},"paymentDate":{"type":"string","format":"date-time"},"paymentMethod":{"type":"string","description":"Payment method. Writable values are the manual methods; `stripe`/`stripeRefund` are set only by Stripe."},"sendReceipt":{"type":"boolean","description":"Metadata only — the API does not send receipt emails."},"notes":{"type":"string"},"stripePaymentIntentId":{"type":"string","description":"Read-only. Present when the payment originated from Stripe."},"stripeRefundId":{"type":"string","description":"Read-only. Present when the payment is a Stripe refund."}}},"PaymentCreate":{"type":"object","required":["invoiceId","amount"],"properties":{"invoiceId":{"type":"string"},"amount":{"type":"number","description":"Negative to record a refund."},"paymentDate":{"type":"string","format":"date-time"},"paymentMethod":{"type":"string","enum":["card","cash","eft","cheque","other"]},"sendReceipt":{"type":"boolean"},"notes":{"type":"string"}}},"PaymentUpdate":{"type":"object","properties":{"amount":{"type":"number"},"paymentDate":{"type":"string","format":"date-time"},"paymentMethod":{"type":"string","enum":["card","cash","eft","cheque","other"]},"sendReceipt":{"type":"boolean"},"notes":{"type":"string"}}},"PaymentResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Payment"}}},"PaymentListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"payments":{"type":"array","items":{"$ref":"#/components/schemas/Payment"}},"pagination":{"$ref":"#/components/schemas/Pagination"}}}}},"Station":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"index":{"type":"integer"},"capacity":{"type":"integer"}}},"StationCreate":{"type":"object","required":["name"],"properties":{"name":{"type":"string"},"index":{"type":"integer"},"capacity":{"type":"integer"}}},"StationUpdate":{"type":"object","properties":{"name":{"type":"string"},"index":{"type":"integer"},"capacity":{"type":"integer"}}},"StationResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/Station"}}},"StationListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"stations":{"type":"array","items":{"$ref":"#/components/schemas/Station"}}}}}},"TaxRate":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"rate":{"type":"number"},"isInclusive":{"type":"boolean"},"defaultEnabled":{"type":"boolean","description":"Only one tax rate per organisation may be the default."}}},"TaxRateCreate":{"type":"object","required":["name","rate"],"properties":{"name":{"type":"string"},"rate":{"type":"number"},"isInclusive":{"type":"boolean"},"defaultEnabled":{"type":"boolean"}}},"TaxRateUpdate":{"type":"object","properties":{"name":{"type":"string"},"rate":{"type":"number"},"isInclusive":{"type":"boolean"},"defaultEnabled":{"type":"boolean"}}},"TaxRateResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/TaxRate"}}},"TaxRateListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"taxRates":{"type":"array","items":{"$ref":"#/components/schemas/TaxRate"}}}}}},"TicketStatus":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"color":{"type":"integer","description":"Packed ARGB32 colour integer."},"index":{"type":"integer"},"type":{"type":"string","description":"`default` for the four built-in statuses, `custom` for user-created ones. Built-in statuses cannot be deleted."}}},"TicketStatusCreate":{"type":"object","required":["name"],"properties":{"name":{"type":"string"},"color":{"type":"integer"},"index":{"type":"integer"}}},"TicketStatusUpdate":{"type":"object","properties":{"name":{"type":"string"},"color":{"type":"integer"},"index":{"type":"integer"}}},"TicketStatusResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"$ref":"#/components/schemas/TicketStatus"}}},"TicketStatusListResponse":{"type":"object","properties":{"success":{"type":"boolean"},"data":{"type":"object","properties":{"ticketStatuses":{"type":"array","items":{"$ref":"#/components/schemas/TicketStatus"}}}}}}}}}