# MyRepairApp API documentation - OpenAPI contract: https://www.myrepairapp.com/openapi.json - Generated from published, non-internal database documentation. ## About MyRepairApp MyRepairApp is point-of-sale and repair ticketing software for cell phone, computer, and electronics repair shops. It combines repair tickets, invoicing, integrated payments, inventory management with supplier ordering, and customer communication in one web-based platform, with single and multi-location support. - Product site: https://www.myrepairapp.com - Get started: https://www.myrepairapp.com/get-started ## Notifications API > Poll your integration's notification feed to find out when new quote requests arrive. - Human: https://www.myrepairapp.com/api-docs/notifications - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/notifications.md - Last updated: 2026-09-06T05:08:38.749Z ## The Notification Model The Notification object represents an in-app notification delivered to your API integration. Use notifications to find out when new quote requests arrive without repeatedly listing all quotes. Below is an example of a Notification object with all possible fields. ```json { "id": "jd7c2v9k4m8p1q3r5s6t7u8v", "read": false, "createdAt": 1751394600000, "type": "QuoteCreated", "title": "New Quote", "message": "John Doe requested a quote for iPhone 12 (Screen Repair) at Main St Repair.", "entityId": "0197a1b2-3c4d-7e5f-8a9b-0c1d2e3f4a5b" } ``` ### Notification Object Properties | Field | Type | Required | Description | | ----------------------- | --------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | `id` (read-only) | `string` | No | The unique identifier for the notification. Use it to mark the notification as read. | | `read` | `boolean` | No | Indicates if the notification has been marked as read by your integration. | | `createdAt` (read-only) | `number` | No | The date and time the notification was created, as a Unix timestamp in milliseconds. | | `type` | `string` | No | The notification type. New quote requests have the type `QuoteCreated`. | | `title` | `string` | No | A short title for the notification. | | `message` | `string` | No | The human-readable notification message. | | `entityId` | `string` | No | The ID of the related record. For `QuoteCreated` notifications, this is the quote ID: use it with the Quotes API to fetch the full quote. Omitted when there is no related record. | Note: Your integration's notification feed starts accruing from the moment your API key is generated. Each store has a single API machine user, so every integration using your store's API key shares the same feed and the same read state. Notifications have their own read state: marking a notification as read through the API does not affect what store employees see in the app. The feed receives organization-wide notifications only. Admin-only notifications, such as invoice paid and ACH status updates, are never delivered to the API. Notifications are deleted 30 days after they are created, whether or not they were read, so poll at least that often. *** ## Notification Resources ### Get notifications This endpoint returns your integration's notifications, newest first. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/notifications?unreadOnly={boolean}&limit={number}&cursor={number} ``` **Parameters** All parameters are optional. The `unreadOnly` parameter, when set to `true`, returns only unread notifications. A typical polling flow is to request `unreadOnly=true`, process the results (e.g., fetch each `QuoteCreated` notification's quote by its `entityId`), and then mark the processed notifications as read. The `limit` parameter sets the maximum number of notifications returned and defaults to `20` (maximum `100`). The `cursor` parameter is used for pagination. Pass the `nextCursor` value from a previous response to fetch the next page. When `nextCursor` is `null`, there are no more results. A non-numeric `cursor` returns a `400` response. **Response** If successful, the response will include a list of notifications and a pagination cursor. ```json { "data": [ { "id": "jd7c2v9k4m8p1q3r5s6t7u8v", "read": false, "createdAt": 1751394600000, "type": "QuoteCreated", "title": "New Quote", "message": "John Doe requested a quote for iPhone 12 (Screen Repair) at Main St Repair.", "entityId": "0197a1b2-3c4d-7e5f-8a9b-0c1d2e3f4a5b" } ], "nextCursor": 1751394600000 } ``` *** ### Mark notifications as read This endpoint marks notifications as read. Only notifications belonging to your integration can be marked as read: IDs that belong to someone else are ignored, and malformed IDs return a `400` response. **HTTP Request** ```http POST https://www.myrepairapp.com/api/v2/notifications/mark-read ``` **Request Body** | Field | Type | Required | Description | | ----- | ---------- | -------- | -------------------------------------------------------------------- | | `ids` | `string[]` | Yes | The IDs of the notifications to mark as read (1 to 100 per request). | **Response** If successful, the response confirms the request was applied. Ignored IDs are not reported, so the response looks the same whether every ID or only some of them belonged to your integration. ```json { "success": true } ``` If one or more IDs are malformed, the endpoint returns a `400` response and no notifications are marked: ```json { "message": "One or more notification IDs are invalid." } ``` --- ## Quotes API > Create and track quote requests from potential customers, and add notes as you work them. - Human: https://www.myrepairapp.com/api-docs/quotes - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/quotes.md - Last updated: 2026-09-05T18:02:30.748Z ## The Quote Model The Quote object represents a quote request from a potential customer, including their contact information, device details, and the requested repair. Below is an example of a Quote object with all possible fields. ```json { "id": "0197a1b2-3c4d-7e5f-8a9b-0c1d2e3f4a5b", "orgId": "org_2abc123", "locationId": null, "firstName": "John", "lastName": "Doe", "phone": "+15035551234", "email": "john.doe@example.com", "preferredContact": "email", "category": "Phone", "manufacturer": "Apple", "model": "iPhone 12", "repair": "Screen Repair", "additionalInfo": "Cracked in the top corner.", "createdAt": "2026-07-01T18:30:00.000Z", "updatedAt": "2026-07-01T18:30:00.000Z", "appointmentDate": "2026-07-03T17:00:00.000Z", "quoteValue": "129.99", "quoteSent": false, "quoteStatus": "QUOTE_CREATED", "createdTicketId": null } ``` ### Quote Object Properties | Field | Type | Required | Description | | ----------------------- | --------- | -------- | ------------------------------------------------------------------------------------ | | `id` (read-only) | `string` | No | The unique identifier for the quote. | | `firstName` | `string` | Yes | The customer's first name. | | `lastName` | `string` | Yes | The customer's last name. | | `phone` | `string` | Yes | The customer's phone number. | | `email` | `string` | Yes | The customer's email address. | | `preferredContact` | `string` | Yes | The customer's preferred contact method (e.g., "email", "phone"). | | `category` | `string` | Yes | The device category (e.g., "Phone", "Tablet", "Computer"). | | `manufacturer` | `string` | Yes | The device manufacturer. Set from the `make` field when creating a quote. | | `model` | `string` | Yes | The device model. | | `repair` | `string` | Yes | The requested repair. | | `additionalInfo` | `string` | Yes | Additional details provided by the customer. May be an empty string. | | `appointmentDate` | `date` | No | The requested appointment time, if the customer scheduled one. | | `quoteValue` | `string` | No | The quoted price set by the store. | | `quoteSent` | `boolean` | No | Indicates if the quote has been sent to the customer. | | `quoteStatus` | `enum` | No | The quote's status (QUOTE_CREATED, SENT, LEFT_VOICEMAIL, NO_ANSWER, TICKET_CREATED). | | `createdTicketId` | `string` | No | The ID of the check-in ticket created from this quote, if it was converted. | | `createdAt` (read-only) | `date` | No | The date and time the quote was created. | | `updatedAt` (read-only) | `date` | No | The date and time the quote was last updated. | Note: "Required" indicates fields that must be provided when creating a quote. Fields on returned quotes may be `null` if the quote was created through another channel (e.g., the embedded quote form) without them. ### Quote Note Object Properties | Field | Type | Required | Description | | ------------------------- | --------- | -------- | ------------------------------------------------------------------------------------------------------------------------- | | `id` (read-only) | `string` | No | The unique identifier for the note. | | `quoteId` (read-only) | `string` | No | The ID of the quote the note belongs to. | | `createdById` (read-only) | `string` | No | The ID of the user who created the note. Notes created through the API are attributed to your integration's machine user. | | `note` | `string` | Yes | The note content (up to 5000 characters). | | `displayOnInvoice` | `boolean` | No | Indicates if the note should be shown on the invoice. Defaults to `false`. | | `createdAt` (read-only) | `date` | No | The date and time the note was created. | ### Quote Status History Object Properties Each entry records one status change on the quote. | Field | Type | Required | Description | | ----------------------- | -------- | -------- | --------------------------------------------------------------------------------------------------- | | `id` (read-only) | `string` | No | The unique identifier for the status history entry. | | `quoteId` (read-only) | `string` | No | The ID of the quote the entry belongs to. | | `fromStatus` | `enum` | No | The status the quote changed from (QUOTE_CREATED, SENT, LEFT_VOICEMAIL, NO_ANSWER, TICKET_CREATED). | | `toStatus` | `enum` | No | The status the quote changed to. | | `changedBy` | `string` | No | The ID of the user who made the change. | | `changedAt` (read-only) | `date` | No | The date and time of the change. | | `notes` | `string` | No | Optional notes about the change. | *** ## Quote Resources ### Get quotes This endpoint returns a paginated list of quotes. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/quotes?page={number}&pageSize={number}&status={string}&createdSince={date}&updatedSince={date} ``` **Parameters** All parameters are optional. The `page` parameter selects the page of results and defaults to `1`. The `pageSize` parameter sets the number of quotes per page and defaults to `20` (maximum `100`). The `status` parameter filters quotes by status and must be one of `QUOTE_CREATED`, `SENT`, `LEFT_VOICEMAIL`, `NO_ANSWER`, or `TICKET_CREATED`. The `createdSince` and `updatedSince` parameters filter quotes created or updated on or after the given date and must be valid ISO 8601 dates (e.g., `2026-07-01T00:00:00.000Z`). Date-only values (e.g., `2026-07-01`) are interpreted as UTC midnight. Use `updatedSince` to poll for new and changed quotes since your last request. **Response** If successful, the response will include a list of quotes sorted by creation date (newest first), along with pagination details. Each quote in `data` also includes a `_count.quoteNotes` field with the number of notes on the quote. ```json { "data": [ { "id": "0197a1b2-3c4d-7e5f-8a9b-0c1d2e3f4a5b", "quoteStatus": "QUOTE_CREATED", "_count": { "quoteNotes": 2 } } ], "totalCount": 42, "totalPages": 3, "currentPage": 1, "pageSize": 20 } ``` *** ### Get a quote by ID This endpoint returns a single quote by ID, including its notes and status history. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/quotes/{quoteId} ``` **Response** If successful, the response will include the details of the requested quote, its notes (`quoteNotes`, an array of Quote Note objects), and its status history (`statusHistory`, an array of Quote Status History objects), both sorted newest first. If the quote does not exist in your store, the endpoint returns a `404` response: ```json { "message": "Quote not found." } ``` *** ### Create a quote This endpoint creates a new quote request. Creating a quote notifies the store the same way a quote submitted through the embedded quote form does. **HTTP Request** ```http POST https://www.myrepairapp.com/api/v2/quotes ``` **Request Body** | Field | Type | Required | Description | | ------------------ | -------- | -------- | -------------------------------------------------------------------------------------------------------------- | | `category` | `string` | Yes | The device category. | | `make` | `string` | Yes | The device manufacturer. Returned as `manufacturer` on the quote. | | `model` | `string` | Yes | The device model. | | `repair` | `string` | Yes | The requested repair. | | `additionalInfo` | `string` | Yes | Additional details about the request. The field is required but may be an empty string. | | `firstName` | `string` | Yes | The customer's first name. | | `lastName` | `string` | Yes | The customer's last name. | | `phone` | `string` | Yes | The customer's phone number. | | `email` | `string` | Yes | The customer's email address. | | `preferredContact` | `string` | Yes | The customer's preferred contact method (e.g., "email", "phone", "text"). | | `appointmentDate` | `string` | No | The requested appointment date in `MM/dd/yyyy` format (e.g., `07/03/2026`), in the store's local timezone. | | `appointmentTime` | `string` | No | The requested appointment time in `hh:mm:ss a` format (e.g., `10:00:00 AM`), in the store's local timezone. | Note: all required fields other than `additionalInfo` must be non-empty, and `email` must be a valid email address. `phone` is stored as provided (trimmed) and is not validated for format. `appointmentDate` and `appointmentTime` must be provided together. Sending only one of them returns a `400` validation error. When both are provided: - Values in any other format (including ISO 8601) return a `400` response with the message `Invalid appointment date or time. Use MM/DD/YYYY for the date and hh:mm:ss AM/PM for the time.` - A time in the past returns a `400` response describing the store's available hours. - The slot is validated against the store's business hours and availability. If the slot is unavailable, the endpoint returns a `400` response with a message describing the store's available hours. **Response** If successful, the response will include the created quote object with a `201` status code. The created quote includes a `quoteNotes` array, which is empty for a new quote. **Rate limiting** Every request counts toward your store's public API limit of 60 requests per minute (see [API Rate Limits](https://www.myrepairapp.com/api-docs/api-rate-limits)). Quote creation may also enforce a stricter per-store limit. When either limit is exceeded, the endpoint returns a `429` response with a `Retry-After` header (the number of seconds to wait before retrying), the `X-RateLimit-Limit`, `X-RateLimit-Remaining`, and `X-RateLimit-Reset` headers, and a body containing the same wait time: ```json { "error": "Too many requests. Please try again later.", "retryAfter": 12 } ``` *** ### Add note to a quote This endpoint adds a note to a quote. **HTTP Request** ```http POST https://www.myrepairapp.com/api/v2/quotes/{quoteId}/note ``` **Request Body** The request body must contain a valid Quote Note object. **Response** If successful, the response will include the created quote note object with a `201` status code. If the quote does not exist in your store, the endpoint returns a `404` response. --- ## Supplier API > Inventory supplier API for adding custom suppliers and retrieving available ones to be attached to your inventory items. - Human: https://www.myrepairapp.com/api-docs/supplier-api-1 - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/supplier-api-1.md - Last updated: 2026-09-06T16:07:01.791Z ## The Supplier Model The Supplier object represents an inventory supplier. Vendors like MobileSentrix and InjuredGadgets are already configured by default for every store, but custom ones can be added to satisfy your needs. ```json { "id": "ABC123", "name": "MobileSentrix", } ``` ### Supplier Object Properties | Field | Type | Required | Description | | ------ | -------- | -------- | ---------------------------------------------------------------------------------------------------------------------------------------------- | | `id` | `string` | Yes | The id of the supplier in our system. You need to use this on your inventory item requests if you want them to be associated to this supplier. | | `name` | `string` | Yes | Supplier name. | ## Supplier Resources ### List suppliers This endpoints lists suppliers visible to your store. HTTP request ```bash curl -X GET "https://www.myrepairapp.com/api/v2/supplier \ -H "X-Api-Key: YOUR_API_KEY" ``` Response ```json [ { "id": "6b6bf6d8-9b7b-49a8-bd3b-7058505aaa1c", "name": "MobileSentrix" }, { "id": "c4adb990-972e-4169-9235-33057a916307", "name": "Wholesale Gadget Parts" }, { "id": "54d2af11-084f-4a8a-9cb3-3ad20ecb6cd3", "name": "Injured Gadgets" }, { "id": "b277d293-fc45-4c07-8b73-ec4f39df61f7", "name": "Phone LCD Parts" }, { "id": "67d841ce-9df6-456d-b9a3-a1bd86124f86", "name": "Axiom Armor" }, { "id": "3bef292b-de3f-443d-b5fc-12b7ebc381b7", "name": "Mobilenzo" } ] ``` ### Create a supplier This endpoint creates a supplier for your store. HTTP Request ```http POST https://www.myrepairapp.com/api/v2/supplier ``` Request Body ```json {"name": "Ebay"} ``` Response If successful, the response will include the created supplier details. --- ## Welcome to MyRepairApp API > Overview of the supported MyRepairApp public API, canonical routes, authentication, and agent-readable contracts. - Human: https://www.myrepairapp.com/api-docs/public-api - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/public-api.md - Last updated: 2026-09-06T16:06:46.652Z Welcome to **MyRepairApp API**! This API enables seamless integration with your MyRepairApp account, allowing developers and businesses to programmatically access repair tickets, customer information, inventory, and more. By automating processes, the API enhances efficiency and reduces manual workload. *** ## **Key Features** * **Customer Management (Beta):** Access and edit customer information securely. * **Ticket Management (Beta)**: Create, update, and track repair tickets and their statuses. * **Inventory Management (Beta):** Add, update, and monitor inventory items. Trade-ins and transferring items between different locations are also supported. * **Order Management (Beta):** Create and manage purchase orders, track invoices, and payment statuses. * **Lead and Quote Management (Beta):** Create and track quote requests from potential customers, and add notes as you work them. * **Notifications (Beta):** Poll your integration's notification feed to find out when new quote requests arrive. * **Automated SMS & Email (Soon):** Send automated messages to customers and leads. *** If you have any questions, please contact our support team at [**support@myrepairapp.com**](mailto:support@myrepairapp.com). --- ## Getting Started - Human: https://www.myrepairapp.com/api-docs/getting-started - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/getting-started.md - Last updated: 2026-09-04T19:17:57.137Z ## Prerequisites - A MyRepairApp account. - Admin privileges to generate an API key. ## Steps to Get Started 1. **Generate an API Key:** - Log in to your MyRepairApp account. - Click on your profile icon and select "Manage account". - Scroll down the Account page and click on "Generate API Key" (available only for admin users). - Copy and securely store the generated API key. Note: The key will only be displayed once. 2. **Review the Documentation:** - Familiarize yourself with the available endpoints, request/response formats, and error codes. 3. **Start Building:** - Use the provided examples to interact with the API using your preferred programming language. --- ## Authentication - Human: https://www.myrepairapp.com/api-docs/authentication - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/authentication.md - Last updated: 2026-09-05T12:43:56.808Z Authentication is required for all API requests. Use your API key in the `X-Api-Key` header to authenticate. ### Example Request Using cURL: ``` curl -X GET "https://www.myrepairapp.com/v2/customers" \ -H "X-Api-Key: YOUR_API_KEY" ``` ### Example Response: ``` { "data": [ { "id": "12345", "name": "John Doe", "email": "john.doe@example.com", "phone": "123-456-7890" } ] } ``` --- ## Request and Response Format - Human: https://www.myrepairapp.com/api-docs/request-response-format - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/request-response-format.md - Last updated: 2026-09-02T09:44:42.180Z - **Format:** JSON - **Headers:** - Content-Type: application/json - X-Api-Key: \ ### Example Request ```json { "name": "John Doe", "email": "john.doe@example.com", "phone": "123-456-7890" } ``` ### Example Response ```json { "id": "12345", "name": "John Doe", "email": "john.doe@example.com", "phone": "123-456-7890" } ``` --- ## Error Handling - Human: https://www.myrepairapp.com/api-docs/error-handling - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/error-handling.md - Last updated: 2026-09-04T19:17:57.137Z When using our API, you may encounter various error responses. This section outlines the common error codes, their meanings, and how to handle them properly. ## Common Error Responses Our API follows standard HTTP response status codes to indicate the success or failure of a request. ### 400 Bad Request Occurs when the request payload is invalid or improperly formatted. **Example Response:** ```json { "message": "Validation error. Please review your request payload.", "errors": { "email": ["Invalid email"], "address.zipCode": ["ZIP code must have 5 digits"] } } ``` The `errors` object is keyed by the field that failed validation and lists every problem found for that field. Invalid query parameters return a `400` with a `message` only. ### 401 Unauthorized Occurs when the API key is missing or invalid. **Example Response:** ```json { "message": "Unauthorized. Please check your credentials (login or API key) to access this resource." } ``` **Solution:** Check your API key and ensure it is valid. Refer to our [Getting Started Guide](https://myrepairapp.com/api-docs/getting-started) for details on generating a new API key. ### 403 Forbidden Occurs when the request is valid but the user does not have sufficient permissions to access the resource. **Example Response:** ```json { "message": "Forbidden. You do not have the necessary permissions to access this resource." } ``` **Solution:** Ensure your account has the necessary permissions to access this resource. ### 404 Not Found Occurs when the requested resource does not exist. **Example Response:** ```json { "message": "Resource not found. The requested endpoint does not exist." } ``` Lookups by ID return a resource-specific message when the record does not exist in your store, for example `"Quote not found."`. **Solution:** Check the API endpoint URL for typos or incorrect resource IDs. ### 429 Too Many Requests Occurs when the request rate limit has been exceeded. **Example Response:** ```json { "error": "Too many requests. Please try again later.", "retryAfter": 12 } ``` The response also includes a `Retry-After` header with the number of seconds to wait, plus `X-RateLimit-Limit`, `X-RateLimit-Remaining`, and `X-RateLimit-Reset` headers. See [API Rate Limits](https://www.myrepairapp.com/api-docs/api-rate-limits). **Solution:** Wait for the number of seconds in `Retry-After` (or `retryAfter`) before retrying. ### 500 Internal Server Error Occurs when an unexpected error happens on the server. **Example Response:** ```json { "message": "Internal server error. Please try again later." } ``` **Solution:** This is usually a temporary issue. Retry after some time or contact support if the issue persists. ## Handling Errors Effectively To ensure a smooth integration with our API, we recommend: - Logging error responses for debugging purposes. - Implementing retry mechanisms for `500` and `429` errors. - Ensuring valid authentication credentials to avoid `401` errors. - Checking request payloads to prevent `400` validation errors. - Reviewing API permissions to resolve `403` errors. For further assistance, refer to our [API Documentation](https://myrepairapp.com/api-docs/public-api) or contact our support team at **support@myrepairapp.com**. --- ## API Rate Limits - Human: https://www.myrepairapp.com/api-docs/api-rate-limits - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/api-rate-limits.md - Last updated: 2026-08-31T21:06:20.093Z ## API Rate Limits - **Limit:** 60 requests per minute. - **Throttling:** Requests exceeding this limit will return a 429 Too Many Requests error. --- ## SMS API > Send SMS and MMS messages to customers using your store's phone number. - Human: https://www.myrepairapp.com/api-docs/send-sms - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/send-sms.md - Last updated: 2026-09-05T03:53:10.199Z # SMS API Send SMS and MMS text messages to your customers using your store's MyRepairApp phone number. Messages are sent through your store's existing SMS configuration and draw down your store's SMS credits, exactly like messages sent from within the app. > **Note:** Your store must have an active SMS subscription with available credits, and completed A2P registration, for messages to be delivered. --- ## Send a Message Sends an SMS to a single phone number. If `mediaUrls` are included, the message is sent as an MMS. ### HTTP Request ```http POST https://www.myrepairapp.com/api/v2/sms/send ``` ### Request Body | Field | Type | Required | Description | | ----- | ---- | -------- | ----------- | | `phone` | `string` | Yes | The destination phone number. Most common formats are accepted and normalized to E.164 (e.g. `+15039969920`). | ### Request Body | Field | Type | Required | Description | | ----- | ---- | -------- | ----------- | | `phone` | `string` | Yes | The destination phone number. Most common formats are accepted and normalized to E.164 (e.g. `+15039969920`). | | `message` | `string` | Yes | The text body of the message. Maximum 1,600 characters. | | `mediaUrls` | `string[]` | No | Publicly accessible URLs of media to attach as an MMS. Maximum of 10. | ### Example Request - SMS ```bash curl -X POST "https://www.myrepairapp.com/api/v2/sms/send" \ -H "X-api-key: YOUR_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "phone": "+15039969920", "message": "Your repair is ready for pickup!" }' ``` ### Example Request - MMS ```bash curl -X POST "https://www.myrepairapp.com/api/v2/sms/send" \ -H "X-api-key: YOUR_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "phone": "+15039969920", "message": "Here is a photo of your device.", "mediaUrls": ["https://example.com/device-photo.jpg"] }' ``` ### Response If successful, the response includes the message identifier and its current delivery status. ```json { "messageSid": "SMd6baeae48b9be910a8bbe0e40fa8e7cb", "status": "queued" } ``` --- ## Error Responses | Status | Description | | ------ | ----------- | | 400 | Invalid request body, or SMS is not configured for your store. | | 401 | Unauthorized - missing or invalid API key. | | 402 | Your SMS subscription has expired, or you have insufficient credits. | | 502 | The message could not be sent due to an upstream provider error. Try again. | ```json { "message": "Insufficient credits, please go to the communication settings page to add more" } ``` --- ## Customers API - Human: https://www.myrepairapp.com/api-docs/customers - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/customers.md - Last updated: 2026-09-05T17:43:46.607Z ## The Customer Model The Customer object represents a customer in the system. Below is an example of a Customer object with all possible fields. ```json { "id": "12345", "firstName": "John", "lastName": "Doe", "company": "ACME Corp", "primaryPhone": "123-456-7890", "contactPhone": "123-456-7890", "email": "john.doe@example.com", "driversLicense": "123456789", "storeCredit": 100.5, "preferredContactMethods": ["email", "phone"], "billingAgent": "John Smith", "netTerms": "30 days", "taxExempt": "No", "postalCode": "12345", "referralSourceId": null, "street1": "123 Main St", "street2": "Suite 100", "country": "US", "state": "CA", "city": "Los Angeles" } ``` ### Customer Object Properties | Field | Type | Required | Description | | ------------------------- | -------- | -------- | ----------------------------------------------------- | | `id` | `string` | No | The unique identifier for the customer. | | `firstName` | `string` | Yes | The customer's first name. | | `lastName` | `string` | Yes | The customer's last name. | | `company` | `string` | Yes | The company associated with the customer. | | `primaryPhone` | `string` | Yes | The customer's primary phone number. | | `contactPhone` | `string` | No | An additional contact phone number. | | `email` | `string` | No | The customer's email address. | | `driversLicense` | `string` | No | The customer's driver's license number. | | `storeCredit` | `number` | Yes | The store credit available for the customer. | | `preferredContactMethods` | `array` | Yes | The customer's preferred methods of contact. | | `billingAgent` | `string` | Yes | The billing agent responsible for this customer. | | `netTerms` | `string` | Yes | The payment terms for the customer (e.g., "30 days"). | | `taxExempt` | `string` | Yes | Indicates if the customer is tax-exempt. | | `postalCode` | `string` | Yes | The postal code for the customer's address. | | `referralSourceId` | `number` | No | The source that referred the customer, if applicable. | | `street1` | `string` | Yes | The primary street address of the customer. | | `street2` | `string` | Yes | Additional street address information. | | `country` | `string` | Yes | The customer's country of residence. | | `state` | `string` | Yes | The state of the customer's address. | | `city` | `string` | Yes | The city of the customer's address. | *** ## Customer Resources ### Get all customers This endpoint returns a list of all customers. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/customers ``` **Response** If successful, the response will include a list of all customers. *** ### Create a customer This endpoint creates a new customer. **HTTP Request** ```http POST https://www.myrepairapp.com/api/v2/customers ``` **Request Body** The request body must contain a valid Customer object. **Response** If successful, the response will include the updated customer's details. *** ### Get a customer by ID This endpoint returns a single customer by ID. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/customers/{id} ``` **Response** If successful, the response will include the details of the requested customer. *** ### Update a customer This endpoint updates a customer's information. **HTTP Request** ```http PATCH https://www.myrepairapp.com/api/v2/customers/{id} ``` **Request Body** The request body must contain a Customer object with the fields to be updated. **Response** If successful, the response will include the updated customer's details. *** ### Delete a customer This endpoint deletes a customer. **HTTP Request** ```http DELETE https://www.myrepairapp.com/api/v2/customers/{id} ``` **Response** If successful, the response will indicate that the customer has been deleted. --- ## Inventory API - Human: https://www.myrepairapp.com/api-docs/inventory-item - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/inventory-item.md - Last updated: 2026-09-05T22:06:18.520Z ## The Inventory Item Model The Inventory Item object represents an item in the inventory system. Below is an example of an Inventory Item object with all possible fields. ```json { "sku": "AP-REPL-BATT-18", "manufacturer": "Apple", "category": "Part", "type": "Part - Computer", "name": "Replacement Battery Compatible For iPhone 11 Pro (AmpSentrix Pro)", "inventoried": true, "serialized": false, "cost": 20.85, "instock": 5, "condition": "New", "price": 20.85, "isRebate": false, "taxFree": false, "serialNum": "72839591ABS" } ``` Allowed Inventory Item Categories * Accessory * Device * Part * Repair * Service * Tool * Prepaid Allowed Inventory Item Conditions * New * Used * Refurbished * Damaged ## Inventory Item Resources ### Create an inventory item This endpoint creates a new inventory item. **HTTP Request** ```http POST https://www.myrepairapp.com/api/v2/inventory ``` **Request Body** | Field | Type | Required | Description | | -------------- | ------------------------ | -------- | ---------------------------------------------------------------------------------------------------------------------------------- | | `sku` | `string` | Yes | The unique stock keeping unit for the item. | | `manufacturer` | `string` | Yes | The manufacturer of the item. | | `category` | `InventoryItemCategory` | Yes | The category classification of the item. Allowed values are listed below this table. | | `type` | `string` | Yes | The type of item. | | `name` | `string` | Yes | The name of the item. | | `cost` | `number` | Yes | The cost of the item. | | `inventoried` | `boolean` | Yes | Indicates whether the item is tracked in inventory. | | `serialized` | `boolean` | Yes | Indicates if the item has a serial number. | | `isRebate` | `boolean` | Yes | Indicates if the item qualifies for a rebate. | | `taxFree` | `boolean` | Yes | Indicates if the item is tax-free. | | `instock` | `number` | Yes | The number of items currently in stock. | | `condition` | `InventoryItemCondition` | Yes | The condition of the item (e.g., New, Used). | | `supplierId` | `string` | No | The ID of the supplier for the item. If present on a request, it must match an existing supplier in the system (see supplier API). | | `serialNum` | `string` | No | The serial number of the item, if applicable. | | `price` | `number` | Yes | The selling price of the item. | | `bin` | `string` | No | The bin location of the item in the warehouse. Used only on update. | | `note` | `string` | No | Additional notes about the item. Used only on update. | **Response** If successful, the response will include the updated inventory item's details. *** ### Update an inventory item This endpoint updates an inventory item's information. **HTTP Request** ```http PATCH https://www.myrepairapp.com/api/v2/inventory/ ``` **Request Body** | Field | Type | Required | Notes | | ------------ | ------------------------ | -------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | category | `InventoryItemCategory` | No | | | type | string | No | | | sku | string | No | | | manufacturer | string | No | | | name | string | No | | | instock | number | No | Items with non empty serial numbers cannot have `instock` greater than 1, so if an `instock` amount larger than 1 is set on such an item a new item will be created with the serial number and a quantity of 1. | | condition | `InventoryItemCondition` | No | | | bin | string | No | | | supplierId | string | No | Can be `null` | | price | number | No | | | cost | number | No | | | isRebate | boolean | No | | | taxFree | boolean | No | | | note | string | No | | | serialNum | string | No | Can be `null`. Items with non empty serial numbers cannot have `instock` greater than 1, so if a serialNumber is set on such an item a new item will be created with the serial number and a quantity of 1. | **Response** If successful, the response will include the updated inventory item's details. In specific scenarios it's possible the response contains also "createdInventoryItem" and "deletedInventoryItem" keys. This is done to enforce a restriction where items with serial numbers can only have 1 of it in stock (they're supposed to be unique), the item essentially splits the item line into two, one with stock greater than 1 and one with the serial number. It will happen if you either: * Edit an item with a serial number changing its `instock` quantity to a value greater than 1 * Add a serial number to an item that has `instock` greater than 1 ```json { "updatedInventoryItem": { "id": "019adb7a-a367-7c23-b51e-6b953b25d7a5", "storeId": "42eb713e-1aa3-4b9f-a6e8-3f9e246b5466", "groupingId": null, "sku": "AP-REPL-BATT-19", "manufacturer": "Apple", "category": "Part", "type": "Part - Computer", "name": "Replacement Battery Compatible For iPhone 11 Pro (AmpSentrix Pro)", "cost": 20.85, "inventoried": true, "serialized": false, "instock": 4, "condition": "New", "bin": "", "supplierId": null, "price": 20.85, "createdAt": "2025-12-01T19:53:58.888Z", "updatedAt": "2025-12-04T10:33:48.062Z", "note": "", "active": true, "serialNum": null, "isRebate": false, "taxFree": false, "repairProvider": null, "tradeinDevice": false, "storage": null, "color": null, "carrier": null, "tradeInCondition": null, "tradeInStatus": null, "additionalInfo": null, "isMotorolaSku": false, "supplier": null }, "createdInventoryItem": { "id": "019ae8ec-d9ee-7802-bfe5-ca29d1da172f", "storeId": "42eb713e-1aa3-4b9f-a6e8-3f9e246b5466", "groupingId": null, "sku": "AP-REPL-BATT-19", "manufacturer": "Apple", "category": "Part", "type": "Part - Computer", "name": "Replacement Battery Compatible For iPhone 11 Pro (AmpSentrix Pro)", "cost": 20.85, "inventoried": true, "serialized": false, "instock": 1, "condition": "New", "bin": "", "supplierId": null, "price": 20.85, "createdAt": "2025-12-01T19:53:58.888Z", "updatedAt": "2025-12-04T10:33:10.688Z", "note": "", "active": true, "serialNum": "093822321", "isRebate": false, "taxFree": false, "repairProvider": null, "tradeinDevice": false, "storage": null, "color": null, "carrier": null, "tradeInCondition": null, "tradeInStatus": null, "additionalInfo": null, "isMotorolaSku": false }, "deletedInventoryItem": null } ``` *** ### Delete an inventory item This endpoint deletes an inventory item. **HTTP Request** ```http DELETE https://www.myrepairapp.com/api/v2/inventory/ ``` **Response** If successful, the response will include a success message. *** ### Search inventory items If a query parameter is provided, a search for inventory items will run based on various criteria. The search algorithm will match any items satisfying the following conditions: 1. Exact name matches (highest relevance) 2. Case-insensitive exact matches 3. Names that start with the query 4. Names that contain the full query 5. Partial matches (lowest relevance) Additionally, items in stock are displayed before out-of-stock items in the results. If one wants to search for items with a query but wants them sorted by update date instead of the above algorithm, the `relevanceSort` parameter must be passed as false. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/inventory/search ``` **Query Parameters** | Parameter | Type | Required | Description | | --------------- | -------- | -------- | ----------------------------------------------------------------------------------------------------------------------------------------------- | | `query` | `string` | No | Search term to filter inventory items (can be sku, part of item name, etc). | | `relevanceSort` | `false` | No | If provided as false, will sort query match results based on item update date rather than the algorithm. Defaults to true if query is provided. | | `storeIds` | `string` | No | Comma-separated list of store IDs to filter by. | | `categories` | `string` | No | Comma-separated list of categories to filter by. | | `types` | `string` | No | Comma-separated list of types to filter by. | | `catalogOnly` | `string` | No | If present, returns only catalog items. | | `inventoryOnly` | `string` | No | If present, returns only inventory items. | | `instockOnly` | `string` | No | If present, returns only items that are in stock. | | `page` | `number` | No | Pagination page. | | `pageSize` | `string` | No | Pagination page size. When not provided defaults to 50 IF page parameter was provided, doesn't limit results otherwise. | **Response** If successful, the response will include an array of inventory items matching the search criteria. --- ## Trade-in Device API - Human: https://www.myrepairapp.com/api-docs/trade-ins - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/trade-ins.md - Last updated: 2026-09-05T03:53:43.752Z ## The Trade-in Device Model The Trade-in Device Item object represents a device that is being traded in the system. Below is an example of a Trade-in Device Item object with all possible fields. ```json { "carrier": "Verizon", "color": "White", "condition": "Grade A", "manufacturer": "Apple", "deviceType": "Phones", "model": "iPhone 13 Pro", "password": "", "serialNumber": "332132131AA", "status": "Opened", "storage": "256GB", "patternLock": "[]", "quoteValue": "100", "tradeinDevice": true, "additionalInfo": "Includes original box and accessories" } ``` ### Trade-in Device Object Properties | Field | Type | Required | Description | | ---------------- | --------- | -------- | ------------------------------------------------- | | `color` | `string` | No | The color of the device. | | `manufacturer` | `string` | No | The manufacturer of the device. | | `deviceType` | `DeviceType` | Yes | The type of device (e.g., Tablets, Computers). | | `model` | `string` | Yes | The device model name. | | `storage` | `string` | Yes | The storage capacity of the device. | | `carrier` | `string` | No | The carrier associated with the device. | | `quoteValue` | `string` | Yes | The quoted value of the trade-in device. | | `serialNumber` | `string` | Yes | The serial number of the device. | | `condition` | `string` | No | The condition of the device. | | `sku` | `string` | No | The SKU of the device. If not provided a random one will be generated. | | `additionalInfo` | `string` | No | Additional information about the trade-in device. | #### Allowed Device Types - Tablets - Computers - Phones - Gaming - Other - Wearables --- ## Trade-in Resources ### Search trade-ins This endpoint returns a list of all trade-ins. #### HTTP Request ```http GET https://www.myrepairapp.com/api/v2/inventory/trade-in ``` #### Query Parameters | Parameter | Type | Required | Description | | --------------- | -------- | -------- | ------------------------------------------------- | | `query` | `string` | No | Search term to filter inventory items (can be sku, part of item name, etc). | | `page` | `number` | No | Pagination page. | | `pageSize` | `string` | No | Pagination page size. When not provided defaults to 50 IF page parameter was provided, doesn't limit results otherwise. | #### Response If successful, the response will include a list of trade-ins that fulfill the search criteria. --- ### Create a trade-in This endpoint creates a list of new trade-in devies. #### HTTP Request ```http POST https://www.myrepairapp.com/api/v2/inventory/trade-in ``` #### Request Body The request body must contain a valid list of TradeIn objects. ```json [ { "carrier": "Verizon", "color": "White", "condition": "Grade A", "manufacturer": "Apple", "deviceType": "Phones", "item": "iPhone 13 Pro", "model": "iPhone 13 Pro", "password": "", "serialNumber": "332132131AA", "status": "Opened", "storage": "256GB", "patternLock": "[]", "quoteValue": "100", "tradeinDevice": true, "additionalInfo": "" } ] ``` #### Response If successful, the response will include the trade-ins' inventory record details after creation. ```json { "createdItems": [ { "id": "019a9d93-ed50-7690-a78b-8283938sajsj", "storeId": "42eb713e-1aa3-4b9f-a6e8-3f9e246b5466", "groupingId": null, "sku": "TRADEIN-ce016b5", "manufacturer": "Apple", "category": "Device", "type": "Device - Phone", "name": "iPhone 13 Pro", "cost": 100, "inventoried": true, "serialized": false, "instock": 1, "condition": "Used", "bin": "", "supplierId": null, "price": 100, "createdAt": "2025-11-19T19:25:08.816Z", "updatedAt": "2025-11-19T19:25:08.816Z", "note": "", "active": true, "serialNum": "332132131AA", "isRebate": false, "taxFree": false, "repairProvider": null, "tradeinDevice": true, "storage": "256GB", "color": "White", "carrier": "Verizon", "tradeInCondition": "Grade A", "tradeInStatus": null, "additionalInfo": "", "isMotorolaSku": null, "pulled": 0, "backOrdered": 0 } ] } ``` --- ## Purchase Order API - Human: https://www.myrepairapp.com/api-docs/purchase-order - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/purchase-order.md - Last updated: 2026-09-01T22:04:18.714Z ## The Inventory Purchase Order Model The Inventory Purchase Order object represents a purchase order in the system. Below is an example of an Inventory Purchase Order object with all possible fields. ```json { "rush": true, "status": "Ordered", "supplierId": "SUP12345", "vendorOrderNumber": "VON67890", "shipper": "FedEx", "trackingNumber": "TRK123456789", "shippingCost": 25.5, "taxes": 5.75, "otherCostAdjustments": 2.0, "note": "Urgent order" } ``` ### Inventory Purchase Order Object Properties This model supports multiple types of updates. An update can contain: * A **rush order flag**. * A **status update**. * Detailed **order information updates**. | Field | Type | Required | Description | | ---------------------- | --------- | -------- | ------------------------------------------------------ | | `rush` | `boolean` | No | Indicates if the order is a rush order. | | `status` | `enum` | No | The status of the purchase order (Ordered/Reconciled). | | `supplierId` | `string` | No | The supplier ID for the purchase order. | | `vendorOrderNumber` | `string` | No | The vendor's order number for reference. | | `shipper` | `enum` | No | The shipping provider (e.g., FedEx, UPS). | | `trackingNumber` | `string` | No | The tracking number for the shipment. | | `shippingCost` | `number` | No | The cost of shipping the order. | | `taxes` | `number` | No | The tax amount for the purchase order. | | `otherCostAdjustments` | `number` | No | Any additional cost adjustments. | | `note` | `string` | No | Any additional notes related to the order. | ### Update Options Updates to an Inventory Purchase Order can be made using any of the following bodies: 1. **Rush Order Update:** Contains only the `rush` field. 2. **Status Update:** Contains only the `status` field. 3. **Order Info Update:** Contains fields such as `supplierId`, `vendorOrderNumber`, `shipper`, `trackingNumber`, `shippingCost`, `taxes`, `otherCostAdjustments`, and `note`. All three updates are possible and can be applied separately or together based on the update requirements. *** ## Purchase Order Resources ### Get all purchase orders This endpoint returns a list of all purchase orders. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/inventory/order ``` **Response** If successful, the response will include a list of all purchase orders from the inventory. *** ### Create a purchase order This endpoint creates an empty purchase order. **HTTP Request** ```http POST https://www.myrepairapp.com/api/v2/inventory/order ``` **Request Body** There should be no request body for this endpoint. **Response** If successful, the response will include the details of the newly created purchase order. *** ### Get a purchase order by ID This endpoint returns a single purchase order by ID. **HTTP Request** ```http GET https://www.myrepairapp.com/api/v2/inventory/order/{id} ``` **Response** If successful, the response will include the details of the requested purchase order. *** ### Update a purchase order This endpoint updates a purchase order's information. **HTTP Request** ```http PATCH https://www.myrepairapp.com/api/v2/inventory/order/{id} ``` **Request Body** The request body can contain any of the following fields: * `rush` * `status` * `supplierId` * `vendorOrderNumber` * `shipper` * `trackingNumber` * `shippingCost` * `taxes` * `otherCostAdjustments` * `note` **Response** If successful, the response will include the updated purchase order's details. *** ### Delete a purchase order This endpoint deletes a purchase order. **HTTP Request** ```http DELETE https://www.myrepairapp.com/api/v2/inventory/order/{id} ``` **Response** If successful, the response will include a confirmation message that the purchase order has been deleted. --- ## Inventory Transfer API - Human: https://www.myrepairapp.com/api-docs/inventory-transfer - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/inventory-transfer.md - Last updated: 2026-09-01T22:04:18.714Z ## The Inventory Transfer Item Model The Inventory Transfer Item object represents the transfer of inventory items between locations within the system. Below is an example of an Inventory Transfer Item object with all possible fields. ```json { "sourceLocation": { "id": "LOC12345", "orgId": "ORG67890", "locationName": "Warehouse A" }, "destinationLocation": { "id": "LOC54321", "orgId": "ORG67890", "locationName": "Store B" }, "items": [ { "id": "ITEM001", "transferQuantity": 10, "price": 25.5, "cost": 20.0 }, { "id": "ITEM002", "transferQuantity": 5, "price": 50.75, "cost": 40.0 } ] } ``` ### Inventory Transfer Item Object Properties | Field | Type | Required | Description | | ---------------------------------- | -------- | -------- | --------------------------------------------- | | `sourceLocation` | `object` | Yes | The source location details. | | `sourceLocation.id` | `string` | Yes | The unique identifier of the source location. | | `sourceLocation.orgId` | `string` | Yes | The organization ID of the source location. | | `sourceLocation.locationName` | `string` | Yes | The name of the source location. | | `destinationLocation` | `object` | Yes | The destination location details. | | `destinationLocation.id` | `string` | Yes | The unique identifier of the destination. | | `destinationLocation.orgId` | `string` | Yes | The organization ID of the destination. | | `destinationLocation.locationName` | `string` | Yes | The name of the destination location. | | `items` | `array` | Yes | A list of items being transferred. | | `items[].id` | `string` | Yes | The unique identifier of the inventory item. | | `items[].transferQuantity` | `number` | Yes | The quantity of the item being transferred. | | `items[].price` | `number` | Yes | The price of the item. | | `items[].cost` | `number` | Yes | The cost of the item. | This model allows for structured inventory transfers between locations, ensuring accurate tracking and organization of stock movements. --- ## Inventory Transfer Resources ### Create an inventory transfer This endpoint transfers an inventory item from one store location to another. #### HTTP Request ```http POST https://www.myrepairapp.com/api/v2/inventory/transfer ``` #### Request Body The request body must contain a valid InventoryTransfer object. #### Response If successful, the response will include the updated inventory transfer's details. --- ## Check-in Ticket API - Human: https://www.myrepairapp.com/api-docs/checkin-ticket - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/checkin-ticket.md - Last updated: 2026-09-05T17:43:46.607Z Integrate with MyRepairApp's ticket management system to create, search, and manage check-in tickets for sales and repairs. ### Important Note: It is important that identifier fields like `customer -> id` or `checkinItem -> inventoryItemId` map to existing entities on your store's customer or inventory records (use the customer or inventory APIs to list those). For `ticket -> assigneeId` or `checkinItem -> assigneeId` the id must correspond to that of a user (you can get it from the assignee object on the ticket search response) --- ## Search Check-in Tickets Search for tickets by customer name, device details, ticket number, or ticket creation date. ### HTTP Request ```http GET /api/v2/checkin-ticket?query={search_term}&closed={boolean} ``` ### Parameters | Parameter | Type | Required | Description | |-----------|------|----------|-------------| | `query` | string | Yes | Search term (name, email, device, etc.) | | `closed` | boolean | No | Fetch closed tickets only (default: false) | ### Searchable Fields - Ticket number - Customer name, email, or phone - Device name, SKU, or serial number - Creation date (`MM/dd/yyyy` format) ### Example Requests ```bash # Search by ticket number curl -X GET "https://www.myrepairapp.com/api/v2/checkin-ticket?query=12345" \ -H "X-api-key: YOUR_API_KEY" # Search by customer name curl -X GET "https://www.myrepairapp.com/api/v2/checkin-ticket?query=John%20Doe" \ -H "X-api-key: YOUR_API_KEY" # Search closed tickets curl -X GET "https://www.myrepairapp.com/api/v2/checkin-ticket?query=repair&closed=true" \ -H "X-api-key: YOUR_API_KEY" ``` ### Response ```json { "tickets": [ { "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "orgId": "org-abcdef-123456", "ticketNumber": 2644, "active": true, "assigneeId": "user-12345678-1234-1234-1234-123456789abc", "customerId": "cust-98765432-4321-4321-4321-210987654321", "order": null, "type": "Repair", "status": "Opened", "closedAt": null, "warrantyPeriodEnd": null, "isWarranty": false, "isReturn": false, "notToExceed": 0, "appointmentTime": null, "customerPossession": false, "storageBin": "", "waitingForPart": false, "shipper": null, "trackingNumber": null, "shipstationShipmentId": null, "labelURL": null, "claimRepairProvider": null, "createdAt": "2025-11-18T19:52:18.452Z", "updatedAt": "2025-11-18T19:52:18.459Z", "assignee": { "id": "user-12345678-1234-1234-1234-123456789abc", "name": "Your Store Name Here Machine User", "email": "", "phone": null, "hiredOn": null, "lastDay": null, "password": "", "pin": null, "akkoSalesRepId": null, "payRate": null, "maxDiscount": null, "discountType": "PERCENTAGE", "priceOverride": false, "discountCode": null, "canAddCredit": false, "displayCost": false, "displayMetrics": false, "editTimeclock": true, "addNewInventoryItems": true, "editInventoryItems": false, "deleteInventoryItems": true, "changeGroupInfo": false, "editShifts": false, "deleteTickets": false, "manageMPCustomers": false, "createdAt": "2025-05-28T18:28:03.043Z", "updatedAt": "2025-05-28T18:28:03.043Z" }, "customer": { "id": "cust-98765432-4321-4321-4321-210987654321", "storeId": "store-12345678-1234-1234-1234-123456789012", "referralSourceId": null, "firstName": "John", "lastName": "Doe", "company": "N/A", "primaryPhone": "", "contactPhone": "1234567890", "email": "john.doe@example.com", "driversLicense": null, "storeCredit": 0, "billingAgent": null, "taxExempt": null, "netTerms": null, "addressId": null, "active": true, "createdAt": "2025-10-03T19:40:31.849Z", "updatedAt": "2025-10-03T19:40:31.849Z", "fullName": "John Doe" }, "checkinItems": [ { "id": "item-11111111-2222-3333-4444-555555555555", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "invoiceId": null, "inventoryItemId": "inv-aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee", "overriddenPrice": 50, "overriddenCost": null, "originalPrice": 0, "originalCost": 0, "quantity": 1, "discount": 0, "tax": 0, "isTaxOverridden": false, "status": "Sold", "rmaReason": null, "rmaId": null, "returnToInventory": null, "assigneeId": "user-12345678-1234-1234-1234-123456789abc", "bitDefenderCode": null, "formSubmissionId": null, "createdAt": "2025-11-18T19:46:00.206Z", "updatedAt": "2025-11-18T19:52:18.493Z", "parts": [], "inventoryItem": { "id": "inv-aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee", "storeId": "store-12345678-1234-1234-1234-123456789012", "groupingId": null, "sku": "AP-IPHO-11-9371", "manufacturer": "Apple", "category": "Repair", "type": "Repair - Phone", "name": "iPhone 11 Battery Repair", "cost": 0, "inventoried": false, "serialized": false, "instock": 0, "condition": "New", "bin": "", "supplierId": null, "price": 0, "createdAt": "2025-09-25T16:26:55.386Z", "updatedAt": "2025-09-25T16:26:55.386Z", "note": "", "active": true, "serialNum": null, "isRebate": false, "taxFree": false, "repairProvider": null, "tradeinDevice": false, "storage": null, "color": null, "carrier": null, "tradeInCondition": null, "tradeInStatus": null, "additionalInfo": null, "isMotorolaSku": false }, "assignee": { "id": "user-12345678-1234-1234-1234-123456789abc", "name": "Your Store Name Here Machine User", "email": "", "phone": null, "hiredOn": null, "lastDay": null, "password": "", "pin": null, "akkoSalesRepId": null, "payRate": null, "maxDiscount": null, "discountType": "PERCENTAGE", "priceOverride": false, "discountCode": null, "canAddCredit": false, "displayCost": false, "displayMetrics": false, "editTimeclock": true, "addNewInventoryItems": true, "editInventoryItems": false, "deleteInventoryItems": true, "changeGroupInfo": false, "editShifts": false, "deleteTickets": false, "manageMPCustomers": false, "createdAt": "2025-05-28T18:28:03.043Z", "updatedAt": "2025-05-28T18:28:03.043Z" }, "formSubmission": null }, { "id": "item-66666666-7777-8888-9999-000000000000", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "invoiceId": null, "inventoryItemId": "inv-bbbbbbbb-cccc-dddd-eeee-ffffffffffff", "overriddenPrice": 11, "overriddenCost": null, "originalPrice": 0, "originalCost": 11.35, "quantity": 1, "discount": 0, "tax": 0.77, "isTaxOverridden": false, "status": "Sold", "rmaReason": null, "rmaId": null, "returnToInventory": null, "assigneeId": "user-12345678-1234-1234-1234-123456789abc", "bitDefenderCode": null, "formSubmissionId": null, "createdAt": "2025-11-18T19:45:55.013Z", "updatedAt": "2025-11-18T19:52:18.493Z", "parts": [], "inventoryItem": { "id": "inv-bbbbbbbb-cccc-dddd-eeee-ffffffffffff", "storeId": "store-12345678-1234-1234-1234-123456789012", "groupingId": null, "sku": "iP11BATT", "manufacturer": "China", "category": "Part", "type": "Part - Phone", "name": "iPhone 11 Battery", "cost": 11.35, "inventoried": true, "serialized": false, "instock": 0, "condition": "New", "bin": "", "supplierId": null, "price": 0, "createdAt": "2025-02-01T14:26:00.177Z", "updatedAt": "2025-03-28T16:34:59.000Z", "note": "", "active": true, "serialNum": null, "isRebate": false, "taxFree": false, "repairProvider": null, "tradeinDevice": false, "storage": null, "color": null, "carrier": null, "tradeInCondition": null, "tradeInStatus": null, "additionalInfo": null, "isMotorolaSku": false }, "assignee": { "id": "user-12345678-1234-1234-1234-123456789abc", "name": "Your Store Name Here Machine User", "email": "", "phone": null, "hiredOn": null, "lastDay": null, "password": "", "pin": null, "akkoSalesRepId": null, "payRate": null, "maxDiscount": null, "discountType": "PERCENTAGE", "priceOverride": false, "discountCode": null, "canAddCredit": false, "displayCost": false, "displayMetrics": false, "editTimeclock": true, "addNewInventoryItems": true, "editInventoryItems": false, "deleteInventoryItems": true, "changeGroupInfo": false, "editShifts": false, "deleteTickets": false, "manageMPCustomers": false, "createdAt": "2025-05-28T18:28:03.043Z", "updatedAt": "2025-05-28T18:28:03.043Z" }, "formSubmission": null } ], "checkinDevices": [ { "id": "device-12345678-1234-1234-1234-123456789012", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "item": "iPhone 11", "serialNumber": "", "password": "", "status": "Opened", "deviceType": "Phone", "model": "", "storage": "256GB", "color": "", "carrier": "", "note": "", "patternLock": "[]", "tradeinDevice": false, "quoteValue": "", "condition": "", "formSubmissionId": null, "completedFormSubmissionId": null, "formSubmission": null, "completedFormSubmission": null } ], "checkinPayments": [ { "id": "payment-11112222-3333-4444-5555-666677778888", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "recordedById": "user-12345678-1234-1234-1234-123456789abc", "tipAssigneeId": null, "externalId": null, "externalType": null, "registerId": null, "method": "Cash", "amount": 61.77, "change": 0, "tip": 0, "processingFee": 0, "status": "", "active": true, "refundedAmount": 0, "paymentTransactionChainId": null, "createdAt": "2025-11-18T19:47:04.010Z", "updatedAt": "2025-11-18T19:52:18.459Z", "recordedBy": { "id": "user-12345678-1234-1234-1234-123456789abc", "name": "Your Store Name Here Machine User", "email": "", "phone": null, "hiredOn": null, "lastDay": null, "password": "", "pin": null, "akkoSalesRepId": null, "payRate": null, "maxDiscount": null, "discountType": "PERCENTAGE", "priceOverride": false, "discountCode": null, "canAddCredit": false, "displayCost": false, "displayMetrics": false, "editTimeclock": true, "addNewInventoryItems": true, "editInventoryItems": false, "deleteInventoryItems": true, "changeGroupInfo": false, "editShifts": false, "deleteTickets": false, "manageMPCustomers": false, "createdAt": "2025-05-28T18:28:03.043Z", "updatedAt": "2025-05-28T18:28:03.043Z" } } ], "checkinNotes": [ { "id": "note-99999999-8888-7777-6666-555555555555", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "createdById": "user-12345678-1234-1234-1234-123456789abc", "note": "

Battery dying, needs replacements

", "displayOnInvoice": false, "createdAt": "2025-11-18T19:52:18.459Z", "createdBy": { "id": "user-12345678-1234-1234-1234-123456789abc", "name": "Your Store Name Here Machine User", "email": "", "phone": null, "hiredOn": null, "lastDay": null, "password": "", "pin": null, "akkoSalesRepId": null, "payRate": null, "maxDiscount": null, "discountType": "PERCENTAGE", "priceOverride": false, "discountCode": null, "canAddCredit": false, "displayCost": false, "displayMetrics": false, "editTimeclock": true, "addNewInventoryItems": true, "editInventoryItems": false, "deleteInventoryItems": true, "changeGroupInfo": false, "editShifts": false, "deleteTickets": false, "manageMPCustomers": false, "createdAt": "2025-05-28T18:28:03.043Z", "updatedAt": "2025-05-28T18:28:03.043Z" } } ], "checkinTicketActivities": [ { "id": "activity-aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "userId": "user-12345678-1234-1234-1234-123456789abc", "type": "ITEMS_CHANGED", "metadata": "{\"updateType\":\"Added\",\"itemName\":\"iPhone 11 Battery Repair\",\"itemSku\":\"AP-IPHO-11-9371\"}", "createdAt": "2025-11-18T19:52:18.498Z" }, { "id": "activity-bbbbbbbb-cccc-dddd-eeee-ffffffffffff", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "userId": "user-12345678-1234-1234-1234-123456789abc", "type": "ITEMS_CHANGED", "metadata": "{\"updateType\":\"Added\",\"itemName\":\"iPhone 11 Battery\",\"itemSku\":\"iP11BATT\"}", "createdAt": "2025-11-18T19:52:18.498Z" }, { "id": "activity-cccccccc-dddd-eeee-ffff-000000000000", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "userId": "user-12345678-1234-1234-1234-123456789abc", "type": "DEVICES_CHANGED", "metadata": "{\"updateType\":\"Added\",\"device\":{\"item\":\"iPhone 11\",\"serialNumber\":\"\",\"password\":\"\",\"status\":\"Opened\",\"deviceType\":\"Phone\",\"model\":\"\",\"storage\":\"256GB\",\"color\":\"\",\"carrier\":\"\",\"condition\":\"\",\"note\":\"\",\"patternLock\":\"[]\",\"formSubmissionId\":null,\"completedFormSubmissionId\":null,\"quoteValue\":\"\",\"tradeinDevice\":false}}", "createdAt": "2025-11-18T19:52:18.498Z" }, { "id": "activity-dddddddd-eeee-ffff-0000-111111111111", "checkinTicketId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890", "userId": "user-12345678-1234-1234-1234-123456789abc", "type": "CREATION", "metadata": "{\"customer\":\"John Doe\"}", "createdAt": "2025-11-18T19:52:18.498Z" } ], "myProtectionPlans": [] } ] } ``` --- ## Create Check-in Ticket Create new tickets for sales or repairs. ### HTTP Request ```http POST /api/v2/checkin-ticket ``` ### Sales Ticket Example ```json { "type": "Sales", "customer": { "id": "cust-55555555-6666-7777-8888-999999999999", "lastName": "Tribiani", "firstName": "Joey" }, "checkinItems": [ { "tax": 1.3993, "parts": [], "status": "Sold", "discount": 0, "quantity": 1, "createdAt": "2025-11-18T20:13:51.469Z", "assigneeId": null, "originalCost": 1.99, "originalPrice": 19.99, "inventoryItemId": "inv-cccccccc-dddd-eeee-ffff-111111111111", "isTaxOverridden": false, "formSubmissionId": null } ], "checkinPayments": [ { "tip": 0, "amount": 21.39, "change": 0, "method": "Card", "status": "N/A", "createdAt": "2025-11-18T20:14:02.198Z", "externalId": null, "registerId": null, "externalType": null, "processingFee": 0, "tipAssigneeId": null, "refundedAmount": 0, "paymentTransactionChainId": null } ], "formSubmissionId": [], "myProtectionPlans": [] } ``` ### Repair Ticket Example ```json { "type": "Repair", "storageBin": "", "initialNote": { "note": "

Battery dying, needs replacement

", "displayOnInvoice": false }, "notToExceed": 0, "customer": { "id": "cust-77777777-8888-9999-0000-111111111111", "lastName": "Doe", "firstName": "John" }, "checkinItems": [ { "tax": 0.77, "parts": [], "status": "Sold", "discount": 0, "quantity": 1, "createdAt": "2025-11-18T19:45:55.013Z", "assigneeId": null, "originalCost": 11.35, "originalPrice": 0, "inventoryItemId": "inv-dddddddd-eeee-ffff-0000-222222222222", "isTaxOverridden": false, "overriddenPrice": 11, "formSubmissionId": null }, { "tax": 0, "parts": [], "status": "Sold", "discount": 0, "quantity": 1, "createdAt": "2025-11-18T19:46:00.206Z", "assigneeId": null, "originalCost": 0, "originalPrice": 0, "inventoryItemId": "inv-eeeeeeee-ffff-0000-1111-333333333333", "isTaxOverridden": false, "overriddenPrice": 50, "formSubmissionId": null } ], "checkinDevices": [ { "item": "iPhone 11", "note": "", "color": "", "model": "", "status": "Opened", "carrier": "", "storage": "256GB", "password": "", "condition": "", "deviceType": "Phone", "quoteValue": "", "patternLock": "[]", "serialNumber": "", "tradeinDevice": false, "formSubmissionId": null, "completedFormSubmissionId": null } ], "trackingNumber": "", "waitingForPart": false, "checkinPayments": [ { "tip": 0, "amount": 61.77, "change": 0, "method": "Cash", "status": "", "createdAt": "2025-11-18T19:47:04.010Z", "externalId": null, "registerId": null, "externalType": null, "processingFee": 0, "tipAssigneeId": null, "refundedAmount": 0, "paymentTransactionChainId": null } ], "formSubmissionId": [], "myProtectionPlans": [], "customerPossession": false } ``` ### Required Fields | Ticket Type | Required Fields | |-------------|-----------------| | **Sales** | `type` | | **Repair** | `type`, `notToExceed`, `customerPossession`, `waitingForPart` | ### Response ```json { "createdTicket": { "id": "ticket-new-12345678-1234-1234-1234-123456789012", "orgId": "org-abcdef-123456", "ticketNumber": 2646, "active": true, "assigneeId": "user-12345678-1234-1234-1234-123456789abc", "customerId": "cust-55555555-6666-7777-8888-999999999999", "order": null, "type": "Sales", "status": "Opened", "closedAt": null, "warrantyPeriodEnd": null, "isWarranty": false, "isReturn": false, "notToExceed": null, "appointmentTime": null, "customerPossession": null, "storageBin": null, "waitingForPart": null, "shipper": null, "trackingNumber": null, "shipstationShipmentId": null, "labelURL": null, "claimRepairProvider": null, "createdAt": "2025-11-18T20:17:06.717Z", "updatedAt": "2025-11-18T20:17:06.723Z" } } ``` --- ## Update Check-in Ticket Update existing tickets. Two update modes are available: ### HTTP Request ```http PATCH /api/v2/checkin-ticket/{ticketId} ``` ### 1. Status Change Mode Use when updating ticket status (e.g closing) or changing assignees on ticket or items (contains status field on request body, even if not editing the status specifically): ```json { "status": "ReadyForPickup", "assigneeId": "user-abcdef12-3456-7890-abcd-ef1234567890" } ``` ### 2. Field Edit Mode Use when updating ticket details like items, parts, customer or devices (does not contain status field on the request body): ```json { "type": "Sales", "updateKey": 4114996984045216, "checkinItems": [ { "tax": 7, "parts": [], "status": "Sold", "discount": 0, "quantity": 1, "createdAt": "2025-11-18T20:48:53.556Z", "assigneeId": null, "originalCost": 0, "originalPrice": 0, "inventoryItemId": "inv-ffffffff-0000-1111-2222-444444444444", "isTaxOverridden": false, "overriddenPrice": 100, "formSubmissionId": null } ], "checkinPayments": [], "myProtectionPlans": [] } ``` ### ⚠️ Important: Update Behavior When Editing Fields When the ticket update, the API logic calculates the difference between the current ticket state in our system and the request you sent in, then modifies the state to reflect your request by "overwriting" it. This means if you want to add a customer to a ticket, in addition to your customer object you must also include all of the data you would get on the ticket GET endpoint otherwise you risk erasing that information from your ticket. THe same logic applies to arrays, when updating them (items, devices, payments), the API replaces the entire array. Include all existing items you want to keep. **Example - Adding an item while keeping existing:** ```json { // ...other ticket fields "checkinItems": [ { "id": "EXISTING_ITEM_001", "tax": 9, "parts": [], "status": "Sold", "discount": 0, "quantity": 1, "createdAt": "2025-11-18T20:48:53.556Z", "originalCost": 0, "originalPrice": 0, "inventoryItemId": "INV001" }, { "tax": 9, "parts": [], "status": "Sold", "discount": 0, "quantity": 1, "createdAt": "2025-11-18T20:48:53.556Z", "originalCost": 0, "originalPrice": 0, "inventoryItemId": "INV002" } ] } ``` --- ## Delete Check-in Ticket Permanently delete a check-in ticket. ### HTTP Request ```http DELETE /api/v2/checkin-ticket/{ticketId} ``` ### Response ```json { "success": true, "deletedTicket": { "id": "ticket-delete-12345678-1234-1234-1234-123456789012", "orgId": "org-abcdef-123456", "ticketNumber": 2645, "active": false, "assigneeId": "user-12345678-1234-1234-1234-123456789abc", "customerId": null, "order": null, "type": "Sales", "status": "ReadyForPickup", "closedAt": null, "warrantyPeriodEnd": null, "isWarranty": false, "isReturn": false, "notToExceed": null, "appointmentTime": null, "customerPossession": null, "storageBin": null, "waitingForPart": false, "shipper": null, "trackingNumber": null, "shipstationShipmentId": null, "labelURL": null, "claimRepairProvider": null, "createdAt": "2025-11-18T20:14:26.007Z", "updatedAt": "2025-11-18T21:11:20.184Z" } } ``` --- ## Add Note to Ticket Add notes to existing tickets. ### HTTP Request ```http POST /api/v2/checkin-ticket/{ticketId}/note ``` ### Request ```json { "note": "Customer called for status update. Parts expected tomorrow.", "displayOnInvoice": false } ``` ### Response ```json { "id": "note-new-12345678-1234-1234-1234-123456789012", "checkinTicketId": "ticket-new-12345678-1234-1234-1234-123456789012", "createdById": "user-12345678-1234-1234-1234-123456789abc", "note": "Customer called for status update. Parts expected tomorrow.", "displayOnInvoice": false, "createdAt": "2025-11-18T21:26:05.254Z", "createdBy": { "name": "Your Store Name Here Machine User", "email": "" } } ``` --- ## ⚠️ Error Handling ### Common Error Responses **400 - Validation Error** ```json { "success": false, "errors": [ { "code": "invalid_union_discriminator", "options": [ "Sales", "Repair" ], "path": [ "type" ], "message": "Invalid discriminator value. Expected 'Sales' | 'Repair'" } ] } ``` **401 - Unauthorized** ```json "Unauthorized" ``` --- ## Invoice API - Human: https://www.myrepairapp.com/api-docs/invoice - Raw Markdown: https://www.myrepairapp.com/api-docs/raw/invoice.md - Last updated: 2026-09-06T03:30:52.354Z ## The Invoice Model The Invoice object represents an invoice in the system. Below is an example of an Invoice object with all possible fields. > **Note:** The minimum invoice amount is **$5.01**. Invoices below this amount will be rejected by the payment processor. ``` { "customerId": "CUST12345", "tax": 10.5, "surchargeAmount": 3.5, "surchargeType": "PERCENTAGE", "description": "Monthly subscription fee", "recurringType": "MONTHLY", "descriptor": "Subscription Invoice", "startsFrom": "2025-02-01", "chargeOn": 1, "chargeUntil": 12, "invoiceItems": [ { "inventoryItemId": "INV001", "originalPrice": 100.00, "originalCost": 50.00, "overriddenPrice": 95.00, "quantity": 1, "discount": 5.00, "tax": 10.50, "status": "Sold", "parts": [ { "inventoryItemId": "PART001", "originalPrice": 20.00, "originalCost": 10.00, "quantity": 1, "discount": 0, "tax": 2.00, "status": "Sold" } ] } ], "sendEmail": true, } ``` ### Invoice Object Properties | Field | Type | Required | Description | | -------------------------------- | --------- | -------- | ----------------------------------------------------------------------------------------------------- | | `customerId` | `string` | Yes | The unique identifier for the customer. | | `amount` | `number` | No | **⚠️ DEPRECATED** - This field is ignored. Invoice amount is calculated from `invoiceItems`. | | `tax` | `number` | Yes | The total tax amount for the invoice. | | `surchargeAmount` | `number` | Yes | The surcharge amount (fixed amount or percentage based on `surchargeType`). | | `surchargeType` | `enum` | Yes | The surcharge calculation type: `FIXED` or `PERCENTAGE`. | | `description` | `string` | Yes | A description of the invoice. | | `recurringType` | `enum` | Yes | The recurrence type: `ONETIME`, `DAILY`, `WEEKLY`, `BIWEEKLY`, `MONTHLY`, `QUARTERLY`, or `ANNUALLY`. | | `descriptor` | `string` | No | The descriptor/subject for the invoice (max 25 characters). | | `startsFrom` | `string` | No | The start date for recurring invoices (ISO 8601 format). | | `chargeOn` | `number` | No | Day of week (0-6) for weekly/biweekly, or day of month (1-31) for monthly recurring invoices. | | `chargeUntil` | `number` | No | The number of billing cycles for recurring invoices. | | `invoiceItems` | `array` | No | A list of items included in the invoice. Total must be at least $5.01. | | `invoiceItems[].inventoryItemId` | `string` | Yes | The unique identifier of the inventory item. | | `invoiceItems[].originalPrice` | `number` | Yes | The original price of the item. | | `invoiceItems[].originalCost` | `number` | Yes | The original cost of the item. | | `invoiceItems[].overriddenPrice` | `number` | No | An overridden price for the item (if different from original). | | `invoiceItems[].overriddenCost` | `number` | No | An overridden cost for the item (if different from original). | | `invoiceItems[].quantity` | `number` | Yes | The quantity of the item. | | `invoiceItems[].discount` | `number` | Yes | The discount amount for the item. | | `invoiceItems[].tax` | `number` | Yes | The tax amount for the item. | | `invoiceItems[].status` | `enum` | Yes | Item status: `Sold`, `AvailableForReturn`, `Shipped`, `Declined`, or `Reconciled`. | | `invoiceItems[].parts` | `array` | No | Sub-parts associated with the invoice item (same structure as invoice items, without `createdAt`). | | `sendEmail` | `boolean` | Yes | Indicates if an email should be sent with the invoice. | This model provides a structured way to manage invoices, including details about recurring payments, invoice items, and shipping information. *** ## Invoice Resources ### Get all invoices This endpoint returns a list of all invoices. HTTP Request ``` GET https://www.myrepairapp.com/api/v2/invoice ``` Response If successful, the response will include a list of all invoices. *** ### Create an invoice This endpoint creates a new invoice. HTTP Request ``` POST https://www.myrepairapp.com/api/v2/invoice ``` Request Body The request body must contain a valid Invoice object. The total amount (calculated from `invoiceItems`) must be at least **$5.01**. Response If successful, the response will include the created invoice's details. Error Responses | Status | Description | | ------ | -------------------------------------------------------------- | | 400 | Invalid invoice data | | 401 | Unauthorized - missing or invalid authentication | | 500 | Invoice amount must be at least $5.01, or other internal error |