The Bulk Users & Companies Update HTTP API allows you to update user and company profiles in bulk. This API is intended for quickly synchronizing or modifying multiple profiles at once—either by sending JSON payloads directly or by uploading NDJSON files containing the updates. This API is different from the Historical Data Import API (for importing historical user/event data) and the Identify & Track API (for updating user/event properties in real time). The Bulk Profile Update API focuses solely on updating user and company profile properties.

Use Cases

  1. Bulk Update User Attributes: Use the JSON endpoint to update custom attributes for multiple users.
  2. Bulk Update Company Information: Send an array of company records to update details like company name, partner contact, or company type.
  3. Large-Scale Data Synchronization: When updating tens of thousands of users/companies, use the file upload endpoints with NDJSON formatted files for better performance and error handling.

Authentication

All requests require an API token in the Authorization header:
  • Authorization: Token {YOUR_API_KEY}
Your API key carries many privileges, so keep it secure and do not share it in public areas. All API requests must be made over HTTPS.

Limitations

  • File size up to 50 MB (for file uploads).
  • JSON/NDJSON list up to 10,000 users or companies per request.
  • Up to 1,200 rows processed per minute.
  • Only primitive types (string, number, boolean, null) are supported in metadata.

Endpoints

1. Update User Profiles (JSON)

Endpoint

POST https://analytex.userpilot.io/v1/users/bulk_identify

Headers

  • Content-Type: application/json
  • Accept: application/json, text/plain, */*
  • Authorization: Token {YOUR_API_KEY}

Request Body

Send a JSON payload containing an array of user profile objects:
{
  "users": [
    {
      "user_id": "user_001",
      "company_id": "comp001",
      "metadata": {
        "last_ticket_created": "2025-02-01T10:20:30Z",
        "tickets_created": "15",
        "tickets_resolved": "14",
        "tickets_pending": "1",
        "avg_resolution_time": "2h",
        "customer_satisfaction": "4.8",
        "escalation_count": "1"
      }
    },
    {
      "user_id": "user_002",
      "company_id": "comp002",
      "metadata": {
        "last_ticket_created": "2025-01-31T09:15:00Z",
        "tickets_created": "8",
        "tickets_resolved": "7",
        "tickets_pending": "1",
        "avg_resolution_time": "3h",
        "customer_satisfaction": "4.5",
        "escalation_count": "0"
      }
    }
  ]
}

Response

A successful call returns a job object:
{
  "job_id": "9536d797-7039-4d30-8c11-ac437367d732",
  "status": "queued",
  "submitted_at": "2025-02-02T12:34:56Z"
}

2. Update Company Profiles (JSON)

Endpoint

POST https://analytex.userpilot.io/v1/companies/bulk_identify

Headers

  • Content-Type: application/json
  • Accept: application/json, text/plain, */*
  • Authorization: Token {YOUR_API_KEY}

Request Body

Send a JSON payload containing an array of company profile objects:
{
  "companies": [
    {
      "company_id": "company_001",
      "metadata": {
        "subscription_status": "active",
        "subscription_plan": "enterprise",
        "deal_size": "500000",
        "monthly_active_users": "120",
        "platform_usage_score": "90",
        "account_manager": "Alice Manager"
      }
    },
    {
      "company_id": "company_002",
      "metadata": {
        "subscription_status": "trial",
        "subscription_plan": "basic",
        "deal_size": "15000",
        "monthly_active_users": "50",
        "platform_usage_score": "70",
        "account_manager": "Bob Manager"
      }
    }
  ]
}

Response

A successful call returns a job object:
{
  "job_id": "f47ac10b-58cc-4372-a567-0e02b2c3d479",
  "status": "queued",
  "submitted_at": "2025-02-02T12:35:10Z"
}

3. Update Profiles via File Upload (NDJSON)

For very large updates, you may upload NDJSON files containing user or company profiles.

3.1 Update User Profiles via File Upload

Endpoint

POST https://analytex.userpilot.io/v1/users/bulk_identify

Headers

  • Content-Type: multipart/form-data
  • Accept: application/json, text/plain, */*
  • Authorization: Token {YOUR_API_KEY}

Request Body

Submit the file using multipart/form-data. Include a key called file with your NDJSON file:
curl -X POST "https://analytex.userpilot.io/v1/users/bulk_identify" \
     -H "Authorization: Token {YOUR_API_KEY}" \
     -H "Content-Type: multipart/form-data" \
     -F "file=@/path/to/your/file.ndjson"
💡 Each line in the file should be a valid JSON object.

3.2 Update Company Profiles via File Upload

Endpoint

POST https://analytex.userpilot.io/v1/companies/bulk_identify

Headers

  • Content-Type: multipart/form-data
  • Accept: application/json, text/plain, */*
  • Authorization: Token {YOUR_API_KEY}

Request Body

Use multipart/form-data with a key named file containing your NDJSON file:
curl -X POST "https://analytex.userpilot.io/v1/companies/bulk_identify" \
     -H "Authorization: Token {YOUR_API_KEY}" \
     -H "Content-Type: multipart/form-data" \
     -F "file=@/path/to/your/file.ndjson"

4. Bulk Update Job Monitoring

After submitting a bulk update, a job is created to process your profiles asynchronously.

4.1 List All Bulk Update Jobs

Endpoint

GET https://analytex.userpilot.io/v1/background_jobs/

Headers

  • Authorization: Token {YOUR_API_KEY}
  • Accept: application/json, text/plain, */*

Response

Returns a list of jobs with their statuses, IDs, and submission timestamps:
[
  {
    "elapsed_time": 7,
    "end_time": "2025-03-08T18:50:14.150722",
    "file_size": 233,
    "filename": "NX-51f4acf7_identify_user_316e590e-755c-4b37-b6a0-0c34912b3210.ndjson",
    "job_id": "bulk:jobs:NX-51f4acf7:96b94fed-e9fe-4aa9-bce5-4f904ee3c533",
    "links": "/v1/background_jobs/bulk:jobs:NX-51f4acf7:96b94fed-e9fe-4aa9-bce5-4f904ee3c533",
    "start_time": "2025-03-08T18:50:07.217364",
    "status": "completed",
    "total_rows": 2,
    "type": "identify_user"
  }
]

4.2 Get Bulk Update Job Status by ID

Endpoint

GET https://analytex.userpilot.io/v1/background_jobs/{job_id}
Replace {job_id} with the ID of the job you want to inspect.

Headers

  • Authorization: Token {YOUR_API_KEY}
  • Accept: application/json, text/plain, */*

Response

Returns details about the specific job, including its current status and any errors encountered:
{
  "job_id": "9536d797-7039-4d30-8c11-ac437367d732",
  "status": "completed",
  "processed_count": 1500,
  "error_count": 0,
  "submitted_at": "2025-02-02T12:34:56Z",
  "completed_at": "2025-02-02T12:45:00Z"
}

Best Practices

  • Validate Your Data: Ensure each record includes the required identifiers (user_id or company_id) and that metadata is formatted correctly.
  • Monitor Jobs: Always use the job monitoring endpoints to check the status of your bulk updates.
  • Rate Limits and Retries: If you experience rate limits or timeouts, batch your requests and monitor job statuses before submitting more.

Troubleshooting

  • Authentication Errors: Verify your API token and that it is sent in the Authorization header.
  • Invalid Payload: Ensure your JSON/NDJSON is well-formed and required fields are present.
  • Job Failures: Use the job status endpoint to inspect error messages for failed records or processing issues.