Работа со штрихкодами в 1С:Предприятии 7.7 (особенно в типовых конфигурациях вроде «Торговля и Склад 9.2») — это классическая задача, которая часто вызывает трудности у начинающих разработчиков. Одной из типичных проблем является ситуация, когда функция поиска товара возвращает результат, отличный от ожидаемого, или когда код внутри условия Если ... Тогда попросту не выполняется, хотя логически должен. Рассмотрим подробнее, как устроена функция глПолучитьТоварПоШтрихкоду, разберем причины «молчания» программы и выясним, как правильно отладить этот процесс.
Прежде всего, проанализируем код стандартной функции. Она предназначена для того, чтобы по переданной строке штрихкода найти соответствующий элемент в справочнике «Номенклатура» (через справочник «Единицы») и вернуть заполненные ссылки на товар, единицу измерения и количество. Это особенно важно для весовых товаров, где количество «зашито» в самом коде.
Посмотрим на пример кода функции, который часто становится источником ошибок из-за множественных точек выхода:
Функция глПолучитьТоварПоШтрихкоду(пШтрихкод, пТовар, пЕдиница, пКоличество) Экспорт
Перем ТоварНайден;
Штрихкод = СокрЛП(пШтрихкод);
// Проверка префикса сканера
ПрефиксШтрихкода = глПрефиксШтрихкода();
Если ПустоеЗначение(ПрефиксШтрихкода) = 0 Тогда
Если Найти(ПрефиксШтрихкода, Лев(Штрихкод, 1)) <> 0 Тогда
Штрихкод = Сред(Штрихкод, 2);
Иначе
// ОШИБКА 1: Сообщение может не выводиться, если функция вызвана в модуле проведения
Сообщить("Формат считанного штрих-кода не предназначен для товаров");
Возврат 0; // Точка выхода
КонецЕсли;
КонецЕсли;
// ... далее идет логика поиска весового или обычного товара
// ...
Возврат Рез;
КонецФункции
Основная проблема, с которой сталкиваются программисты, заключается в том, что в 1С 7.7 переменная Рез может быть не инициализирована в начале функции. Если ни одно из условий поиска не сработало, функция вернет пустое значение, которое при сравнении с числом 0 может вести себя непредсказуемо, хотя формально 0 = "" в 1С 7.7 возвращает 1 (Истина).
Если вы написали условие вида Если глПолучитьТоварПоШтрихкоду(...) = 0 Тогда Сообщить("Товар не найден"); КонецЕсли;, но сообщение не появляется, проанализируем следующие ситуации:
Возврат. Если код «вылетает» из функции раньше, чем переменная Рез получила значение 0, вызывающий код может получить неопределенный результат.ОткрытьФормуМодально), и пользователь закрывает её некорректно, выполнение может прерваться или пойти по непредусмотренному сценарию.Единицы. У реквизита ШтрихКод обязательно должен стоять признак «Сортировка». Без него метод НайтиПоРеквизиту может работать некорректно или возвращать ошибку выполнения, которая «тихо» гасится системой.Чтобы понять, где именно «теряется» управление, воспользуемся проверенными методами отладки в 1С 7.7.
Шаг 1. Использование «Жуколова» (Debugger)
Это самый надежный способ. Установите точку останова (F9) на строке вызова функции в вашем документе. Когда выполнение программы остановится, используйте клавишу F8, чтобы зайти внутрь функции. Пошагово проходя по строкам, вы увидите, в какое именно условие Если ... Тогда заходит программа и какое значение принимает переменная Рез перед выходом.
Шаг 2. Расстановка контрольных сообщений
Если отладчик по каким-то причинам недоступен (например, на терминальном сервере), используйте метод «трассировки» через Сообщить. Добавьте уникальные маркеры в каждую ветку кода:
Если Рез = 1 Тогда
Сообщить("Ветка 1: Товар найден в базе");
ИначеЕсли ИспользоватьЮнискан = 1 Тогда
Сообщить("Ветка 2: Запрос к ЮНИСКАН");
Иначе
Сообщить("Ветка 3: Ничего не найдено");
КонецЕсли;
Если после запуска вы не видите ни одного из этих сообщений, значит, функция завершается по оператору Возврат где-то в самом начале (например, из-за неверного префикса сканера).
Часто ошибка кроется в логике обработки веса. Рассмотрим пример кода, который парсит весовой штрихкод стандарта EAN-13:
// Штрихкод: 21 00001 00500 5
// 21 - префикс, 00001 - код товара, 00500 - вес (500г), 5 - контрольный разряд
ВремШтрихкод = глСформироватьШтрихкод(глПрефиксВесовогоШтрихкода, Сред(Штрихкод, 3, 5) + "00000");
Рез = ОбЕдиница.НайтиПоРеквизиту("ШтрихКод", ВремШтрихкод, 1);
Если Рез = 1 Тогда
пТовар = ОбЕдиница.Владелец;
пЕдиница = ОбЕдиница.ТекущийЭлемент();
пКоличество = Число(Сред(Штрихкод, 8, 5)) / 1000;
КонецЕсли;
Проанализируем этот фрагмент: если функция глСформироватьШтрихкод (которая обычно дополняет код контрольным символом) вернет значение, не совпадающее с тем, что записано в справочнике Единицы, переменная Рез останется равной 0. Обязательно проверьте, что именно ищет программа, выведя ВремШтрихкод в окно сообщений.
Чтобы гарантированно отловить результат, попробуйте изменить структуру вызова в документе, явно обрабатывая все варианты. Вместо краткой записи Если ... = 0, используйте полную структуру:
РезультатПоиска = глПолучитьТоварПоШтрихкоду(Данные, ВремТовар, ВремЕдиница, ВремКоличество);
Если РезультатПоиска = 1 Тогда
// Обработка найденного товара
ОбработкаПодбора(ВремТовар, ВремЕдиница, ВремКоличество);
Иначе
// Товар не найден или произошла ошибка
Сообщить("Не удалось идентифицировать штрихкод: " + Данные, "!");
КонецЕсли;
Важный совет: В 1С 7.7 параметры пТовар, пЕдиница и другие передаются по ссылке. Это означает, что если функция вернула 0, но внутри успела что-то присвоить переменной пТовар, в вызывающем модуле эта переменная перестанет быть пустой. Всегда очищайте переменные перед вызовом функции поиска, используя "" или ПолучитьПустоеЗначение("Справочник.Номенклатура").
Проблема «неработающего» условия чаще всего сводится к скрытым возвратам из функции или некорректной инициализации переменных. Используя пошаговую отладку клавишей F8 и контролируя значения префиксов, вы сможете быстро найти место, где логика программы расходится с вашими ожиданиями. Помните, что в системе 1С 7.7 важна точность каждого символа в строке штрихкода, включая пробелы и невидимые символы префиксов торгового оборудования.