При написании небольших автоматизированных тестов часто надо обойти всю конфигурацию и проверить, например, для всех форм какое-нибудь свойство. Это всё легко делается через свойство глобального контекста "Метаданные", но чтоб дорбаться до обхода реквизитов надо написать кучу вложенных циклов. При этом код становится слабочитаемым и слабомодифицируемым.
Ниже приведен небольшой модуль, который решает задачу легко и удобно. Создана специальная функция РазвернутьСтрокуОбходаМетаданных, которая может по строке типа "Метаданные.Справочники.*.Реквизиты.*" построить массив строк с перечислением всех реквизитов всех справочников. При помощи этой и нескольких других функций в экспортных функциях модуля реализованы вполне прикладные задачи - получение всех реквизитов, всех макетов, всех форм конфигурации и построение таблицы всех составных типов.
Код 1C v 8.х
Функция РазвернутьСтрокуОбходаМетаданных(СтрокаОбхода, ЗаменяемоеЗначение = "*" , ПредставлениеПоУмолчанию = "" )
Рез = Новый Массив;
ЧастиСтрокиОбхода = РазобратьСтрокуОбхода( СтрокаОбхода, ЗаменяемоеЗначение, ПредставлениеПоУмолчанию) ;
Если ЧастиСтрокиОбхода = Неопределено тогда
Рез. Добавить( СтрокаОбхода) ;
Иначе
ОбъектКоллекции = Вычислить( ЧастиСтрокиОбхода. СтрокаКоллекции) ;
РазвернутаяКоллекция = РазвернутьКоллекциюВПредставления( ОбъектКоллекции, ЧастиСтрокиОбхода. СтрокаПредставление) ;
Для каждого ЭлементРазвернутойКоллекции Из РазвернутаяКоллекция Цикл
ТекущаяСтрокаОбхода = ЧастиСтрокиОбхода. СтрокаНачало + ЭлементРазвернутойКоллекции + ЧастиСтрокиОбхода. СтрокаКонец;
МассивЭлемента = РазвернутьСтрокуОбходаМетаданных( ТекущаяСтрокаОбхода, ЗаменяемоеЗначение, ПредставлениеПоУмолчанию) ;
Для каждого ПримитивныйЭлементОбхода Из МассивЭлемента Цикл
Рез. Добавить( ПримитивныйЭлементОбхода) ;
КонецЦикла ;
КонецЦикла ;
КонецЕсли ;
Возврат Рез;
КонецФункции
Функция РазобратьСтрокуОбхода(СтрокаОбхода, ЗаменяемоеЗначение, ПредставлениеПоУмолчанию)
Если ПустаяСтрока( ЗаменяемоеЗначение) Тогда
ВызватьИсключение "Некорректное выражение заменяемого значения" ;
КонецЕсли ;
ПозицияЗамены = Найти( СтрокаОбхода, ЗаменяемоеЗначение) ;
Если ПозицияЗамены = 0 Тогда
Возврат Неопределено ;
КонецЕсли ;
СтрокаНачало = Лев( СтрокаОбхода, ПозицияЗамены - 1 ) ;
СтрокаКоллекции = СтрокаНачало;
Если Прав( СтрокаКоллекции, 1 ) = "." Тогда
СтрокаКоллекции = Лев( СтрокаКоллекции, СтрДлина( СтрокаКоллекции) - 1 ) ;
КонецЕсли ;
ПозицияОкончанияЗамены = ПозицияЗамены + СтрДлина( ЗаменяемоеЗначение) ;
ОстатокВыражения = Сред( СтрокаОбхода, ПозицияОкончанияЗамены) ;
ОткрывающаяСкобка = "[" ;
ЗакрывающаяСкобка = "]" ;
Если Найти( ОстатокВыражения, ОткрывающаяСкобка) = 1 Тогда
ОстатокВыражения = Сред( ОстатокВыражения, СтрДлина( ОткрывающаяСкобка) + 1 ) ;
ПозицияЗакрывающейСкобки = Найти( ОстатокВыражения, ЗакрывающаяСкобка) ;
Если ПозицияЗакрывающейСкобки = 0 Тогда
ВызватьИсключение "Синтаксическая ошибка разбора выражения" ;
КонецЕсли ;
СтрокаПредставление = Лев( ОстатокВыражения, ПозицияЗакрывающейСкобки - 1 ) ;
ОстатокВыражения = Сред( ОстатокВыражения, ПозицияЗакрывающейСкобки + СтрДлина( ЗакрывающаяСкобка) ) ;
Иначе
СтрокаПредставление = ПредставлениеПоУмолчанию;
КонецЕсли ;
СтрокаКонец = ОстатокВыражения;
Рез = Новый Структура( "ПозицияЗамены, СтрокаНачало, СтрокаКоллекции, СтрокаПредставление, СтрокаКонец" ,
ПозицияЗамены, СтрокаНачало, СтрокаКоллекции, СтрокаПредставление, СтрокаКонец) ;
Возврат Рез;
КонецФункции
Функция РазвернутьКоллекциюВПредставления(Коллекция, Знач ПредставлениеЭлемента = "" )
Если не ПустаяСтрока( ПредставлениеЭлемента) Тогда
Если Найти( ПредставлениеЭлемента, ";" ) > 0 Тогда
ВызватьИсключение "Некорректное выражение представления" ;
КонецЕсли ;
ПредставлениеЭлемента = "." + ПредставлениеЭлемента;
КонецЕсли ;
Рез = Новый Массив;
Для каждого ЭлементКоллекции Из Коллекция Цикл
ТекПредставление = Строка( Вычислить( "ЭлементКоллекции" + ПредставлениеЭлемента) ) ;
Рез. Добавить( ТекПредставление) ;
КонецЦикла ;
Возврат Рез;
КонецФункции
Функция РазвернутьМассивСтрокОбходаМетаданных(МассивСтрокОбхода, ЗаменяемоеЗначение = "*" , ПредставлениеПоУмолчанию = "Имя" )
Рез = Новый Массив;
Для каждого СтрокаОбхода Из МассивСтрокОбхода Цикл
ДополнениеРезультата = РазвернутьСтрокуОбходаМетаданных( СтрокаОбхода, ЗаменяемоеЗначение, ПредставлениеПоУмолчанию) ;
Для каждого ТекСтрока Из ДополнениеРезультата Цикл
Рез. Добавить( ТекСтрока) ;
КонецЦикла ;
КонецЦикла ;
Возврат Рез;
КонецФункции
Функция ПолучитьМассивСтрокМногострочнойСтроки(ПреобразуемаяСтрока, ИгнорироватьПустые = Истина, СокращатьПробелы = Истина)
Рез = Новый Массив;
ЧислоСтрок = СтрЧислоСтрок( ПреобразуемаяСтрока) ;
Для Сч = 1 По ЧислоСтрок Цикл
ТекСтрока = СтрПолучитьСтроку( ПреобразуемаяСтрока, Сч) ;
Если ИгнорироватьПустые и ПустаяСтрока( ТекСтрока) Тогда
Продолжить;
КонецЕсли ;
Если СокращатьПробелы Тогда
ТекСтрока = СокрЛП( ТекСтрока) ;
КонецЕсли ;
Рез. Добавить( ТекСтрока) ;
КонецЦикла ;
Возврат Рез;
КонецФункции
Функция ПолучитьВсеХранимыеРеквизитыКонфигурации() Экспорт
СтрокаВсехРеквизитов =
"
|Метаданные.Константы.*
|Метаданные.ПланыОбмена.*.Реквизиты.*
|Метаданные.ПланыОбмена.*.ТабличныеЧасти.*.Реквизиты.*
|Метаданные.Справочники.*.Реквизиты.*
|Метаданные.Справочники.*.ТабличныеЧасти.*.Реквизиты.*
|Метаданные.Документы.*.Реквизиты.*
|Метаданные.Документы.*.ТабличныеЧасти.*.Реквизиты.*
|Метаданные.Последовательности.*.Измерения.*
|Метаданные.ПланыВидовХарактеристик.*.Реквизиты.*
|Метаданные.ПланыВидовХарактеристик.*.ТабличныеЧасти.*.Реквизиты.*
|Метаданные.ПланыСчетов.*.Реквизиты.*
|Метаданные.ПланыСчетов.*.ПризнакиУчета.*
|Метаданные.ПланыСчетов.*.ПризнакиУчетаСубконто.*
|Метаданные.ПланыСчетов.*.ТабличныеЧасти.*.Реквизиты.*
|Метаданные.ПланыВидовРасчета.*.Реквизиты.*
|Метаданные.ПланыВидовРасчета.*.ТабличныеЧасти.*.Реквизиты.*
|Метаданные.РегистрыСведений.*.Измерения.*
|Метаданные.РегистрыСведений.*.Ресурсы.*
|Метаданные.РегистрыСведений.*.Реквизиты.*
|Метаданные.РегистрыНакопления.*.Измерения.*
|Метаданные.РегистрыНакопления.*.Ресурсы.*
|Метаданные.РегистрыНакопления.*.Реквизиты.*
|Метаданные.РегистрыБухгалтерии.*.Измерения.*
|Метаданные.РегистрыБухгалтерии.*.Ресурсы.*
|Метаданные.РегистрыБухгалтерии.*.Реквизиты.*
|Метаданные.РегистрыРасчета.*.Измерения.*
|Метаданные.РегистрыРасчета.*.Ресурсы.*
|Метаданные.РегистрыРасчета.*.Реквизиты.*
|Метаданные.БизнесПроцессы.*.Реквизиты.*
|Метаданные.БизнесПроцессы.*.ТабличныеЧасти.*.Реквизиты.*
|Метаданные.Задачи.*.Реквизиты.*
|Метаданные.Задачи.*.РеквизитыАдресации.*
|Метаданные.Задачи.*.ТабличныеЧасти.*.Реквизиты.*
|" ;
ВсеХранимыеРеквизитыКонфигурации = РазвернутьМассивСтрокОбходаМетаданных( ПолучитьМассивСтрокМногострочнойСтроки( СтрокаВсехРеквизитов) ) ;
Возврат ВсеХранимыеРеквизитыКонфигурации;
КонецФункции
Функция ПолучитьВсеХранимыеРеквизитыКонфигурацииСоставногоТипа() Экспорт
ВсеХранимыеРеквизитыКонфигурации = ПолучитьВсеХранимыеРеквизитыКонфигурации( ) ;
Рез = Новый ТаблицаЗначений;
Рез. Колонки. Добавить( "Имя" , Новый ОписаниеТипов( "Строка" ) ) ;
Рез. Колонки. Добавить( "Тип" , Новый ОписаниеТипов( "ОписаниеТипов" ) ) ;
Рез. Колонки. Добавить( "КоличествоПростыхТипов" , Новый ОписаниеТипов( "Число" ) ) ;
Для каждого ТекРеквизит Из ВсеХранимыеРеквизитыКонфигурации Цикл
Реквизит = Вычислить( ТекРеквизит) ;
Тип = Реквизит. Тип;
КоличествоПростыхТипов = Тип. Типы( ) . Количество( ) ;
Если КоличествоПростыхТипов< > 1 Тогда
ТекСтрока = Рез. Добавить( ) ;
ТекСтрока. Имя = ТекРеквизит;
ТекСтрока. Тип = Тип;
ТекСтрока. КоличествоПростыхТипов = КоличествоПростыхТипов;
КонецЕсли ;
КонецЦикла ;
Возврат Рез;
КонецФункции
Функция ПолучитьВсеФормыКонфигурации() Экспорт
СтрокаВсехРеквизитов =
"
|Метаданные.ПланыОбмена.*.Формы.*
|Метаданные.КритерииОтбора.*.Формы.*
|Метаданные.ОбщиеФормы.*
|Метаданные.Справочники.*.Формы.*
|Метаданные.Документы.*.Формы.*
|Метаданные.ЖурналыДокументов.*.Формы.*
|Метаданные.Перечисления.*.Формы.*
|Метаданные.Отчеты.*.Формы.*
|Метаданные.Обработки.*.Формы.*
|Метаданные.ПланыВидовХарактеристик.*.Формы.*
|Метаданные.ПланыСчетов.*.Формы.*
|Метаданные.ПланыВидовРасчета.*.Формы.*
|Метаданные.РегистрыСведений.*.Формы.*
|Метаданные.РегистрыНакопления.*.Формы.*
|Метаданные.РегистрыБухгалтерии.*.Формы.*
|Метаданные.РегистрыРасчета.*.Формы.*
|Метаданные.БизнесПроцессы.*.Формы.*
|Метаданные.Задачи.*.Формы.*
|" ;
ВсеФормыКонфигурации = РазвернутьМассивСтрокОбходаМетаданных( ПолучитьМассивСтрокМногострочнойСтроки( СтрокаВсехРеквизитов) ) ;
Возврат ВсеФормыКонфигурации;
КонецФункции
Функция ПолучитьВсеМакетыКонфигурации() Экспорт
СтрокаВсехРеквизитов =
"
|Метаданные.ПланыОбмена.*.Макеты.*
|Метаданные.ОбщиеМакеты.*
|Метаданные.Справочники.*.Макеты.*
|Метаданные.Документы.*.Макеты.*
|Метаданные.ЖурналыДокументов.*.Макеты.*
|Метаданные.Перечисления.*.Макеты.*
|Метаданные.Отчеты.*.Макеты.*
|Метаданные.Обработки.*.Макеты.*
|Метаданные.ПланыВидовХарактеристик.*.Макеты.*
|Метаданные.ПланыСчетов.*.Макеты.*
|Метаданные.ПланыВидовРасчета.*.Макеты.*
|Метаданные.РегистрыСведений.*.Макеты.*
|Метаданные.РегистрыНакопления.*.Макеты.*
|Метаданные.РегистрыБухгалтерии.*.Макеты.*
|Метаданные.РегистрыРасчета.*.Макеты.*
|Метаданные.БизнесПроцессы.*.Макеты.*
|Метаданные.Задачи.*.Макеты.*
|" ;
ВсеМакетыКонфигурации = РазвернутьМассивСтрокОбходаМетаданных( ПолучитьМассивСтрокМногострочнойСтроки( СтрокаВсехРеквизитов) ) ;
Возврат ВсеМакетыКонфигурации;
КонецФункции