ИИ в снабжении: заявки, счета и сверка номенклатуры

Как устроен разбор прайсов и счетов, почему поиск по номенклатуре 1С ломается из-за латинской «С» в русском слове и как матчинг дообучается на архиве закупок.

51 прайс от поставщиков. Часть — нормальные Excel-файлы. Часть — PDF. Часть — фотографии распечатки, снятые на телефон и присланные в WhatsApp.

Снабженец сводит это в одну таблицу руками. Потом сверяет каждую строку с номенклатурой в 1С. Потому что «Цемент М500 50 кг» и «Цемент портландский М-500, меш. 50кг» — это, вообще-то, одно и то же, а компьютер об этом не догадывается.

Мы такой сервис сделали, он работает в проде у отдела снабжения строительной группы компаний, и им пользуются каждый день. Расскажу, из чего он состоит и где мы набили шишки, — потому что закупки автоматизируются не там, где кажется.

Что реально съедает время

Спросите снабженца, на что уходит день. Ответ будет не «выбор поставщика». День уходит на другое:

  • перебить чужие таблицы в свою;
  • выяснить, та же это труба или другая;
  • найти позицию, которая в 1С называется иначе;
  • перенести итог в учётную систему руками.

Собственно решение — какой поставщик лучше — занимает минуты. Остальное рутина. Её и надо снимать.

Прайсы приходят как попало

Первое, что должен уметь сервис, — разбирать чужие файлы без предварительной подготовки. Шапка на четвёртой строке, объединённые ячейки, колонка «Цена» называется «Стоимость с НДС», а поставщик не указан нигде, кроме имени файла.

Парсер ищет шапку сам и понимает синонимы колонок:

  • материал — наименование, номенклатура, позиция, товар, ТМЦ;
  • цена — стоимость, прайс, цена с НДС, цена за единицу;
  • срок — поставка, отгрузка, срок в днях, «под заказ»;
  • поставщик — берём из колонки, а нет колонки — вытаскиваем из имени файла.

Звучит просто. На деле именно эта часть даёт больше всего мелких сбоев, и доводить её приходится недели две на живых файлах.

Отдельная боль — единицы измерения. Метр погонный, штука, упаковка на 6 метров, тонна. Сравнивать позиции в разных единицах нельзя, а поставщики про это не думают. Приводим всё к общей единице и помечаем, где пересчитали. Иначе сравнение врёт, причём не на проценты, а в разы.

Сканы: OCR нужен реже, чем думают

Про то, как ИИ читает сканы, любят рассказывать первым делом. По факту это самая переоценённая часть.

Мы прогнали архив из 51 отработанного лота — заявки, конкурентные листы, счета. OCR понадобился ровно двум счетам. Остальные PDF оказались текстовыми: текст в них лежит внутри файла, его надо просто вынуть библиотекой (PyMuPDF), и это быстро и точно.

Порядок такой. Сначала достаём текстовый слой. Не вышло — тогда зовём Tesseract. Русскую модель берём из набора tessdata_best. На tessdata_fast мы потеряли пару дней: движок молча спотыкается, откатывается на английский и выдаёт латинскую кашу. Ошибки в логах нет. Результат — мусор.

Фото с телефона надо подготовить, прежде чем скармливать движку:

  • перевести в чёрно-белый;
  • увеличить в два раза;
  • прогнать автоконтраст.

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

Ловушка гомоглифов

Теперь про грабли, ради которых стоило писать эту статью. В выгрузке номенклатуры из 1С 571 позиция числилась как «нет у поставщиков». Товар у поставщиков был.

Оказалось, что названия набраны вперемешку кириллицей и латиницей:

Как выглядитЧто внутриИтог
Сгонлатинская C вместо русской «С»поиск не находит
угольниклатинская yпозиция уходит в «не найдено»
PN16латинская N в русской строкене совпадает с номенклатурой

Глазами это не отличить вообще. Шрифт одинаковый, длина строки та же. А для компьютера «С» и «C» — разные символы, и любое сравнение проваливается молча: не ошибка, а пустой результат.

Появляются такие вещи естественно. Человек копирует кусок названия из письма, дописывает своё, переключает раскладку — и в базе навсегда остаётся гибрид. За годы работы 1С таких позиций накапливаются сотни.

Лечится это одной функцией. В словах, где встретились оба алфавита, латинские двойники переводим в кириллицу. Чисто латинские слова — VALTEC, COMPACT, PN — не трогаем, иначе сломаем нормальные названия. Гоняем её первой, до всякого поиска.

Мораль шире одной функции: перед тем как учить ИИ работать с вашими данными, данные надо посмотреть. Не «выгрузить и загрузить», а именно посмотреть — там будут дубли, пробелы в начале строк, «ё» вперемешку с «е» и номенклатура, заведённая тремя разными людьми по трём разным логикам.

Матчинг, который дообучается

Свести чужую строку с нашей позицией — сердце всей истории. Правила и нечёткое сравнение строк неплохо тянут трубы и метизы. На инструменте, электрике и расходке они сыплются. «Бита PH2x90» и «Бита РН-2 90мм» — человеку очевидно, что это одно и то же. Алгоритму нет.

Решение оказалось не в более умной модели, а в памяти. Мы взяли архив отработанных тендеров — папки с заявками, счетами и конкурентными листами — и вытащили оттуда пары «строка поставщика → наша позиция» в том виде, как их свёл живой снабженец. Стыковка шла по цене, которая в лоте уникальна, поэтому брак в память не попадал.

Из 51 лота получилось 1374 уникальные пары. Память сопоставлений выросла с 14 803 записей до 15 519 — плюс 716 новых, и почти все как раз в слабых категориях. Дальше система дообучается сама: каждая правка снабженца («нет, это не тот кабель») сохраняется и в следующий раз применяется автоматически.

Важная деталь про конфликты: когда одна и та же строка в разных лотах сведена к разным позициям, мы решаем голосованием, а спорные случаи не трогаем вовсе. Тихо «угадывать» в закупках нельзя.

Выбор поставщика: не только цена

Самое дешёвое предложение часто самое долгое. Мы считаем по каждой позиции балл, где цена весит 0.5, срок 0.3, надёжность поставщика 0.2. Веса настраиваются: у кого-то стройка горит, и срок важнее денег.

Что это даёт на реальных листах. На одном лоте выбор сервиса полностью совпал с протоколом отдела — приятно, но неинтересно. На двух других нашлись альтернативы дешевле на 82 720 ₽ и на 298 194 ₽ при сопоставимых сроках. Это не «ИИ умнее снабженца» — это человек физически не может каждый раз перепроверить 200 позиций по семи прайсам.

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

Как результат попадает в 1С

Финал цепочки — не красивый отчёт, а данные в учётной системе. Сервис пишет JSON, в котором лежит всё, что нужно 1С:

  • уникальный идентификатор позиции (уид) — чтобы 1С поняла, куда класть;
  • ключ строки заявки;
  • цена, срок поставки, ставка НДС;
  • поставщик и дата, на которую цена актуальна.

Файл 1С забирает по таймеру. Никто ничего не перебивает руками.

Формат обмена согласуйте с вашим 1С-ником до начала работ. Этот пункт любят отложить «на потом», а потом он съедает три недели. Мы согласовывали поля до первой строчки кода — и не пожалели.

Как мы это провалили в первый раз

Первый движок, который сводил строки, вышел слишком самоуверенным. Мы взяли нечёткое сравнение, выставили порог похожести и разрешили применять совпадения автоматически. На демо смотрелось отлично.

На реальном лоте вылезли «Кран шаровой 1/2» против «Кран шаровой 1/2 с американкой» — разные вещи, разница в цене заметная, а строки похожи на 92%. Автомат их склеил.

Что мы поменяли:

  • автоприменение выключили совсем. Движок предлагает, снабженец подтверждает — одним кликом;
  • совпадения ниже уверенного порога уходят в отдельный список «посмотреть глазами», а не в результат;
  • каждое подтверждение запоминается, и в следующий раз эта пара уже не спрашивается;
  • разные типоразмеры и исполнения (с американкой, под приварку, оцинкованный) вынесли в признаки, по которым позиции нельзя сливать даже при высокой похожести.

Урок простой. В закупках лучше показать снабженцу десять пар на проверку, чем молча ошибиться в одной. Доверие теряется на первой же неверной склейке, и обратно его собирать долго.

Чек-лист перед пилотом

Что стоит проверить у себя до того, как звать подрядчика:

  • Сколько поставщиков реально шлют прайсы каждый месяц? Меньше пяти — автоматизировать нечего, хватит нормального шаблона Excel.
  • В каком виде приходят файлы: Excel, PDF, фото, письма в теле сообщения?
  • Есть ли у вас справочник номенклатуры, или позиции заводят прямо в заявке?
  • Прогоняли ли номенклатуру на гомоглифы и дубли? Это десять минут и часто объясняет «поиск ничего не находит».
  • Кто у вас 1С-ник и готов ли он согласовать формат обмена? Без него финал цепочки не собрать.
  • Сохранился ли архив прошлых закупок — заявки, счета, конкурентные листы? Это топливо для памяти сопоставлений, и чем его больше, тем быстрее система становится полезной.

Частые вопросы

Сколько это стоит? Честно: фиксированного прайса у нас нет, потому что объём работ зависит от состояния ваших данных. Пилот на одном участке считается после разбора: сколько поставщиков, какие форматы, есть ли справочник. Цифру называем после аудита, а не по телефону наугад.

Нужно ли менять 1С? Нет. Обмен идёт файлом, который 1С забирает по расписанию. Конфигурацию не трогаем — это принципиально, потому что доработка чужой конфигурации стоит дороже всего остального проекта.

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

Сколько ждать первого результата? Две-три недели до рабочего сравнения на ваших прайсах, если файлы типовые. Дальше несколько недель на накопление памяти сопоставлений, и качество заметно подрастает.

Где это не работает

Не ждите результата, если у вас нет номенклатуры. Когда позиции заводят как попало прямо в заявке, сопоставлять не с чем: сначала наведите порядок в справочнике. И делают это ваши люди, а не подрядчик. Месяц-полтора минимум.

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

Про качество матчинга скажу прямо: на старте, до накопления памяти, руками приходится править заметную часть позиций. Первые недели это выглядит как «а что тут автоматизировали». Кривая идёт вверх по мере правок — и вот тут важно, чтобы у снабженца была одна кнопка на исправление, а не форма на десять полей. Иначе он просто не будет её нажимать, и система не научится.

И последнее: цену ошибки в закупках держит человек. Система готовит сравнение, показывает варианты и считает разницу. Подпись под решением ставит снабженец.

Первый шаг

Возьмите прайсы за последний месяц и посчитайте: сколько поставщиков, сколько позиций, сколько часов ушло, чтобы всё это свести. Отдельно посмотрите, какая доля файлов пришла сканами. Эти три цифры — уже готовое техзадание на пилот.

Заодно проверьте номенклатуру на гомоглифы, это делается скриптом за десять минут и часто объясняет, почему поиск «ничего не находит». Как выглядят похожие контуры на других участках — в кейсах; про то, откуда ИИ берёт правильные ответы, — в статье про базу знаний. А разбор вашего процесса закупок с оценкой, что даст эффект первым, — это AI-аудит, приходите с примерами файлов.

Хотите такой же процесс у себя?

Начните с AI-аудита: разберём процессы, покажем, где автоматизация окупится первой, и предложим сценарий внедрения.

Запросить AI-аудит Написать в Telegram