Фильтрация

Справочник по построению параметров фильтра в Bitrix24 REST API v2 (префиксные операторы) и v3 (массив троек), включая формат дат и правило отбрасывания order.

Обзор

В Bitrix24 два диалекта фильтров, и они не взаимозаменяемы — каждая версия API принимает только свой.

  • v2 ($b24.actions.v2.{call,callList,fetchList}.make) использует объект с префиксными ключами: оператор — это префикс к имени поля.
  • v3 ($b24.actions.v3.{call,callList,fetchList}.make) использует массив троек: [field, operator, value].

Передача фильтра в стиле v3 в v2-действие молча парсится неверно; передача фильтра в стиле v2 в v3-действие возвращает UnknownFilterOperatorException.

v2 — префиксные операторы

Оператор — это префикс к имени поля. Несколько ключей объединяются через AND. Два оператора на одном поле требуют двух отдельных ключей (например, диапазон).

filter: {
  '>=opportunity': 50000,
  '<=opportunity': 200000,
  '!stageId': 'LOST',
  '=%title': 'A%'
}
ПрефиксЗначениеПример
(нет)точное совпадение{ stageId: 'NEW' }
>=больше либо равно{ '>=opportunity': 50000 }
>больше{ '>id': 100 }
<=меньше либо равно{ '<=opportunity': 200000 }
<меньше{ '<closeDate': '2026-01-01' }
!не равно{ '!stageId': 'LOST' }
!=не равно (альтернатива){ '!=stageId': 'LOST' }
%LIKE (подстрока, без учёта регистра){ '%title': 'supply' }
=%LIKE с явным шаблоном (% / _){ '=%title': 'A%' }
!%NOT LIKE{ '!%title': 'test' }

Простое массивное значение означает IN; сочетайте с ! для «not in»:

filter: {
  stageId: ['NEW', 'PREPARATION', 'EXECUTING'], // IN
  '!categoryId': [4, 7]                          // NOT IN
}

v3 — массив троек

Фильтр — это JSON-массив; каждый элемент — условие [field, operator, value]. Массив верхнего уровня неявно объединяется через AND.

filter: [
  ['stageId', '=', 'NEW'],
  ['createdTime', '>=', '2026-01-01T00:00:00+03:00'],
  ['responsibleId', 'in', [1, 2, 3]]
]

v3-операторы — всего 8

=   !=   >   >=   <   <=   in   between
Нет оператора like / % / подстроки на уровне протокола v3. Поиск по подстроке сейчас доступен только в v2 — используйте v2 с % или =%. Запрос v3 ['title', 'like', 'A%'] падает с UnknownFilterOperatorException.
  • значение between должно быть массивом из 2 элементов: [min, max].
  • значение in должно быть массивом.

Двухаргументные формы — синтаксический сахар:

['id', 42]              // то же, что ['id', '=', 42]
['stageId', ['A', 'B']] // то же, что ['stageId', 'in', ['A', 'B']]

Для всего, что сложнее плоского списка, предпочитайте типизированный билдер FilterV3 — он валидирует операторы и форму in / between на стороне клиента. См. скилл b24jssdk-filtering.

Даты

Используйте хелпер SDK Text.toB24Format(date) для обоих диалектов — он выдаёт формат Bitrix24 yyyy-MM-dd'T'HH:mm:ssZZ и принимает на вход Date, DateTime или string.

import { Text } from '@bitrix24/b24jssdk'

const sixMonthsAgo = new Date()
sixMonthsAgo.setMonth(sixMonthsAgo.getMonth() - 6)

// v2
const filterV2 = { '>=createdTime': Text.toB24Format(sixMonthsAgo) }

// v3
const filterV3 = [['createdTime', '>=', Text.toB24Format(sixMonthsAgo)]]
Всегда включайте смещение часового пояса в строки дат — порталы Bitrix24 работают в часовом поясе, заданном на портале. Text.toB24Format() выводит смещение за вас.

Параметр order и list-действия

callList.make и fetchList.make (и v2, и v3) отбрасывают любой переданный order и принудительно сортируют по id курсора ({ [cursorIdKey]: 'ASC' }), потому что листают набор данных keyset-курсором. Если передать order, SDK его отбрасывает и логирует warning — значение молча игнорируется для результирующего набора.

Если нужен конкретный порядок сортировки, спуститесь до call.make и листайте вручную — но почти всегда вместо этого стоит фильтровать точнее. Подробности — Ограничения CallList.

Бок о бок: один запрос в v2 и v3

Открытые сделки (stageId не в WON / LOSE) с суммой от 50 000 до 200 000, созданные за последние полгода:

v2
import { EnumCrmEntityTypeId, Text } from '@bitrix24/b24jssdk'

const sixMonthsAgo = new Date()
sixMonthsAgo.setMonth(sixMonthsAgo.getMonth() - 6)

const response = await $b24.actions.v2.callList.make({
  method: 'crm.item.list',
  params: {
    entityTypeId: EnumCrmEntityTypeId.deal,
    filter: {
      '!stageId': ['WON', 'LOSE'],
      '>=opportunity': 50000,
      '<=opportunity': 200000,
      '>=createdTime': Text.toB24Format(sixMonthsAgo)
    },
    select: ['id', 'title', 'stageId', 'opportunity']
  },
  idKey: 'id',
  customKeyForResult: 'items'
})
v3
import { EnumCrmEntityTypeId, Text } from '@bitrix24/b24jssdk'

const sixMonthsAgo = new Date()
sixMonthsAgo.setMonth(sixMonthsAgo.getMonth() - 6)

const response = await $b24.actions.v3.callList.make({
  method: 'crm.item.list',
  params: {
    entityTypeId: EnumCrmEntityTypeId.deal,
    filter: [
      // в v3 нет оператора «not in» — оберните `in` в NOT-группу (`negative: true`).
      // Хелпер `FilterV3.not(FilterV3.in(...))` строит ту же форму.
      { negative: true, conditions: [['stageId', 'in', ['WON', 'LOSE']]] },
      ['opportunity', 'between', [50000, 200000]],
      ['createdTime', '>=', Text.toB24Format(sixMonthsAgo)]
    ],
    select: ['id', 'title', 'stageId', 'opportunity']
  },
  idKey: 'id',
  customKeyForResult: 'items'
})

См. также