# Отладка обмена с 1С: логи, зависшие сессии, повторный импорт

URL: https://dmeshcheryakov.ru/blog/bitrix-1c-exchange-debug/
Раздел: 1С-Битрикс
Теги: 1С-Битрикс, Интеграции, Каталог, Администрирование
Опубликовано: 2026-10-07
Обновлено: 2026-10-07
Автор: Дмитрий Мещеряков (https://dmeshcheryakov.ru)

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

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

Каждая из них лечится по-своему, и перебор настроек в админке не приближает ни к одной. Работает другое — чтение источников в жёстко заданном порядке.

Порядок здесь не педантизм. Он экономит часы: восемь из десяти «неразрешимых» проблем закрываются на втором шаге, где выясняется, что спорного поля не было в самой выгрузке, и весь дальнейший разговор про настройки сайта не имеет смысла.

## Что такое отладка обмена

Отладка обмена — это восстановление цепочки «1С отправила → сайт принял → сайт разобрал → данные изменились» с определением звена, где цепочка порвалась. Не поиск правильной галочки, а сужение области поиска: каждый источник отвечает ровно на один вопрос и либо снимает подозрение с целого куска системы, либо указывает на него.

Источников четыре, и они читаются в этом порядке.

| № | Источник | Отвечает на вопрос |
|---|---|---|
| 1 | Лог веб-сервера | 1С вообще приходила? |
| 2 | XML в `/upload/1c_catalog/` | Что она прислала? |
| 3 | Журнал обмена Битрикса | Что он с этим сделал? |
| 4 | Лог ошибок PHP | Почему упал? |

## Источник 1: приходила ли 1С

```bash
# Все запросы обмена за сегодня
grep "1c_exchange" /var/log/nginx/access.log | tail -50

# Только коды ответа и режимы — компактная картина цикла
grep "1c_exchange" /var/log/nginx/access.log \
  | awk '{print $4, $7, $9}' \
  | sed 's/.*mode=\([a-z]*\).*" \([0-9]*\)/\1 \2/' \
  | tail -30
```

Что здесь видно сразу:

**Запросов нет вообще.** Сайт ни при чём. Вопрос к регламентному заданию в 1С или к сети между ними. Разговор с администратором 1С начинается с этой строки, а не с обсуждения настроек Битрикса.

**Есть `checkauth` с кодом 401.** Права. Пользователь обмена заблокирован, сменился пароль или его выкинули из группы.

**Цепочка обрывается на `file`.** Файл не долез. Смотрите права на запись в `/upload/1c_catalog/` и `client_max_body_size` в nginx — второе особенно вероятно, если каталог недавно вырос.

**Десятки одинаковых `mode=import` подряд.** Тот самый бесконечный `progress`, к которому мы вернёмся отдельно.

Приёмы разбора логов по датам и кодам ответа подробнее разобраны в статье про [анализ логов nginx и Apache](/blog/apache-nginx-logs-analysis).

## Источник 2: что именно приехало

Здесь закрывается большинство споров. XML-файлы лежат в `/upload/1c_catalog/` до следующего обмена, и это **единственный достоверный источник** того, что было отправлено. Админка показывает результат разбора — то есть уже интерпретацию.

```bash
cd /home/site/www/upload/1c_catalog/
ls -la --time-style=full-iso

# Дата формирования и версия схемы — первое, на что смотрим
head -c 400 import.xml

# Есть ли в выгрузке конкретный товар
grep -c "SM-1024" import.xml

# Сколько всего товаров в файле
grep -c "<Товар>" import.xml
```

Дальше — точечная проверка спорного товара. Кириллические теги здесь работают на нас:

```bash
# Вырезать блок одного товара по артикулу с контекстом
grep -A 40 "<Артикул>SM-1024</Артикул>" import.xml
```

**Дата изменения файла — половина диагноза.** Файл вчерашний, а обмен «шёл сегодня ночью» — значит, сегодняшний обмен не дошёл до шага `file`, и вы смотрите на позавчерашние данные. Эта проверка занимает секунду и регулярно закрывает вопрос целиком.

**Не открывайте многогигабайтный `import.xml` в редакторе.** Ни в консольном, ни тем более по SFTP. Каталоги на 100–200 тысяч товаров дают файлы, которые кладут и редактор, и терминал, а на сервере с ними ещё и память съедается. Работайте `grep`, `head`, `sed -n '1000,1100p'` — этого достаточно для любой диагностики.

## Источник 3: журнал обмена Битрикса

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

Поэтому журнал включают заранее, на этапе настройки обмена, вместе с ротацией:

```bash
# /etc/logrotate.d/bitrix-1c-exchange
/home/site/www/upload/1c_exchange.log {
    weekly
    rotate 8
    compress
    missingok
    notifempty
    copytruncate
}
```

Без ротации журнал обмена — это будущий инцидент «на сервере кончилось место», и произойдёт он через несколько месяцев, когда про включённое логирование все забудут.

## Источник 4: почему упал

```bash
# Ошибки PHP за время обмена
tail -200 /var/log/php-fpm/error.log | grep -iE "fatal|memory|timeout"

# Классика жанра для больших каталогов
grep -i "allowed memory size" /var/log/php-fpm/error.log | tail
```

Два характерных диагноза:

**`Allowed memory size exhausted`.** Шаг импорта пытается держать в памяти слишком много. Правильный ответ — уменьшить размер порции в настройках обмена. Поднимать `memory_limit` можно, но это отодвигает проблему, а не решает: каталог продолжит расти.

**Обрыв без записи в лог PHP.** Скорее всего, соединение закрыл веб-сервер по своему таймауту, а PHP при этом продолжал работать. Проверяются `fastcgi_read_timeout` в nginx и `max_execution_time` в PHP. Как разделять эти два случая, подробно разобрано в статье про [диагностику PHP-FPM](/blog/php-fpm-diagnostics).

## Зависшая сессия: механика бесконечного progress

Это самая непрозрачная неисправность обмена, и она заслуживает отдельного разбора, потому что снаружи выглядит как поломка Битрикса, а формально всё работает правильно.

Напомню устройство шага из разбора [протокола обмена](/blog/bitrix-1c-exchange-commerceml): импорт пошаговый, и позиция, на которой он остановился, **хранится в сессии**. Ответ `progress` означает «я обработал порцию, приходи ещё за продолжением».

Теперь представим, что 1С не подставляет сессионную куку из ответа `checkauth`. Что происходит:

```
Запрос 1 → новая сессия A → прогресс 0    → обработано 500 → progress
Запрос 2 → новая сессия B → прогресс 0    → обработано 500 → progress
Запрос 3 → новая сессия C → прогресс 0    → обработано 500 → progress
...
```

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

Как убедиться, что дело именно в этом:

```bash
# Смотрим, приходит ли кука в запросах импорта.
# В логе её видно, только если формат лога включает $http_cookie;
# если нет — временно добавьте отдельный формат для этого location
grep "mode=import" /var/log/nginx/access.log | tail -5
```

Три причины потери сессии, в порядке частоты:

**1С не сохраняет куку.** Ошибка настройки на стороне 1С или обмен настроен по устаревшей схеме.

**Смена домена или протокола на редиректе.** 1С ходит на `http://site.ru`, сайт редиректит на `https://www.site.ru`, кука остаётся на другом домене. Проверяется одной командой:

```bash
curl -sI "http://site.ru/bitrix/admin/1c_exchange.php?type=catalog&mode=checkauth" | head -3
# Ищем 301/302 — их быть не должно, 1С обязана ходить на конечный адрес
```

**Балансировщик без липких сессий.** Несколько бэкендов, файловое хранилище сессий, каждый запрос попадает на другой сервер. Лечится общим хранилищем сессий или закреплением обмена за одним бэкендом.

## Повторный импорт руками

Иногда нужно перезапустить разбор уже лежащего на сайте файла — например, после того как вы поправили сопоставление свойств. Полный цикл обмена ради этого гонять не обязательно.

```bash
# 1. Авторизация, сохраняем куки в файл
curl -s -c /tmp/1c.jar -u "exchange1c:password" \
  "https://site.ru/bitrix/admin/1c_exchange.php?type=catalog&mode=checkauth"

# 2. Импорт с той же кукой, повторяем до success
for i in $(seq 1 200); do
  RESP=$(curl -s -b /tmp/1c.jar -c /tmp/1c.jar \
    "https://site.ru/bitrix/admin/1c_exchange.php?type=catalog&mode=import&filename=import.xml")
  echo "[$i] $(echo "$RESP" | head -1)"
  echo "$RESP" | head -1 | grep -q "^success" && break
  echo "$RESP" | head -1 | grep -q "^failure" && break
done
```

Ключевая деталь — `-c` вместе с `-b`: куки не только отправляются, но и обновляются. Без этого вы своими руками воспроизведёте зависшую сессию из предыдущего раздела.

**Это настоящий импорт со всеми последствиями.** Он изменит цены, остатки и активность элементов ровно так же, как обмен из 1С — включая деактивацию товаров, которых нет в файле, если такая настройка включена. На боевом сайте запускается только после бэкапа базы и с пониманием, что лежит в файле. Отлаживают на копии — той же, на которой проверяют обновления Битрикса.

## Симптом → причина → проверка

| Симптом | Вероятная причина | Чем проверить |
|---|---|---|
| Нет запросов в логе | 1С не запускалась или не дошла | `grep 1c_exchange access.log` |
| `checkauth` возвращает 401 | Права пользователя обмена | `curl -u` вручную |
| Обрыв на `mode=file` | Права на папку, `client_max_body_size` | `ls -la upload/1c_catalog/` |
| Бесконечный `progress` | Потеряна сессия | Редиректы, куки в запросах |
| `failure` без деталей | Память или права | `error.log`, вторая строка ответа |
| Обмен успешен, данных нет | Поля нет в XML | `grep` по артикулу в `import.xml` |
| Данные в базе, но не на сайте | Кэш каталога | Сброс кэша, [политика кэширования](/blog/bitrix-catalog-cache-policy) |
| Цены не обновились | Тип цены не сопоставлен | Сопоставление в настройках обмена |
| Обмен идёт часами | Обработчик на каждом элементе | Профилирование, [события](/blog/bitrix-events) |
| Товары продублировались | Затёрт `XML_ID` | Сравнение `XML_ID` с `<Ид>` в XML |

## Итоги

**Порядок источников важнее знания настроек.** Лог сервера → XML → журнал обмена → лог PHP. Нарушение порядка означает, что вы правите настройки сайта в ситуации, где 1С не приходила вовсе.

**XML — единственный достоверный источник того, что прислали.** Спор «мы выгрузили, у вас не приехало» разрешается одним `grep` по артикулу, а не созвоном на сорок минут.

**Журнал обмена включайте заранее и с ротацией.** Включённый после аварии, он бесполезен; включённый без ротации — сам станет следующей аварией.

**Бесконечный `progress` — это сессия, а не Битрикс.** Три причины: 1С не хранит куку, редирект между доменами, балансировщик без липких сессий.

**Повторный импорт руками — рабочий инструмент, но с полными последствиями.** С `-b` и `-c` одновременно, после бэкапа, желательно не на бою.

Наблюдение напоследок. Тяжелее всего диагностируются не падения, а обмены, которые проходят успешно и ничего не меняют. Падение оставляет след в логе, а молчаливое игнорирование несопоставленного свойства — нет. Поэтому первый вопрос при «обмен прошёл, но ничего не изменилось» — не «что сломалось», а «а это поле вообще приезжало». В большинстве случаев ответ отрицательный, и искать на сайте нечего.