Каждый технический специалист или опытный пользователь систем на платформе «1С:Предприятие 8» рано или поздно сталкивается со странным поведением поиска в списках. Типичный сценарий: пользователь пытается найти элемент справочника или документ в динамическом списке, нажимает горячие клавиши Ctrl+F (или использует стандартное поле быстрого поиска), вводит строку поиска, но система ничего не находит. В то же время, если открыть форму расширенного поиска по клавишам Alt+F, те же самые элементы мгновенно обнаруживаются.
Ситуация становится еще более загадочной, если выясняется, что новые элементы, созданные пользователями вручную, отлично находятся обоими способами, а данные, загруженные ранее сторонними обработками или в ходе интеграции, упорно игнорируются быстрым поиском. В этой статье мы подробно разберем внутреннюю кухню работы механизмов поиска платформы «1С:Предприятие», выясним первопричину такого поведения и рассмотрим все возможные пути решения проблемы.
Для того чтобы понять, почему один поиск работает, а другой игнорирует данные, проанализируем, какие именно алгоритмы платформа 1С запускает при использовании разных горячих клавиш.
Быстрый поиск (Ctrl+F) ориентирован в первую очередь на скорость работы. В современных конфигурациях 1С, особенно в управляемых формах, динамические списки отображают огромные массивы информации. Чтобы при вводе каждого символа система не «замораживала» интерфейс, отправляя тяжелые запросы к СУБД, платформа использует встроенный механизм полнотекстового поиска данных (ППД). Когда в свойствах динамического списка заполнена «Основная таблица» (например, Справочник.Номенклатура), платформа перенаправляет поисковый запрос из строки Ctrl+F не к таблицам базы данных SQL, а к предварительно построенному и проиндексированному файловому кэшу полнотекстового поиска. Если данный индекс поврежден, устарел или не содержит сведений о конкретных записях, то Ctrl+F вернет пустой результат.
Расширенный поиск (Alt+F) устроен совершенно иначе. Этот механизм предназначен для точечной фильтрации данных по конкретным колонкам. При его вызове платформа полностью игнорирует полнотекстовый индекс. Вместо этого она транслирует запрос напрямую к СУБД (будь то MS SQL Server, PostgreSQL или файловая база данных), преобразуя поисковую строку в SQL-конструкцию со стандартным оператором сравнения ПОДОБНО (в SQL-синтаксисе это оператор LIKE). База данных обращается к актуальным физическим таблицам, поэтому расширенный поиск всегда гарантированно находит актуальные данные, даже если они были записаны секунду назад и еще не успели попасть в индекс ППД.
Особое внимание следует уделить моменту массового наполнения базы данных. Как показывает практика, проблема «невидимости» данных для Ctrl+F часто возникает после работы внешних обработок переноса или загрузки данных. Почему так происходит?
При написании обработок загрузки разработчики ради ускорения процесса записи тысяч объектов часто используют специальный режим:
НовыйОбъект = Справочники.Контрагенты.СоздатьЭлемент();
// Заполнение реквизитов объекта
НовыйОбъект.ОбменДанными.Загрузка = Истина;
НовыйОбъект.Записать();
Установка свойства ОбменДанными.Загрузка = Истина отключает выполнение стандартных платформенных и прикладных обработчиков событий (таких как ПередЗаписью, ПриЗаписи), а также оптимизирует запись на уровне СУБД. Обратной стороной медали является то, что при определенных условиях или сбоях в транзакциях платформа может «забыть» зарегистрировать измененные и добавленные объекты в специальной таблице регистрации изменений для полнотекстового поиска. В результате эти элементы физически существуют в базе данных, но очередь на их индексацию остается пустой. Именно поэтому ручное создание нового элемента в интерфейсе программы решает проблему только локально для этой конкретной новой записи — стандартный интерактивный сеанс корректно регистрирует объект, и он мгновенно индексируется.
Рассмотрим последовательность действий, которые помогут восстановить корректную работу поиска Ctrl+F в динамических списках.
Большинство пользователей и администраторов при возникновении проблем с поиском запускают регламентное задание по обновлению индекса. Однако, если элементы не были зарегистрированы в очереди на индексацию (как в случае с загрузкой данных), обычное обновление не принесет результатов, так как система считает, что обновлять нечего. Требуется провести полную очистку и переиндексацию.
Важное предупреждение: процесс полного построения индекса на крупных информационных базах (объемом в сотни гигабайт) может занять от нескольких часов до суток. В этот период производительность сервера может снизиться, поэтому операцию рекомендуется выполнять во внерабочее время.
Если информационная база слишком велика, а полное перестроение индекса заблокирует работу пользователей на долгое время, мы можем принудительно заставить платформу зарегистрировать для индексации только конкретный справочник или документы. Для этого напишем и запустим простую внешнюю обработку, которая программно перезапишет нужные элементы в обычном режиме (без флага загрузки):
Выборка = Справочники.Номенклатура.Выбрать();
Пока Выборка.Следующий() Цикл
ОбъектНоменклатуры = Выборка.ПолучитьОбъект();
// Отключаем режим загрузки, чтобы сработали все стандартные механизмы регистрации
ОбъектНоменклатуры.ОбменДанными.Загрузка = Ложь;
Попытка
ОбъектНоменклатуры.Записать();
Исключение
ЗаписьЖурналаРегистрации("ОшибкиИндексации", УровеньЖурналаРегистрации.Ошибка,,,
"Не удалось перезаписать объект: " + ОбъектНоменклатуры.Ссылка + " - " + ОписаниеОшибки());
КонецПопытки;
КонецЦикла;
Этот код принудительно обновит время модификации объектов и добавит их в очередь на индексацию полнотекстового поиска. После выполнения обработки достаточно запустить стандартное регламентное задание ОбновлениеИндексаППД или нажать кнопку «Обновить индекс» в настройках администрирования. Процесс займет считанные минуты, так как обрабатываться будут только элементы конкретного справочника. Для интерактивного мониторинга и регламентных операций с индексом можно использовать обработку для управления полнотекстовым поиском.
Если проблема носит регулярный характер, а высокая скорость поиска по миллионной базе не требуется (например, в справочнике содержится всего несколько тысяч элементов), мы можем изменить логику работы динамического списка непосредственно в конфигураторе, чтобы Ctrl+F всегда искал данные напрямую в СУБД.
Рассмотрим, как это сделать:
ДинамическийСписок и откроем его палитру свойств.В редких случаях, особенно в клиент-серверных вариантах работы на базе СУБД (MS SQL, PostgreSQL, IBM DB2), сбои в работе полнотекстового поиска могут быть вызваны рассинхронизацией физических таблиц или повреждением файлов базы данных. В таких ситуациях простые административные действия внутри «1С:Предприятия» могут не дать стабильного результата.
Для устранения глубоких системных ошибок выполним следующие шаги:
После проведения комплексного тестирования и исправления рекомендуется повторить Шаг 1 (очистку и перестроение индекса полнотекстового поиска) в режиме предприятия. Совместное выполнение этих процедур гарантированно восстанавливает работоспособность всех механизмов поиска в любых списках системы 1С.