При ведении учета импортных товаров в конфигурациях 1С (например, 1С:Бухгалтерия предприятия 3.0) часто возникает необходимость проверить корректность введенных номеров грузовых таможенных деклараций (ГТД / деклараций на товары). Некорректно заполненные номера могут приводить к ошибкам при формировании книги покупок и декларации по НДС. Разберем по шагам, как построить запрос с оператором ПОДОБНО для поиска и фильтрации ошибочных номеров, а также рассмотрим важные нюансы работы с шаблонами в языке запросов 1С.
Прежде чем составлять шаблон проверки, вспомним стандартную структуру регистрационного номера таможенной декларации. Согласно правилам заполнения (Решение КТС № 257), номер состоит из трех основных блоков, разделенных косой чертой (слешем), и опционального четвертого блока (номер товара):
ДДММГГ;/1, /01 или /001).Таким образом, базовый формат номера имеет вид XXXXXXXX/XXXXXX/XXXXXXX, а расширенный с номером позиции товара — XXXXXXXX/XXXXXX/XXXXXXX/ХХ.
В языке запросов 1С оператор ПОДОБНО поддерживает спецсимволы и диапазоны, аналогичные регулярным выражениям SQL. Для проверки того, что на определенной позиции стоит именно цифра, используется конструкция [0-9]. Каждая пара квадратных скобок задает проверку ровно одного символа.
Рассмотрим пример запроса, который проверяет список номеров ГТД на соответствие заданным шаблонам и выводит признак корректности:
ВЫБРАТЬ
Т.Ссылка КАК НомерГТД,
ВЫБОР
КОГДА Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]"
ИЛИ Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9]"
ИЛИ Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9]"
ИЛИ Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9]"
ТОГДА "Корректный"
ИНАЧЕ "Не соответствует формату"
КОНЕЦ КАК Статус
ИЗ
Справочник.НомераГТД КАК Т
Если требуется отобрать только ошибочные записи, перенесем условие проверки в секцию ГДЕ с отрицанием НЕ:
ВЫБРАТЬ
Т.Ссылка КАК Ссылка,
Т.Код КАК НомерГТД
ИЗ
Справочник.НомераГТД КАК Т
ГДЕ
НЕ (Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]"
ИЛИ Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9]"
ИЛИ Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9]"
ИЛИ Т.Код ПОДОБНО "[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9][0-9][0-9][0-9][0-9]/[0-9][0-9][0-9]")
Проанализируем технические нюансы, с которыми можно столкнуться при использовании оператора ПОДОБНО:
ПОДОБНО проверяет только то, что во втором блоке находятся 6 цифр, но не может проверить их семантическую корректность. Например, номер с ошибочной датой 999999 пройдет проверку шаблона, так как состоит из цифр.ПОДОБНО и условий НЕ (...) не использует индексы базы данных и приводит к полному сканированию таблицы (Table Scan). На справочниках с миллионами записей такой запрос может выполняться длительное время.Если требуется глубокая проверка с контролем даты и структуры, оптимально использовать встроенный язык 1С после базовой выборки данных. Разберем пример процедуры, которая разделяет номер на составляющие с помощью СтрРазделить и валидирует части:
Функция НомерГТДКорректен(Знач СтрокаНомера) Экспорт
СтрокаНомера = СокрЛП(СтрокаНомера);
ЧастиНомера = СтрРазделить(СтрокаНомера, "/");
// В номере должно быть 3 или 4 блока
Если ЧастиНомера.Количество() <> 3 И ЧастиНомера.Количество() <> 4 Тогда
Возврат Ложь;
КонецЕсли;
// Проверка длины блоков: 8 знаков, 6 знаков, 7 знаков
Если СтрДлина(ЧастиНомера[0]) <> 8
Или СтрДлина(ЧастиНомера[1]) <> 6
Или СтрДлина(ЧастиНомера[2]) <> 7 Тогда
Возврат Ложь;
КонецЕсли;
// Проверка 4-го блока (номер товара: от 1 до 3 знаков)
Если ЧастиНомера.Количество() = 4 И (СтрДлина(ЧастиНомера[3]) < 1 Или СтрДлина(ЧастиНомера[3]) > 3) Тогда
Возврат Ложь;
КонецЕсли;
Возврат Истина;
КонецФункции
Такой комбинированный подход позволяет быстро найти грубые ошибки форматов на уровне запроса и выполнить точечную проверку данных средствами встроенного языка.