Skip to main content

Integrating Chariot with External Lead Providers via API

Chariot provides an external-facing API for creating new leads. It is a single endpoint described in this document below.

Introduction

Chariot provides an external-facing API for creating new leads. It is a single endpoint described in this document below. If you are considering connecting with Chariot via this API, please read the documentation and contact us directly if you need an access token or want to set up a test connection.

Things You'll Need to Obtain from Chariot

To access and use the API, you'll need to request the following from Chariot: To generate these credentials via UI, follow these steps:

  1. Log in to your Chariot account.

  2. Navigate to: Users > Office Users > API Users.

  3. Click +Create API User to create a new Account ID and Auth Token.

API

The API is exposed via the api/external/lead endpoint. So the full URL will be something like https://{client_name}.chariotmove.com/api/external/lead to which you would make a POST request with contents described below. Fields with ! are required, everything else is optional. You will get a 200 response only if the lead was created successfully, and a 4xx error with a descriptive error message otherwise. Ensure you include the Content-Type: application/json header in your POST request.

{
   "meta": !{
     "account_id": !string,
     "auth_token": !string
   },
   "customer": !{
       "first_name": !string,
       "last_name": !string,
       "phone" !string,
       "email" !string,
       "category": ! "RESIDENTIAL" | "COMMERCIAL",
       "company_name": string
   },
   "other_contacts": [
       {
           "first_name": !string,
           "last_name": !string,
           "phone": string,
           "email": string
       }
   ],
   "lead": !{
       "lead_source": string,
       "other_source": string,
       "date_requested": ISO date string,
       "date_flexibility": "EXACT" | "PLUS_ONE" | "MINUS_ONE" | "PLUS_MINUS_ONE" | "PLUS_MINUS_TWO" | "PLUS_MINUS_THREE",
       "job_services": {
           "moving": "FULL_MOVE" | "LOAD_ONLY" | "UNLOAD_ONLY" | "MOVE_WITHIN_SAME_BUILDING" | "DELIVERY" | "NONE",
           "packing": "FULL_PACKING" | "FULL_PACKING_UNPACKING" | "PARTIAL_PACKING" | "PARTIAL_PACKING_UNPACKING" | "NONE",
           "storage": "STORAGE_IN" | "STORAGE_OUT" | "NONE"
       }
   },
   "job": {
       "distance_category": "IN_STATE_SHORT" | "IN_STATE_LONG" | "INTERSTATE",
       "notes": string
   },
   "locations": [
       {
           "raw_address": !string,
           "apartment_number": string,
           "category": "STUDIO" | "ONE_BEDROOM" | "TWO_BEDROOM" | "THREE_PLUS_BEDROOM" | "HOUSE" | "CONDO" | "TOWNHOME" | "COMMERCIAL" | "STORAGE_UNIT" | "WAREHOUSE",
           "floor": string,
           "parking": "STREET" | "GARAGE" | "PARKING_LOT" | "DRIVEWAY"| "ALLEY" | "LOADING_DOCK" | "OTHER" | "UNKNOWN",
           "access": "ELEVATOR_NO_STAIRS", "BASEMENT", "GROUND_FLOOR", "ONE_FLIGHT", "TWO_FLIGHTS", "THREE_FLIGHTS", "FOUR_FLIGHTS", "FIVE_FLIGHTS", "SIX_PLUS_FLIGHTS",
           "stories": string,
           "to_door_distance": "UNDER_FIFTY" | "FIFTY_ONE_TO_ONE_HUNDRED" | "ONE_HUNDRED_ONE_TO_TWO_HUNDRED" | "OVER_TWO_HUNDRED_ONE" | "UNKNOWN",
           "purpose": "PICK_UP" | "DROP_OFF",
           "coi_required": "YES" | "NO" | "IDK",
           "notes": string
       }
   ],
   "inventory": {
       "inventory_items": [
           {
               "name": !string,
               "room": string,
               "quantity" !int,
               "not_moving_quantity": !int,
               "volume": decimal,
               "weight": decimal,
               "packing_type": "PBO" | "CP",
               "notes": string
           }
       ],
       "notes": string
   }
}

Examples

Here are a couple of examples of valid payloads:

Minimal payload

{
   "meta": {"account_id": "test_user", "auth_token": "XXXX"},
   "customer": {
       "first_name": "John",
       "last_name": "",
       "phone": "7325551212",
       "email": "john@example.com",
       "category": "",
   },
}

Simple payload

{
   "meta": {"account_id": "test_user", "auth_token": "XXXX"},
   "customer": {
       "first_name": "Fobby",
       "last_name": "Doy",
       "phone": "7325551212",
       "email": "fobby@example.com",
       "category": "RESIDENTIAL",
   },
   "locations": [
       {"raw_address": "1216 Broadway New York NY 10000", "floor": "4"},
   ],
   "other_contacts": [],
   "lead": {"job_services": {"moving": "LOAD_ONLY"}},
   "job": {},
   "inventory": {
       "inventory_items": [],
       "notes": "some inventory notes",
   },
}

Maximal payload

{
   "meta": {"account_id": "test_user", "auth_token": "XXXX"},
   "customer": {
       "first_name": "Dobby",
       "last_name": "Boyd",
       "phone": "7325551212",
       "email": "dobby@example.com",
       "category": "COMMERCIAL",
       "company_name": "Acme",
   },
   "locations": [
       {"raw_address": "506 washington ave linden nj", "floor": 3},
       {"raw_address": "716 amherst road linden nj", "floor": 1},
       {
           "raw_address": "400 n wood ave linden nj",
           "apartment_number": "A",
           "category": "THREE_PLUS_BEDROOM",
           "floor": "3",
           "parking": "LOADING_DOCK",
           "access": "SIX_PLUS_FLIGHTS",
           "stories": "several, it's a multiplex penthouse!",
           "to_door_distance": "ONE_HUNDRED_ONE_TO_TWO_HUNDRED",
           "purpose": "DROP_OFF",
           "coi_required": "IDK",
           "notes": "blablabla, blabla.",
       },
       {"raw_address": "1216 Broadway, New York NY 1000", "floor": 4},
       {"raw_address": "506 washington ave linden nj", "floor": 3},
   ],
   "other_contacts": [
       {
           "first_name": "",
           "last_name": "LastNameOnly",
           "phone": "8665551212",
           "email": "another@example.com",
       },
       {
           "first_name": "FirstNameOnly and no phone",
           "last_name": "",
           "email": "andanotherone@example.com",
       },
   ],
   "lead": {
       "lead_source": "some_source",
       "date_requested": "2023-03-01",
       "date_flexibility": "PLUS_MINUS_THREE",
       "job_services": {
           "moving": "LOAD_ONLY",
           "packing": "PARTIAL_PACKING_UNPACKING",
           "storage": "STORAGE_IN",
       },
   },
   "job": {
       "distance_category": "INTERSTATE",
       "notes": "Lorem Ipsum, etc.",
   },
   "inventory": {
       "inventory_items": [
           {
               "name": "Magazine Rack",
               "room": "Living Room",
               "quantity": 1,
               "not_moving_quantity": 0,
               "volume": "2.00",
               "weight": "14.00",
           },
           {
               "name": "Piano - Upright",
               "room": "Living Room",
               "quantity": 1,
               "not_moving_quantity": 0,
               "volume": "70.00",
               "weight": "490.00",
           },
       ],
       "notes": "minimal inventory notes",
   },
}

Using No-Code Tools (Zapier, Make, etc.)

Some customers connect to the Chariot lead API using no-code automation platforms like Zapier or Make instead of writing custom code. These tools work well with the API, but there are two important differences to be aware of when setting them up.

Passing Credentials as Request Headers

The standard way to authenticate is to include your account_id and auth_token inside the meta object in the request body. However, some no-code tools have difficulty sending properly structured nested JSON — which can result in an unauthorized error even when your credentials are correct.

If you run into this, pass your credentials as HTTP request headers instead:

  • X-Account-Id — your account ID (e.g. yourcompany_api_api)

  • X-Auth-Token — your auth token

These headers work as a direct alternative to the meta body fields. You can still include meta in your payload if you want, but if both are present the headers take precedence.

Sending Nested Fields as Flat Key-Value Pairs

Chariot's API expects JSON with nested objects (e.g. a customer object containing first_name, phone, etc.). Most no-code tools let you build a full JSON body, which is the recommended approach. But some tools — especially Zapier's webhook action in certain configurations — send data as flat key-value pairs rather than structured JSON.

When that's the case, use double underscores (__) to represent nesting. For example:

  • customer__first_name instead of customer.first_name

  • job__notes instead of job.notes

  • lead__lead_source instead of lead.lead_source

Single dots (.) will not work as separators — this is a common source of errors when first setting up a Zapier integration.

Example: Zapier-style flat payload

Below is an example of the same lead data sent as flat key-value pairs. This format is equivalent to the nested JSON format the API normally expects:

customer__first_name: Jane
customer__last_name: Smith
customer__phone: 555-867-5309
customer__email: jane@example.com
customer__category: RESIDENTIAL
lead__lead_source: Website
lead__utm_source: google
locations__0__raw_address: 100 Main St, Raleigh NC 27601
job__notes: 3BR local move

Note: List items (like locations) use a zero-based index — locations__0__raw_address for the first location, locations__1__raw_address for the second, and so on.

Testing Your Integration

You can test your setup directly in a browser by navigating to your client's API endpoint URL:

https://{client_name}.chariotmove.com/api/external/lead

Submitting a request here will return a specific error message if something in your payload is malformed — useful for quickly pinpointing issues before going live.

Credentials, Testing, and Limits

To authenticate your requests, obtain credentials as follows:

  1. Log in to your Chariot account.

  2. Navigate to: Users > Office Users > API Users.

  3. Click +Create API User. Your account ID and authentication token will be generated automatically.

We have a demo environment that you can use to test your connection, let us know if you would like that set up as well. Otherwise, once ready we can provide you with the above-mentioned credentials via phone or secure email. Before deploying, test integration as follows:

  1. Prepare a sample JSON payload.

  2. Use a tool like curl or a development framework to POST data to the API endpoint.

  3. Verify the lead appears in your Chariot UI under Leads > Form Submitted.

  4. Address errors in payload structure or authentication.

The API will allow you to make up to 6 requests per minute per user. If you go beyond that limit, you will get a 429 status code which you can use for any back-off logic.

Best Practices for API Usage

  • Keep Credentials Secure: Never publish or hardcode your API credentials in public repositories.

  • Test Thoroughly: Use a testing or development environment to validate your integration before production deployment.

  • Monitor Submission Logs: Regularly review logs to identify and debug integration issues promptly.

  • Stay Within Rate Limits: Implement back-off logic to handle 429 status codes effectively.

Did this answer your question?