Rest V2 Gap - Filter by ID in relevant list methods

In the XMLRPC API DataService - we could paginate through various tables. Most of these tables have an “id” field. So when paginating, I could filter for id > 0 .. get 1000 records back (let’s say the last ID is 2548) .. then filter for ID > 2548 and so on until all records are retrieved.

If we’re importing data for an account and the import script dies prematurely in the middle for whatever reason, it’s easy to restart by filtering for the ID > X last received. Since we are filtering by a key such as ID it’s effiicient and fast.

In the Rest v2 API - we are unable to filter by “id” in the relevant list methods such as: listContacts, listOrders, listOpportunities

My request here is to add “id” as a filterable column to all list methods for consistency.

I also wanted to provide my feedback regarding the list methods. The majority of list methods allow you to bulk import data from a table, which is basically what the DataService allowed you to do.

listContacts() GET /v2/contacts
listCompanies() GET /v2/companies
listLeadSources() GET /v2/leadSources
listPaginatedUsers() GET /v2/users
listUserGroups() GET /v2/userGroups
listTags() GET /v2/tags
listSubscriptions() GET /v2/subscriptions
listProducts() GET /v2/products
listProductCategories() GET /v2/productCategories
listOrders() GET /v2/orders
listOpportunities() GET /v2/opportunities
listOpportunityStages() GET /v2/opportunities/stages
listTasks() GET /v2/tasks
listLeadSourceCategories() GET /v2/leadSourceCategories
listCategoryDiscounts() GET /v2/discounts/productCategories
listCampaigns() GET /v2/campaigns
listAutomations() GET /v2/automations
listAffiliate() GET /v2/affiliates

The list methods below make you filter for a given ID which is inconsistent with all the other list methods above.. It also makes it very inefficient when trying to import something like all notes.

listNotes() GET /v2/contacts/{contact_id}/notes
listPaymentMethods() GET /v2/contacts/{contact_id}/paymentMethods
listLeadSourceRecurringExpenses() GET /v2/leadSources/{lead_source_id}/recurringExpenses
listLeadSourceExpenses() GET /v2/leadSources/{lead_source_id}/expenses

Thanks,
Casey

Thanks for sharing your detailed feedback regarding the id filter in the REST v2 API and the list methods. We’ll discuss this internally and I’ll get back to you with an update as soon as I have more information.

All the gaps reported in this post have been added to the known issues tracker.

Hi @Casey_Page,

Thanks again for your detailed feedback and for highlighting these gaps. I wanted to share a quick update on this.

The issue regarding listPaymentMethods has been addressed with the introduction of a new endpoint, which you can find here:

This should help improve efficiency when retrieving payment methods without requiring a contact-specific filter.

Hi @Casey_Page,

Just wanted to share an update on this—filtering has been improved for orders in the REST v2 API. You can now filter orders by id using comparison operators, which should make pagination and incremental syncing much more consistent with the older DataService behavior.

This includes using operators like greater-than / less-than on the id field, so you can resume imports cleanly from the last processed ID (e.g., id > X) without needing workarounds.

Additionally, this same capability is now available for products, contacts, notes, tasks, tags, companies, opportunities, affiliates, product categories, category discounts, opportunity stages and subscriptions, allowing id-based filtering with comparison operators across those endpoints as well.

Documentation for reference:

Thanks again for the detailed feedback—it’s been really helpful in shaping these improvements.

Hi @Casey_Page, quick update on the notes use case. We recently released GET /v2/notes , which allows listing notes without requiring a contact ID in the path.

Docs for reference: Keap REST API

Hi Casey, just a quick update: the GET /crm/rest/v2/leadSources/{lead_source_id}/expenses endpoint now supports using - as a wildcard for lead_source_id, allowing you to retrieve expenses across all lead sources in a single request.

Awesome, thanks.