В этой статье разберем, как данные iiko становятся входом для WFM TARGControl: как забирать из POS почасовую выручку и количество чеков, превращать их во временные ряды, использовать для прогноза нагрузки и дальше — для планирования смен и аналитики.

Прежде чем перейти к API и эндпоинтам, ответим на вопрос «зачем вообще тащить POS в планирование». В HoReCa расписание проверяется не отчетом в конце недели, а кассой и залом в ближайшие 1–2 часа: спрос распределен неравномерно по времени, каналам (зал/доставка/навынос) и дням недели. Поэтому устойчивое планирование начинается не с «графика в таблице», а с измеримых драйверов спроса, которые можно регулярно обновлять автоматически.

Кадровый дефицит только повышает цену ошибки: недокомплект в пиковое окно дает перегруз сотрудников, потери выручки и ухудшение сервиса, а избыток в «тихие» часы — прямые лишние часы ФОТ. В результате управляемая зона смещается в две практические вещи: точнее попадать сменой в почасовой профиль спроса и иметь механизм быстрых корректировок, когда фактическая картина отклоняется от плана. POS-контур iiko как раз и дает основу для такого подхода — данные, на которых можно строить прогноз и честно сравнивать «продажи ↔ часы».

Ключевые особенности HoReCa, которые ломают ручное планирование:

  • Почасовая волатильность: ланч/вечер, будни/выходные, зал/доставка — разные профили нагрузки.

  • Высокая цена ошибки: недобор в пике = очередь и потери; перебор в провале = лишний ФОТ.

  • Ролевая структура: важен не «N человек», а состав по ролям/навыкам (кухня/зал/бар/доставка).

  • Операционный шум: невыходы/опоздания/подмены — регулярность, а не исключение, значит нужен контур быстрых замен.

Что такое система WFM для общепита 

WFM (Workforce Management) — это система, которая связывает фактическую нагрузку и график работы. По сути, она нужна, чтобы ответить на три практических вопроса:

  1. Сколько людей нужно по часам и ролям?

  2. Кого назначить с учетом навыков, доступности и ограничений?

  3. Как реагировать на отклонения без ручного хаоса?

Базовая цепочка WFM

  • Прогноз драйвера по часам (выручка/чеки/структура каналов).

  • Расчет потребности: перевод прогноза в человеко-часы по ролям/зонам через нормы и SLA сервиса.

  • Построение смен: правила, доступность, навыки/допуски, нормы ТК, лимиты часов.

  • Учет факта: сравнение план/факт (невыходы, опоздания, переработки).

  • Замены и обмены: открытые смены/биржа/подработки в рамках правил и ограничений.

  • Аналитика план-факт: продажи↔часы, покрытие пиков, overtime, дефицит ролей.

Почему прогноз без POS — это «умные шаблоны», а не WFM

На практике ограничения WFM почти всегда упираются в данные:

  • без POS-драйверов прогноз становится «по шаблонам»;

  • без факта (учета выхода) план-факт не замыкается и модель не улучшается;

  • без норм и стандартов сервиса нельзя корректно перевести спрос в человеко-часы.

В российской HoReCa роль источника фактической нагрузки чаще всего выполняет POS, и в большинстве сетей — iiko. Поэтому интеграция iiko → TARGControl — это не «дополнение», а техническая база для цепочки «факт продаж → прогноз → потребность → график → факт выхода → план-факт».

Как устроена интеграция iiko → TARGControl

Основная задача интеграции — синхронизировать почасовые показатели из iiko: количество транзакций (чеков) и сумму выручки, чтобы далее использовать их в TARGControl для прогноза нагрузки и построения смен.

Интеграция с iiko реализована через API iikoServer. Этот API дает доступ к ключевым сущностям, которые используются в WFM-контуре: справочникам (в т.ч. номенклатуре), отчетам по продажам/выручке, данным по сотрудникам. (полную документацию можно найти на официальном сайте). Далее разберем практический минимум эндпоинтов, необходимых ��ля выгрузки почасовой выручки и чеков.

1) Синхронизация локаций (ресторанов)

Прежде чем забирать продажи, нужно определить локации, чтобы разделять данные по отдельным ресторанам. В iiko такой локации соответствует подразделение типа “Торговое предприятие” — сущность DEPARTMENT.

Список подразделений получаем запросом:

GET {{baseUrl}}/resto/api/corporation/departments?key={{key}}

где 

baseUrl - url нашего сервера (Например, http://localhost:8080)

key - токен, полученный в ходе процедуры авторизации (можно передавать как параметр запроса или в качестве ключа в cookies. Подробнее про процедуру авторизации можно прочитать в оф. документации)

В ответ мы получим данные в виде XML документа примерного вида:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<corporateItemDtoes>
    <corporateItemDto>
        <id>b5909f4b-bff1-4b80-bb42-0932e23e12cf</id>
        <parentId>1e1dab62-6074-4f80-8ffb-e9ad4d8ff80c</parentId>
        <code>1</code>
        <name>Ресторан 1</name>
        <type>DEPARTMENT</type>
        <taxpayerIdNumber>1111111111</taxpayerIdNumber>
    </corporateItemDto>
    …
</corporateItemDtoes>

Из списка corporateItemDtoes нас интересуют сущности структуры corporateItemDto с type DEPARTMENT. Именно их мы будем использовать в TARGControl в качестве локаций. Запомним id сущности, он нам пригодится далее для получения отчета по выручке.

2) Подготовка датасетов в TARGControl

После того как мы синхронизировали локации, в TARGControl создадим датасеты для выручки и количества чеков и наполним их данными из iiko.

3) Получение почасовой выручки и чеков через OLAP-отчеты

Для выгрузки показателей используем API построения OLAP-отчетов iiko.

Чтобы получить список полей доступных для агрегации, группировки и фильтрации выполним запрос:

GET {{baseUrl}}/resto/api/v2/reports/olap/columns?key={{key}}&reportType=SALES

Здесь в качестве параметра передаем reportType со значением SALES, чтобы получить поля отчет по продажам.

В ответ получаем JSON со списком полей. Для нашей задачи важны следующие:

{
    …
    "OpenDate.Typed": {
        "name": "Учетный день",
        "type": "DATE",
        "aggregationAllowed": false,
        "groupingAllowed": true,
        "filteringAllowed": true,
        "tags": [
            "Время"
        ]
    },
    …
    "HourOpen": {
        "name": "Час открытия",
        "type": "STRING",
        "aggregationAllowed": false,
        "groupingAllowed": true,
        "filteringAllowed": true,
        "tags": [
            "Время"
        ]
    },
    …
    "DishSumInt": {
        "name": "Сумма без скидки",
        "type": "MONEY",
        "aggregationAllowed": true,
        "groupingAllowed": false,
        "filteringAllowed": false,
        "tags": [
            "Оплата"
        ]
    },
    …
    "UniqOrderId": {
        "name": "Чеков",
        "type": "INTEGER",
        "aggregationAllowed": true,
        "groupingAllowed": false,
        "filteringAllowed": false,
        "tags": [
            "Заказ"
        ]
    },
    …
    "Department.Id": {
        "name": "ID подразделения",
        "type": "ID_STRING",
        "aggregationAllowed": false,
        "groupingAllowed": true,
        "filteringAllowed": true,
        "tags": [
            "Корпорация",
            "Организация"
        ]
    },
    …
}

На основании этих данных сформируем итоговый запрос для получения информации о выручке и количестве чеков для конкретной торговой точки.

Для этого выполним запрос:

POST {{baseUrl}}/resto/api/v2/reports/olap?key={{key}}

тело запроса:

{
  "reportType": "SALES",
  "buildSummary": false,
  "groupByRowFields": [
    "OpenDate.Typed",
    "HourOpen"
  ],
  "aggregateFields": [
    "DishSumInt",
    "UniqOrderId"
  ],
  "filters": {
    "OpenDate.Typed": {
      "filterType": "DateRange",
      "periodType": "CUSTOM",
      "from": "2026-02-01T00:00:00.000", 
      "to": "2026-02-07T00:00:00.000" 
    },
    "Department.Id": {
      "filterType": "IncludeValues",
      "values": ["b5909f4b-bff1-4b80-bb42-0932e23e12cf"]
    },
  "DeletedWithWriteoff": {
      "filterType": "IncludeValues",
      "values": ["NOT_DELETED"]
    },
   "OrderDeleted": {
      "filterType": "IncludeValues",
      "values": ["NOT_DELETED"]
    }
  }
}

В качестве ответа получим данные по часам:

{
    "data": [
        {
            "DishSumInt": 3570,
            "HourOpen": "09",
            "OpenDate.Typed": "2026-02-01",
            "UniqOrderId": 2
        },
        {
            "DishSumInt": 6530,
            "HourOpen": "10",
            "OpenDate.Typed": "2026-02-01",
            "UniqOrderId": 4
        },
        {
            "DishSumInt": 8825,
            "HourOpen": "11",
            "OpenDate.Typed": "2026-0201",
            "UniqOrderId": 5
        },
        …
        {
            "DishSumInt": 13205,
            "HourOpen": "20",
            "OpenDate.Typed": "2026-02-10",
            "UniqOrderId": 9
        },
        {
            "DishSumInt": 18405,
            "HourOpen": "21",
            "OpenDate.Typed": "2026-02-10",
            "UniqOrderId": 12
        },
        {
            "DishSumInt": 3230,
            "HourOpen": "22",
            "OpenDate.Typed": "2026-02-10",
            "UniqOrderId": 3
        }
],
    "summary": []
}

Значения OpenDate.Typed и HourOpen объединяем и получаем дату и время 2026-02-01T09:00:00.000+03:00. Соответственно в этот час было проведено 2 чека на общую сумму выручки 3570 у.е.

Таким образом, OLAP API iikoServer позволяет стабильно забирать почасовую выручку и количество чеков в разрезе локаций (DEPARTMENT). Эти данные загружаются в датасеты TARGControl и дальше используются как вход для прогнозирования нагрузки, расчета потребности в персонале, формирования и корректировки смен в WFM-контуре.

Вывод: что дает связка WFM + iiko для ресторанов

Интеграция WFM с iiko решает прикладную задачу: поднять почасовой контур спроса (чеки/выручка) из POS и превратить его в управляемый вход для планирования смен. На практике это позволяет уйти от ситуации, когда график строится «по ощущению» или «по среднему дню», и перейти к модели, где расписание проверяется и корректируется в метриках бизнеса: продажи ↔ часы ↔ ФОТ.

Ключевой результат интеграции — не сам факт выгрузки отчета, а то, что появляется общий язык данных для WFM-управления:

  • единая разметка времени (дата+час как базовый ключ);

  • разрез по локациям (DEPARTMENT как идентификатор ресторана);

  • два основных драйвера для временных рядов (выручка и транзакции), которые устойчиво считаются и удобно прогнозируются.

Что важно учесть при промышленной эксплуатации:

  • Качество мастер-данных: стабильные ID локаций, единые правила сопоставления, отсутствие дубликатов.

  • Согласование календаря и часовых зон: одинаковая интерпретация “учетного дня”, времени открытия, переходов суток.

  • Семантика метрик: что именно считается выручкой (до/после скидок, возвраты), что считается транзакцией (уникальный чек vs заказ), как фильтруются удаленные/списанные записи.

  • Регулярность и инкрементальная загрузка: как часто обновляем данные (час/день), как догружаем поздние правки, как контролируем полноту.

Почему это “фундамент WFM”, а не просто отчетность:
WFM опирается на динамику: чтобы прогноз работал, нужны регулярные временные ряды; чтобы план-факт был честным — нужны единые правила времени и фильтрации; чтобы управлять пиками — нужен быстрый пересчет потребности и механизм закрытия отклонений. POS-контур iiko дает именно эту базу: спрос становится измеримым и сравнимым с трудозатратами.

Итоговая рамка для HoReCa

Связка TARGControl WFM + iiko не “отменяет” дефицит персонала. Она делает дефицит управляемым:

  • видно, где именно возникают провалы по часам и локациям;

  • можно связать их с продажами и стоимостью часов;

  • появляется технический контур, который поддерживает прогноз → план → факт → корректировки, а не разрозненные Excel-таблицы и ручные обзвоны.