Выводит на экран окно вопроса.
Синтаксис
Вопрос(<ТекстВопроса>, <Кнопки>, <Таймаут>, <КнопкаПоУмолчанию>, <Заголовок>, <КнопкаТаймаута>)Примеры платформы
Режим = РежимДиалогаВопрос.ДаНет;
Ответ = Вопрос(НСтр("ru = 'Продолжить выполнение операции?';"
+ " en = 'Do you want to continue?'"), Режим, 0);
Если Ответ = КодВозвратаДиалога.Нет Тогда
Возврат;
КонецЕсли;Полное описание, параметры и ограничения
Глобальный контекст.Вопрос (Global context.DoQueryBox)
Глобальный контекст (Global context)
Вопрос (DoQueryBox)
Доступен, начиная с версии 8.0.
Синтаксис:
Вопрос(<ТекстВопроса>, <Кнопки>, <Таймаут>, <КнопкаПоУмолчанию>, <Заголовок>, <КнопкаТаймаута>)
Параметры:
<ТекстВопроса> (обязательный)
Тип: Строка, ФорматированнаяСтрока.
Текст задаваемого вопроса.
<Кнопки> (обязательный)
Тип: РежимДиалогаВопрос, СписокЗначений.
Задает состав и текст кнопок диалога, а также, связанные с кнопками значения.
При использовании типа СписокЗначений:
Значение – содержит значение, связанное с кнопкой. Это значение является возвращаемым значением при выборе кнопки. В качестве значения может использоваться значение перечисления КодВозвратаДиалога, а также другие значения;
Представление – задает текст кнопки. Если представление не задано и в качестве значения используется значение перечисления КодВозвратаДиалога, то используется стандартное представление;
Картинка – не используется (должна быть пустой);
Пометка – не используется (должна быть пустой).
При использовании типа СписокЗначений список не должен быть пустым.
<Таймаут> (необязательный)
Тип: Число.
Интервал времени в секундах, в течение которого система будет ожидать ответа пользователя. По истечении интервала окно вопроса будет закрыто. Если параметр не указан, то время ожидания не ограничено.
Если параметр имеет отрицательное значение, будет сгенерировано исключение.
Значение по умолчанию: 0.
<КнопкаПоУмолчанию> (необязательный)
Тип: Произвольный.
Определяет кнопку по умолчанию по типу кнопки или по связанному с ней значению.
<Заголовок> (необязательный)
Тип: Строка.
Содержит заголовок окна вопроса.
Если не установлен, то у диалога заголовок не отображается.
<КнопкаТаймаута> (необязательный)
Тип: Произвольный.
Определяет кнопку (по типу кнопки или по связанному с ней значению), на которой отображается количество секунд, оставшихся до истечения таймаута.
Возвращаемое значение:
Тип: Произвольный.
В зависимости от реакции пользователя возвращается значение системного перечисления или значение, связанное с нажатой кнопкой.
В случае закрытия диалога по истечении времени ожидания возвращается значение Таймаут.
Описание:
Выводит на экран окно вопроса.
Доступность:
Тонкий клиент, мобильный клиент, толстый клиент, мобильное приложение (клиент).
Примечание:
В веб-клиенте в случае, если клавиша Esc не используется (нет кнопки, связанной со значением Отмена) и пользователь закрывает окно "крестиком", повторно открывается диалог с первоначальными параметрами.
Если для конфигурации свойство РежимИспользованияМодальности установлено в НеИспользовать, следует использовать метод ПоказатьВопрос.
Ширина всех кнопок диалога одинакова и равна ширине самой широкой кнопки.
Ширина текста в диалоге ограничена 40 символами.
Пример:
Режим = РежимДиалогаВопрос.ДаНет;
Ответ = Вопрос(НСтр("ru = 'Продолжить выполнение операции?';"
+ " en = 'Do you want to continue?'"), Режим, 0);
Если Ответ = КодВозвратаДиалога.Нет Тогда
Возврат;
КонецЕсли;
См. также:
Глобальный контекст, метод ВопросАсинх
Глобальный контекст, метод ПоказатьВопрос
Использование в версии:
Доступен, начиная с версии 8.0.
Описание изменено в версии 8.3.18.
Методическая информация
Практические примеры
Набор своего прихода: вхождениеA/AA, безопасная pending проба и подтвержденная поправка
Один полный самостоятельный маршрут собственной новой FileCF: реальные данные/штатные формы, различие отбора списка и строк и отдельное согласие на точную поправку.
Где и как запускать
Полный основной модуль: РегистрНакопления.ПриходыСчета85.Форма.НаборСчета85, обычная форма набора.
Подготовка
Вручную создайте НОВУЮ файловую ИБ по точному пути C:\1C85_OwnAccumulationInvoice\9d8a6e13-4790-4bc1-a048-84c78ae597e5\Base. Это отдельный UUID-каталог собственного опыта, не UUID рабочей ИБ. Не копируйте УТ/КА/УНФ/БП и не используйте клиент-серверную ИБ. Здесь ИБ/каталог не создавались, 1С не запускалась.
Конфигурация Уч85ПриходыСчета: в Конфигураторе выберите Сервис → Параметры → Общие → Редактирование конфигурации для режима запуска = «Управляемое приложение и обычное приложение»; свойство конфигурации ОсновнойРежимЗапуска = ОбычноеПриложение, режим совместимости Не использовать, платформа8.5.1.1343. Единственная роль УчебныйАдминистратор85: Администрирование для native списка пользователей; чтение/добавление/изменение своих документов и своего регистра, использование собственных обычных форм. Единственный пользователь Уч85Приход_9d8a6e13 получает эту роль. Нет BSP, расширений, разделителей, внешних источников и других прикладных объектов.
Создайте Документ.Приход85: проведение РАЗРЕШИТЬ; три реквизита Метка85:Строка36, Пользователь85:Строка36, КодДокумента85:Строка1; табличных частей нет. Приход85 — единственный разрешенный тип регистратора РегистрНакопления.ПриходыСчета85, он выбран в составе движений документа. Модуль документа пуст: автоматических движений, обработок проведения и подписок нет. Вручную проводятся только два своих документа, движения вводятся отдельно штатной формой регистра ДО установки fail-closed обработчика.
Создайте РегистрНакопления.ПриходыСчета85, вид регистра Остатки: одно измерение Код85:Строка10; ресурсы Количество85:Число9,0 неотрицательное и Сумма85:Число12,2 неотрицательное; реквизит Цена85:Число12,2 неотрицательное. Не добавляйте иных реквизитов, измерений, ресурсов и регистраторов. ВидДвижения читается только потому, что выбран регистр остатков; не переносите этот код в регистр оборотов.
INITIAL FIXTURE делается вручную ДО вставки Set-модуля и событий собственных форм. Сначала в своем единственном FileCF получите UUID своего реального пользователя штатным синтаксис-помощником/конфигуратором и введите его строку в Пользователь85 обоих документов; не выдумывайте UUID. Документ A: дата10.10.2026 09:00:00, КодДокумента85=A; документ B: дата10.10.2026 10:00:00, код B. Метка обоих=9d8a6e13-4790-4bc1-a048-84c78ae597e5. Запишите и проведите оба документа, пометка удаления Ложь; номера реальные штатные непустые, не предписываются фиктивные номера.
Пока fail-closed модули еще НЕ установлены, в штатной форме собственного регистра создайте по фактическому регистратору A ровно2 записи: номер1 кодA количество2 цена250 сумма500; номер2 кодAA количество1 цена250 сумма250. По фактическому регистратору B ровно1 запись: номер1 кодB количество3 цена250 сумма750. АктивностьИстина, ВидДвиженияПриход, Период ровноДата соответствующего документа. НомерСтроки readonly: не присваивайте его кодом; фактические номера проверяются после штатной записи. Проверяйте весь регистр1500 и только эти3 записи. Любая другая строка/неверный номер означает остановку, не автоматическое удаление/перепроведение.
Теперь в Конфигураторе создайте ОбщийМодуль.УчПриходыСчета85: ГлобальныйНет, СерверДа, КлиентОбычноеПриложениеДа, ВнешнееСоединениеДа, КлиентУправляемоеПриложениеНет, ВызовСервераНет, ПривилегированныйНет, повторное использование возвращаемых значений Не использовать. Вставьте полный COMMON supporting module. Он содержит только чистые проверки/чтение и не хранит общую авторизацию в Перем.
Создайте ОбщаяФорма.МаршрутПрихода85, вид Обычная: реквизит Состояние85:Строка500 только для просмотра; две обычные кнопки Список85/Набор85 с Нажатие→одноименнаяПроцедура(Кнопка), ровно1 параметр. ПриОткрытии→ПриОткрытии()0. Основной модуль Hub из первой карточки; родителем создаваемых форм является именно эта обычная форма, не control.
В РегистрНакопления.ПриходыСчета85 мастером создайте обычную форму СПИСКА СписокСчета85. Основной реквизит Список:РегистрНакопленияСписок.ПриходыСчета85; ТабличноеПоле Строки85 с Данные=Список. Состояние85:Строка500 только для просмотра, кнопка ТочныйКод85 (native Нажатие1), ПриОткрытии0. Свой список получает ровно9 штатных/подготовленных колонок кодом. Вставьте LIST main module; параметры регистратора и ключа задает настоящий Hub ДО Открыть.
Мастером создайте обычную форму НАБОРА НаборСчета85. Основной реквизит Набор:РегистрНакопленияНаборЗаписей.ПриходыСчета85; ТабличноеПоле Строки85, Данные=Набор. Состояние85:Строка500 только для просмотра; кнопки СледующийОтбор85/СвояПробнаяСтрока85/СохранитьПоправку85, каждая native Нажатие1. ПриОткрытии0, настоящее событие формы ПередЗаписью→ПередЗаписью(Отказ)1. Вставьте SET_FORM main module. Таблица только для просмотра: текущую существующую запись меняет исключительно подтвержденная собственная команда.
В МОДУЛЬ НАБОРА ЗАПИСЕЙ собственного регистра вставьте полный SET_MODULE из четвертой карточки; native событие ПередЗаписью(Отказ,Замещение)2. ЭтотОбъект существует именно здесь. После установки вся неподтвержденная запись, включая штатные кнопки/ввод fixture повторно, отказывает. События нельзя вызывать вручную; форму и объект вызывает сама native WriteInForm.
В модуль обычного приложения вставьте полный APPLICATION supporting module. Обновите свою новую конфигурацию и начните отдельный запуск толстого обычного клиента этой FileCF. Формы не вызывают неизвестные соседние уроки: все4 MAIN и полный COMMON/APP присутствуют в supporting modules каждой карточки. После успешной поправки начальный1500 уже не существует: новый просмотр этого одноразового маршрута намеренно откажет, автоматического восстановления fixture нет.
Перем Источник85, Готов85, НеизвестныйИсход85, РазрешенаЗапись85, Этап85, Токен85;
Процедура ПодтвердитьИсточник85(Переданный85) Экспорт
Если Готов85 <> Неопределено Или НеизвестныйИсход85 <> Неопределено Тогда
ВызватьИсключение "Повторный initializer не может сбросить неизвестный исход.";
КонецЕсли;
НеизвестныйИсход85 = Истина;
РазрешенаЗапись85 = Ложь;
Источник85 = УчПриходыСчета85.Источник85();
УчПриходыСчета85.СравнитьИсточник85(Переданный85, Источник85);
УчПриходыСчета85.ПроверитьНабор85(Набор, Источник85, Ложь);
Если Набор.ДополнительныеСвойства.Количество() <> 0 Тогда
ВызватьИсключение "Новый собственный набор не должен содержать чужих transient свойств.";
КонецЕсли;
Таблица85 = ЭлементыФормы.Строки85;
Если ТипЗнч(Таблица85) <> Тип("ТабличноеПоле") Или Таблица85.Данные <> "Набор" Или Таблица85.Значение <> Набор Тогда
ВызватьИсключение "Нужна настоящая обычная таблица конкретного набора.";
КонецЕсли;
Таблица85.СоздатьКолонки();
Таблица85.ИзменятьПорядокСтрок = Ложь;
Таблица85.ИзменятьСоставСтрок = Ложь;
Таблица85.ТолькоПросмотр = Истина;
Таблица85.ОбновлятьПриИзмененииОтбора = Ложь;
Таблица85.ПроверкаОтображенияНовойСтроки = ВариантПроверкиОтображенияНовойСтроки.СообщатьОНесоответствииОтбору;
Для Каждого Правило85 Из Таблица85.НастройкаОтбораСтрок Цикл
Правило85.Доступность = Ложь;
КонецЦикла;
Для Каждого Условие85 Из Таблица85.ОтборСтрок Цикл
Если Условие85.Использование Тогда
ВызватьИсключение "Не очищаем неизвестный исходный row filter.";
КонецЕсли;
КонецЦикла;
КолонкаСуммы85 = Таблица85.Колонки.Найти("Сумма85");
КолонкаКлюча85 = Таблица85.Колонки.Найти("НомерСтроки");
Если КолонкаСуммы85 = Неопределено Или КолонкаКлюча85 = Неопределено Тогда
ВызватьИсключение "Нет реальных собственных колонок суммы и номера.";
КонецЕсли;
Если КолонкаСуммы85.Данные <> "Сумма85" Или КолонкаКлюча85.Данные <> "НомерСтроки" Тогда
ВызватьИсключение "Не совпали typed bindings собственных колонок.";
КонецЕсли;
Таблица85.Подвал = Истина;
КолонкаСуммы85.ОтображатьИтогиВПодвале = Истина;
КолонкаКлюча85.ОтображатьСтандартнуюКартинку = Истина;
Этап85 = 0;
Готов85 = Истина;
НеизвестныйИсход85 = Ложь;
КонецПроцедуры
Процедура ПриОткрытии()
ПроверитьГотовность85();
ПроверитьОтбор85(Ложь, 750, 2);
КонецПроцедуры
Процедура ПроверитьГотовность85()
Если Готов85 <> Истина Или НеизвестныйИсход85 <> Ложь Или РазрешенаЗапись85 <> Ложь Тогда
ВызватьИсключение "Свой экземпляр не подготовлен или прошлый исход неизвестен.";
КонецЕсли;
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
УчПриходыСчета85.ПроверитьНабор85(Набор, Источник85, Ложь);
Если Набор.ДополнительныеСвойства.Количество() <> 0 Тогда
ВызватьИсключение "Transient разрешение не должно пережить прошлое действие.";
КонецЕсли;
КонецПроцедуры
Процедура ПроверитьОтбор85(Включен85, ОжидаемаяСумма85, ОжидаемоеЧисло85)
Таблица85 = ЭлементыФормы.Строки85;
Если Таблица85.Данные <> "Набор" Или Таблица85.Значение <> Набор
Или Таблица85.ИзменятьПорядокСтрок Или Таблица85.ИзменятьСоставСтрок
Или Не Таблица85.ТолькоПросмотр Или Таблица85.ОбновлятьПриИзмененииОтбора
Или Таблица85.ПроверкаОтображенияНовойСтроки <> ВариантПроверкиОтображенияНовойСтроки.СообщатьОНесоответствииОтбору
Или Не Таблица85.Подвал Или Не Таблица85.Колонки.Сумма85.ОтображатьИтогиВПодвале
Или Не Таблица85.Колонки.НомерСтроки.ОтображатьСтандартнуюКартинку Тогда
ВызватьИсключение "Реальные собственные политики таблицы изменены.";
КонецЕсли;
Для Каждого Правило85 Из Таблица85.НастройкаОтбораСтрок Цикл
Если Правило85.Доступность Тогда
ВызватьИсключение "Не разрешена интерактивная подмена собственных row filters.";
КонецЕсли;
КонецЦикла;
Для Каждого Условие85 Из Таблица85.ОтборСтрок Цикл
Если Условие85.Использование И Условие85.Имя <> "Код85" Тогда
ВызватьИсключение "Неизвестный активный row filter не удаляем.";
КонецЕсли;
КонецЦикла;
Если Таблица85.ОтборСтрок.Код85.Использование <> Включен85 Тогда
ВызватьИсключение "Не совпало реальное включение своего row filter.";
КонецЕсли;
ФактСумма85 = 0;
ФактЧисло85 = 0;
Для Каждого Запись85 Из Набор Цикл
Если Таблица85.ПроверитьСтроку(Запись85) Тогда
Данные85 = Таблица85.ДанныеСтроки(Запись85);
Если ТипЗнч(Данные85) <> Тип("РегистрНакопленияЗапись.ПриходыСчета85") Тогда
ВызватьИсключение "Native RowData не вернул настоящую запись своего набора.";
КонецЕсли;
Если Данные85.Регистратор <> Запись85.Регистратор Или Данные85.НомерСтроки <> Запись85.НомерСтроки
Или Данные85.Период <> Запись85.Период Или Данные85.Активность <> Запись85.Активность
Или Данные85.ВидДвижения <> Запись85.ВидДвижения Или Данные85.Код85 <> Запись85.Код85
Или Данные85.Количество85 <> Запись85.Количество85 Или Данные85.Сумма85 <> Запись85.Сумма85
Или Данные85.Цена85 <> Запись85.Цена85 Тогда
ВызватьИсключение "Нативные данные поля не совпали со всеми полями собственной записи.";
КонецЕсли;
ФактЧисло85 = ФактЧисло85 + 1;
ФактСумма85 = ФактСумма85 + Данные85.Сумма85;
КонецЕсли;
КонецЦикла;
Если ФактСумма85 <> ОжидаемаяСумма85 Или ФактЧисло85 <> ОжидаемоеЧисло85 Тогда
ВызватьИсключение "Native CheckRow/RowData не подтвердили реальное вхождение и сумму.";
КонецЕсли;
Состояние85 = "Этап=" + Строка(Этап85) + "; native строк=" + Строка(ФактЧисло85) + "; сумма=" + Строка(ФактСумма85);
КонецПроцедуры
Процедура СледующийОтбор85(Кнопка)
Если Кнопка <> ЭлементыФормы.СледующийОтбор85 Или Кнопка.Имя <> "СледующийОтбор85" Тогда
ВызватьИсключение "Нужна настоящая кнопка своей таблицы.";
КонецЕсли;
ПроверитьГотовность85();
Если Этап85 > 2 Тогда
ВызватьИсключение "Три этапа отбора уже завершены.";
КонецЕсли;
НеизвестныйИсход85 = Истина;
Попытка
Снимок85 = УчПриходыСчета85.XML85(Набор.Выгрузить());
ЭлементыФормы.Строки85.ОтборСтрок.Код85.Установить(?(Этап85 = 0, "A", "AA"), Этап85 <> 2);
ЭлементыФормы.Строки85.ОбновитьСтроки();
Этап85 = Этап85 + 1;
ПроверитьОтбор85(Этап85 < 3, ?(Этап85 = 2, 250, 750), ?(Этап85 = 2, 1, 2));
Если УчПриходыСчета85.XML85(Набор.Выгрузить()) <> Снимок85 Тогда
ВызватьИсключение "Отбор представления изменил собственный полный набор.";
КонецЕсли;
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
НеизвестныйИсход85 = Ложь;
Исключение
НеизвестныйИсход85 = Истина;
ВызватьИсключение;
КонецПопытки;
КонецПроцедуры
Процедура СвояПробнаяСтрока85(Кнопка)
Если Кнопка <> ЭлементыФормы.СвояПробнаяСтрока85 Или Кнопка.Имя <> "СвояПробнаяСтрока85" Тогда
ВызватьИсключение "Нужна настоящая кнопка пробной строки.";
КонецЕсли;
ПроверитьГотовность85();
Если Этап85 <> 3 Тогда
ВызватьИсключение "Сначала завершите свой маршрут A/AA/без отбора.";
КонецЕсли;
НеизвестныйИсход85 = Истина;
Попытка
Снимок85 = УчПриходыСчета85.XML85(Набор.Выгрузить());
ЭлементыФормы.Строки85.ОтборСтрок.Код85.Установить("AA", Истина);
Проба85 = Набор.ДобавитьПриход();
Проба85.Регистратор = Источник85.Документы[0].Ссылка;
Проба85.Период = Источник85.Документы[0].Дата;
Проба85.Активность = Истина;
Проба85.Код85 = "B";
Проба85.Количество85 = 1;
Проба85.Цена85 = 100;
Проба85.Сумма85 = Проба85.Количество85 * Проба85.Цена85;
Если Набор.Количество() <> 3 Или ЭлементыФормы.Строки85.ПроверитьСтроку(Проба85) Тогда
ВызватьИсключение "Своя pending строка B должна не соответствовать row filter AA.";
КонецЕсли;
Набор.Удалить(Проба85);
Если УчПриходыСчета85.XML85(Набор.Выгрузить()) <> Снимок85 Тогда
ВызватьИсключение "После удаления только собственной пробной строки полный набор не восстановился.";
КонецЕсли;
ЭлементыФормы.Строки85.ОтборСтрок.Код85.Использование = Ложь;
ЭлементыФормы.Строки85.ОбновитьСтроки();
УчПриходыСчета85.ПроверитьНабор85(Набор, Источник85, Ложь);
ПроверитьОтбор85(Ложь, 750, 2);
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
Этап85 = 4;
НеизвестныйИсход85 = Ложь;
Исключение
НеизвестныйИсход85 = Истина;
ВызватьИсключение;
КонецПопытки;
КонецПроцедуры
Процедура СохранитьПоправку85(Кнопка)
Если Кнопка <> ЭлементыФормы.СохранитьПоправку85 Или Кнопка.Имя <> "СохранитьПоправку85" Тогда
ВызватьИсключение "Нужна настоящая собственная кнопка записи.";
КонецЕсли;
ПроверитьГотовность85();
Если Этап85 <> 4 Тогда
ВызватьИсключение "Сначала завершите все локальные проверки; повторная запись не разрешена.";
КонецЕсли;
Если Вопрос("ТОЛЬКО своя новая FileCF. Заменить ровно две записи своего документа A: A500→250, AA250 неизменно; общий итог1500→1250?", РежимДиалогаВопрос.ДаНет) <> КодВозвратаДиалога.Да Тогда
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
УчПриходыСчета85.ПроверитьНабор85(Набор, Источник85, Ложь);
Возврат;
КонецЕсли;
ПроверитьГотовность85();
НеизвестныйИсход85 = Истина;
Токен85 = Строка(Новый УникальныйИдентификатор);
Попытка
Запись85 = Набор.Получить(0);
Если Запись85.Код85 <> "A" Или Запись85.НомерСтроки <> 1 Тогда
ВызватьИсключение "Нельзя изменять неизвестную строку.";
КонецЕсли;
Запись85.Количество85 = 1;
Запись85.Сумма85 = Запись85.Количество85 * Запись85.Цена85;
УчПриходыСчета85.ПроверитьНабор85(Набор, Источник85, Истина);
Разрешение85 = Новый Структура("Метка,Пользователь,Регистратор,Токен,Подтверждено", Источник85.Паспорт.Метка, Источник85.Паспорт.Пользователь, Источник85.Документы[0].Ссылка, Токен85, Истина);
Набор.ДополнительныеСвойства.Вставить("УчПриходРазрешение85", Разрешение85);
РазрешенаЗапись85 = Истина;
Если Не ЭтаФорма.ЗаписатьВФорме() Тогда
ВызватьИсключение "Native WriteInForm вернул False; исход неизвестен, повтор и rollback запрещены.";
КонецЕсли;
РазрешенаЗапись85 = Ложь;
Если Набор.ДополнительныеСвойства.Количество() <> 0 Тогда
ВызватьИсключение "Нативный callback не подтвердил потребление собственных transient данных.";
КонецЕсли;
Свежий85 = УчПриходыСчета85.Источник85(Истина);
Если УчПриходыСчета85.XML85(Свежий85.Документы) <> УчПриходыСчета85.XML85(Источник85.Документы) Тогда
ВызватьИсключение "Запись регистра не должна менять собственные документы.";
КонецЕсли;
УчПриходыСчета85.ПроверитьНабор85(Набор, Свежий85, Истина);
ПроверитьОтбор85(Ложь, 500, 2);
Источник85 = Свежий85;
Этап85 = 5;
НеизвестныйИсход85 = Ложь;
Состояние85 = "Полный fresh readback: свой A=500, свой B=750, общий итог1250; повтор записи запрещен.";
Исключение
РазрешенаЗапись85 = Ложь;
НеизвестныйИсход85 = Истина;
Если Набор.ДополнительныеСвойства.Свойство("УчПриходРазрешение85", Остаток85) Тогда
Если ТипЗнч(Остаток85) = Тип("Структура") Тогда
Если Остаток85.Свойство("Токен", ОстатокТокена85) И ОстатокТокена85 = Токен85 Тогда
Набор.ДополнительныеСвойства.Удалить("УчПриходРазрешение85");
КонецЕсли;
КонецЕсли;
КонецЕсли;
ВызватьИсключение;
КонецПопытки;
КонецПроцедуры
Процедура ПередЗаписью(Отказ)
Отказ = Истина;
Если РазрешенаЗапись85 <> Истина Тогда
Возврат;
КонецЕсли;
РазрешенаЗапись85 = Ложь;
Если Готов85 <> Истина Или НеизвестныйИсход85 <> Истина Или Этап85 <> 4 Тогда
ВызватьИсключение "Форма не находится в подтвержденном собственном этапе записи.";
КонецЕсли;
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
УчПриходыСчета85.ПроверитьНабор85(Набор, Источник85, Истина);
Если Не Набор.ДополнительныеСвойства.Свойство("УчПриходРазрешение85", Разрешение85)
Или ТипЗнч(Разрешение85) <> Тип("Структура") Тогда
ВызватьИсключение "Форма не передала собственные подтвержденные transient данные.";
КонецЕсли;
Если Разрешение85.Токен <> Токен85 Или Не Разрешение85.Подтверждено Тогда
ВызватьИсключение "Разрешение не совпало с собственным настоящим нажатием.";
КонецЕсли;
Отказ = Ложь;
КонецПроцедурыЧистый общий модуль проверок/чтения
Общие модули → УчПриходыСчета85; СерверДа/КлиентОбычноеПриложениеДа/ВнешнееСоединениеДа, не глобальный, не privileged, без shared Перем.
Функция Паспорт85() Экспорт
Если СтрокаСоединенияИнформационнойБазы() <> "File=""C:\1C85_OwnAccumulationInvoice\9d8a6e13-4790-4bc1-a048-84c78ae597e5\Base"";" Или Метаданные.РежимСовместимости <> Метаданные.СвойстваОбъектов.РежимСовместимости.НеИспользовать Или Метаданные.Документы.Количество() <> 1 Или Метаданные.РегистрыНакопления.Количество() <> 1 Или Метаданные.РегистрыСведений.Количество() <> 0 Или Метаданные.РегистрыБухгалтерии.Количество() <> 0 Или Метаданные.РегистрыРасчета.Количество() <> 0 Или Метаданные.Справочники.Количество() <> 0 Или Метаданные.ПланыВидовХарактеристик.Количество() <> 0 Или Метаданные.ПланыСчетов.Количество() <> 0 Или Метаданные.ПланыВидовРасчета.Количество() <> 0 Или Метаданные.Перечисления.Количество() <> 0 Или Метаданные.ОбщиеРеквизиты.Количество() <> 0 Тогда
ВызватьИсключение "Допустим только точный новый собственный FileCF без совместимости.";
КонецЕсли;
ДокМД85 = Метаданные.Документы.Найти("Приход85");
РегМД85 = Метаданные.РегистрыНакопления.Найти("ПриходыСчета85");
Если ДокМД85 = Неопределено Или РегМД85 = Неопределено Тогда
ВызватьИсключение "Не подготовлены единственные собственные прикладные объекты.";
КонецЕсли;
Если ДокМД85.Проведение <> Метаданные.СвойстваОбъектов.Проведение.Разрешить
Или ДокМД85.Движения.Количество() <> 1 Или Не ДокМД85.Движения.Содержит(РегМД85)
Или РегМД85.ВидРегистра <> Метаданные.СвойстваОбъектов.ВидРегистраНакопления.Остатки
Или РегМД85.Измерения.Количество() <> 1
Или РегМД85.Ресурсы.Количество() <> 2
Или РегМД85.Реквизиты.Количество() <> 1 Тогда
ВызватьИсключение "Проведение, собственное движение или полный состав регистра изменены.";
КонецЕсли;
РегистраторМД85 = Неопределено;
Для Каждого Стандартный85 Из РегМД85.СтандартныеРеквизиты Цикл
Если Стандартный85.Имя = "Регистратор" Тогда
Если РегистраторМД85 <> Неопределено Тогда
ВызватьИсключение "Неоднозначный стандартный реквизит регистратора.";
КонецЕсли;
РегистраторМД85 = Стандартный85;
КонецЕсли;
КонецЦикла;
Если РегистраторМД85 = Неопределено Тогда
ВызватьИсключение "Не найден стандартный тип регистратора.";
КонецЕсли;
Если РегистраторМД85.Тип.Типы().Количество() <> 1
Или Не РегистраторМД85.Тип.СодержитТип(Тип("ДокументСсылка.Приход85")) Тогда
ВызватьИсключение "Разрешен только собственный тип регистратора Приход85.";
КонецЕсли;
Для Каждого Имя85 Из СтрРазделить("Код85,Количество85,Сумма85,Цена85", ",") Цикл
Описание85 = ?(Имя85 = "Код85", РегМД85.Измерения.Найти(Имя85), ?(Имя85 = "Цена85", РегМД85.Реквизиты.Найти(Имя85), РегМД85.Ресурсы.Найти(Имя85)));
Если Описание85 = Неопределено Тогда
ВызватьИсключение "Нет обязательного собственного поля " + Имя85;
КонецЕсли;
Если Имя85 = "Код85" Тогда
ОжидаемыйТип85 = Новый ОписаниеТипов("Строка", , Новый КвалификаторыСтроки(10));
Иначе
ОжидаемыйТип85 = Новый ОписаниеТипов("Число", Новый КвалификаторыЧисла(?(Имя85 = "Количество85", 9, 12), ?(Имя85 = "Количество85", 0, 2), ДопустимыйЗнак.Неотрицательный));
КонецЕсли;
Если XML85(Описание85.Тип) <> XML85(ОжидаемыйТип85) Тогда
ВызватьИсключение "Не совпал полный тип собственного поля " + Имя85;
КонецЕсли;
КонецЦикла;
Если РасширенияКонфигурации.Получить(, ИсточникРасширенийКонфигурации.БазаДанных).Количество() <> 0
Или РасширенияКонфигурации.Получить(, ИсточникРасширенийКонфигурации.СеансАктивные).Количество() <> 0
Или РасширенияКонфигурации.Получить(, ИсточникРасширенийКонфигурации.СеансОтключенные).Количество() <> 0 Тогда
ВызватьИсключение "Стенд не должен содержать расширений.";
КонецЕсли;
Пользователь85 = ПользователиИнформационнойБазы.ТекущийПользователь();
Пользователи85 = ПользователиИнформационнойБазы.ПолучитьПользователей();
Если Пользователь85 = Неопределено Или Пользователи85.Количество() <> 1 Тогда
ВызватьИсключение "Нужен единственный свой администратор, не гостевой сеанс.";
КонецЕсли;
Если Пользователь85.Имя <> "Уч85Приход_9d8a6e13"
Или Пользователи85[0].УникальныйИдентификатор <> Пользователь85.УникальныйИдентификатор
Или Метаданные.Роли.Количество() <> 1
Или Не Пользователь85.Роли.Содержит(Метаданные.Роли.УчебныйАдминистратор85) Тогда
ВызватьИсключение "Подготовьте точного собственного пользователя и его единственную роль.";
КонецЕсли;
Возврат Новый Структура("Метка,Пользователь", "9d8a6e13-4790-4bc1-a048-84c78ae597e5", Строка(Пользователь85.УникальныйИдентификатор));
КонецФункции
Функция XML85(Значение85) Экспорт
Писатель85 = Новый ЗаписьXML;
Писатель85.УстановитьСтроку();
Попытка
СериализаторXDTO.ЗаписатьXML(Писатель85, Значение85);
Исключение
Писатель85.Закрыть();
ВызватьИсключение;
КонецПопытки;
Возврат Писатель85.Закрыть();
КонецФункции
Функция Источник85(Исправлен85 = Ложь) Экспорт
Паспорт85 = Паспорт85();
Запрос85 = Новый Запрос("ВЫБРАТЬ Д.Ссылка, Д.Дата, Д.Номер, Д.Проведен, Д.ПометкаУдаления, Д.Метка85, Д.Пользователь85, Д.КодДокумента85 ИЗ Документ.Приход85 КАК Д УПОРЯДОЧИТЬ ПО Д.КодДокумента85");
Документы85 = Запрос85.Выполнить().Выгрузить();
Если Документы85.Количество() <> 2 Тогда
ВызватьИсключение "Допустимы ровно два собственных документа, проверяется весь источник.";
КонецЕсли;
Для Индекс85 = 0 По 1 Цикл
Док85 = Документы85[Индекс85];
Если ТипЗнч(Док85.Ссылка) <> Тип("ДокументСсылка.Приход85") Или Док85.Ссылка.Пустая()
Или Док85.Метка85 <> Паспорт85.Метка Или Док85.Пользователь85 <> Паспорт85.Пользователь
Или Док85.КодДокумента85 <> ?(Индекс85 = 0, "A", "B")
Или Док85.Дата <> Дата(2026, 10, 10, 9 + Индекс85, 0, 0)
Или ПустаяСтрока(Док85.Номер) Или Док85.ПометкаУдаления Или Не Док85.Проведен Тогда
ВызватьИсключение "Не совпал полный паспорт своего реального документа.";
КонецЕсли;
КонецЦикла;
Если Документы85[0].Ссылка = Документы85[1].Ссылка Тогда
ВызватьИсключение "Регистраторы обязаны быть различными реальными ссылками.";
КонецЕсли;
Запрос85 = Новый Запрос("ВЫБРАТЬ Р.Регистратор, Р.НомерСтроки, Р.Период, Р.Активность, Р.ВидДвижения, Р.Код85, Р.Количество85, Р.Сумма85, Р.Цена85 ИЗ РегистрНакопления.ПриходыСчета85 КАК Р УПОРЯДОЧИТЬ ПО Р.Код85");
Строки85 = Запрос85.Выполнить().Выгрузить();
Если Строки85.Количество() <> 3 Или Строки85.Колонки.Количество() <> 9 Тогда
ВызватьИсключение "Проверяется весь регистр: ровно три строки и девять полей без чужих записей.";
КонецЕсли;
Для Индекс85 = 0 По 2 Цикл
Строка85 = Строки85[Индекс85];
Регистратор85 = Документы85[?(Индекс85 = 2, 1, 0)].Ссылка;
Количество85 = ?(Индекс85 = 0, ?(Исправлен85, 1, 2), ?(Индекс85 = 1, 1, 3));
Код85 = ?(Индекс85 = 0, "A", ?(Индекс85 = 1, "AA", "B"));
Если ТипЗнч(Строка85.Регистратор) <> Тип("ДокументСсылка.Приход85")
Или Строка85.Регистратор <> Регистратор85
Или Строка85.НомерСтроки <> ?(Индекс85 = 2, 1, Индекс85 + 1)
Или Строка85.Период <> Документы85[?(Индекс85 = 2, 1, 0)].Дата
Или Строка85.Код85 <> Код85 Или Не Строка85.Активность
Или Строка85.ВидДвижения <> ВидДвиженияНакопления.Приход
Или Строка85.Количество85 <> Количество85 Или Строка85.Цена85 <> 250
Или Строка85.Сумма85 <> Количество85 * Строка85.Цена85 Тогда
ВызватьИсключение "Изменились собственный реальный ключ, период, активность, вид движения или сумма.";
КонецЕсли;
КонецЦикла;
Если Строки85.Итог("Количество85") <> ?(Исправлен85, 5, 6)
Или Строки85.Итог("Сумма85") <> ?(Исправлен85, 1250, 1500) Тогда
ВызватьИсключение "Независимый итог всего прочитанного регистра не совпал.";
КонецЕсли;
Возврат Новый Структура("Паспорт,Документы,Строки", Паспорт85, Документы85, Строки85);
КонецФункции
Процедура ПроверитьНабор85(Набор85, Источник85, Исправлен85) Экспорт
Если ТипЗнч(Набор85) <> Тип("РегистрНакопленияНаборЗаписей.ПриходыСчета85")
Или Набор85.Метаданные() <> Метаданные.РегистрыНакопления.ПриходыСчета85
Или Набор85.Количество() <> 2 Или Набор85.Отбор.Количество() <> 1
Или Не Набор85.Отбор.Регистратор.Использование
Или Набор85.Отбор.Регистратор.ВидСравнения <> ВидСравнения.Равно
Или Набор85.Отбор.Регистратор.Значение <> Источник85.Документы[0].Ссылка Тогда
ВызватьИсключение "Нужен полный двухстрочный набор только собственного регистратора A.";
КонецЕсли;
Для Индекс85 = 0 По 1 Цикл
Запись85 = Набор85.Получить(Индекс85);
Исходная85 = Источник85.Строки[Индекс85];
Если ТипЗнч(Запись85) <> Тип("РегистрНакопленияЗапись.ПриходыСчета85") Тогда
ВызватьИсключение "Получена не настоящая запись собственного набора.";
КонецЕсли;
Если Запись85.Регистратор <> Исходная85.Регистратор Или Запись85.НомерСтроки <> Исходная85.НомерСтроки
Или Запись85.Период <> Исходная85.Период Или Запись85.Активность <> Исходная85.Активность
Или Запись85.ВидДвижения <> Исходная85.ВидДвижения Или Запись85.Код85 <> Исходная85.Код85
Или Запись85.Цена85 <> Исходная85.Цена85 Тогда
ВызватьИсключение "Изменено защищаемое поле своей строки.";
КонецЕсли;
Количество85 = ?(Индекс85 = 0, ?(Исправлен85, 1, 2), 1);
Если Запись85.Количество85 <> Количество85 Или Запись85.Сумма85 <> Количество85 * Запись85.Цена85 Тогда
ВызватьИсключение "Кандидат не совпал с точной собственной поправкой A.";
КонецЕсли;
КонецЦикла;
Если Набор85.Итог("Количество85") <> ?(Исправлен85, 2, 3)
Или Набор85.Итог("Сумма85") <> ?(Исправлен85, 500, 750) Тогда
ВызватьИсключение "Полный итог реального набора A не совпал.";
КонецЕсли;
КонецПроцедуры
Функция КлючAA85(Источник85) Экспорт
Строка85 = Источник85.Строки[1];
Если Строка85.Регистратор <> Источник85.Документы[0].Ссылка
Или ТипЗнч(Строка85.Регистратор) <> Тип("ДокументСсылка.Приход85")
Или ТипЗнч(Строка85.НомерСтроки) <> Тип("Число") Или Строка85.НомерСтроки <> 2
Или Строка85.Код85 <> "AA" Тогда
ВызватьИсключение "Ключ создается только после проверки реальных Регистратор/НомерСтроки.";
КонецЕсли;
ЗначенияКлюча85 = Новый Структура("Регистратор,НомерСтроки", Строка85.Регистратор, Строка85.НомерСтроки);
Ключ85 = РегистрыНакопления.ПриходыСчета85.СоздатьКлючЗаписи(ЗначенияКлюча85);
Если ТипЗнч(Ключ85) <> Тип("РегистрНакопленияКлючЗаписи.ПриходыСчета85")
Или Ключ85.Регистратор <> Строка85.Регистратор Или Ключ85.НомерСтроки <> Строка85.НомерСтроки Тогда
ВызватьИсключение "Фактический native ключ не совпал с двумя ключевыми полями.";
КонецЕсли;
Возврат Ключ85;
КонецФункции
Процедура СравнитьИсточник85(Прежний85, Новый85) Экспорт
Если XML85(Прежний85.Документы) <> XML85(Новый85.Документы)
Или XML85(Прежний85.Строки) <> XML85(Новый85.Строки) Тогда
ВызватьИсключение "Полный собственный сохраненный источник изменился; не продолжаем и не восстанавливаем слепо.";
КонецЕсли;
КонецПроцедурыМодуль обычного приложения: настоящий старт
Конфигурация → Модуль обычного приложения; native ПриНачалеРаботыСистемы0.
Процедура ПриНачалеРаботыСистемы()
ПолучитьОбщуюФорму("МаршрутПрихода85", , Новый УникальныйИдентификатор).Открыть();
КонецПроцедурыШтатные фабрики: открыть именно свой список и свой прочитанный набор
ОбщаяФорма.МаршрутПрихода85, обычная форма
Перем Источник85;
Процедура ПриОткрытии()
Если Источник85 <> Неопределено Тогда
ВызватьИсключение "Повторная инициализация собственного экземпляра запрещена.";
КонецЕсли;
Источник85 = УчПриходыСчета85.Источник85();
Состояние85 = "Два своих документа, три записи; фактическая сумма=" + Строка(Источник85.Строки.Итог("Сумма85"));
КонецПроцедуры
Процедура Список85(Кнопка)
Если Кнопка <> ЭлементыФормы.Список85 Или Кнопка.Имя <> "Список85" Тогда
ВызватьИсключение "Нужна настоящая собственная кнопка списка.";
КонецЕсли;
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
Менеджеры85 = РегистрыНакопления;
Если ТипЗнч(Менеджеры85) <> Тип("РегистрыНакопленияМенеджер") Тогда
ВызватьИсключение "Не получена штатная фабрика менеджеров.";
КонецЕсли;
Менеджер85 = Менеджеры85["ПриходыСчета85"];
Ключ85 = УчПриходыСчета85.КлючAA85(Источник85);
Форма85 = Менеджер85.ПолучитьФормуСписка("СписокСчета85", ЭтаФорма, Новый УникальныйИдентификатор);
Если Форма85 = Неопределено Тогда
ВызватьИсключение "Штатная фабрика отказала в создании формы списка.";
КонецЕсли;
Если Форма85.ВладелецФормы <> ЭтаФорма Тогда
ВызватьИсключение "Не совпал владелец именно обычной формы.";
КонецЕсли;
Форма85.ПараметрОтборПоРегистратору = Источник85.Документы[0].Ссылка;
Форма85.ПараметрТекущаяСтрока = Ключ85;
Форма85.ПодтвердитьИсточник85(Источник85);
Форма85.Открыть();
КонецПроцедуры
Процедура Набор85(Кнопка)
Если Кнопка <> ЭлементыФормы.Набор85 Или Кнопка.Имя <> "Набор85" Тогда
ВызватьИсключение "Нужна настоящая собственная кнопка набора.";
КонецЕсли;
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
Менеджеры85 = РегистрыНакопления;
Если ТипЗнч(Менеджеры85) <> Тип("РегистрыНакопленияМенеджер") Тогда
ВызватьИсключение "Не получен штатный менеджер регистров.";
КонецЕсли;
СвойНабор85 = Менеджеры85.ПриходыСчета85.СоздатьНаборЗаписей();
Если ТипЗнч(СвойНабор85) <> Тип("РегистрНакопленияНаборЗаписей.ПриходыСчета85") Или СвойНабор85.Количество() <> 0 Тогда
ВызватьИсключение "Нужен реальный собственный пустой native набор.";
КонецЕсли;
СвойНабор85.Отбор.Регистратор.Установить(Источник85.Документы[0].Ссылка, Истина);
СвойНабор85.Прочитать();
УчПриходыСчета85.ПроверитьНабор85(СвойНабор85, Источник85, Ложь);
Форма85 = СвойНабор85.ПолучитьФорму("НаборСчета85", ЭтаФорма, Новый УникальныйИдентификатор);
Если Форма85 = Неопределено Тогда
ВызватьИсключение "Штатная фабрика отказала в создании формы конкретного набора.";
КонецЕсли;
Если Форма85.ВладелецФормы <> ЭтаФорма Или Форма85.Набор <> СвойНабор85 Тогда
ВызватьИсключение "Форма принадлежит не собственному владельцу/экземпляру набора.";
КонецЕсли;
Форма85.ПодтвердитьИсточник85(Источник85);
Форма85.Открыть();
КонецПроцедурыСписок своего регистра: точный код500, реальное позиционирование и native картинки
РегистрНакопления.ПриходыСчета85.Форма.СписокСчета85, обычная форма списка
Перем Источник85, Готов85, НеизвестныйИсход85, Этап85;
Процедура ПодтвердитьИсточник85(Переданный85) Экспорт
Если Готов85 <> Неопределено Или НеизвестныйИсход85 <> Неопределено Тогда
ВызватьИсключение "Нельзя повторно инициализировать или очищать неизвестный исход.";
КонецЕсли;
НеизвестныйИсход85 = Истина;
Источник85 = УчПриходыСчета85.Источник85();
УчПриходыСчета85.СравнитьИсточник85(Переданный85, Источник85);
Если ТипЗнч(Список) <> Тип("РегистрНакопленияСписок.ПриходыСчета85")
Или ЭтаФорма.ПараметрОтборПоРегистратору <> Источник85.Документы[0].Ссылка
Или ТипЗнч(ЭтаФорма.ПараметрТекущаяСтрока) <> Тип("РегистрНакопленияКлючЗаписи.ПриходыСчета85")
Или ЭтаФорма.ПараметрТекущаяСтрока.Регистратор <> Источник85.Документы[0].Ссылка
Или ЭтаФорма.ПараметрТекущаяСтрока.НомерСтроки <> 2 Тогда
ВызватьИсключение "Начальные параметры формы должны содержать настоящий документ A и проверенный ключ AA.";
КонецЕсли;
Список.Колонки.Установить("Регистратор,НомерСтроки,Период,Активность,ВидДвижения,Код85,Количество85,Сумма85,Цена85");
ЭлементыФормы.Строки85.СоздатьКолонки();
Поле85 = ЭлементыФормы.Строки85;
Если ТипЗнч(Поле85) <> Тип("ТабличноеПоле") Или Поле85.Данные <> "Список" Или Поле85.Значение <> Список Тогда
ВызватьИсключение "Требуется подготовленное обычное поле реального списка.";
КонецЕсли;
Колонка85 = Поле85.Колонки.Найти("НомерСтроки");
Если Колонка85 = Неопределено Тогда
ВызватьИсключение "Не создана собственная колонка номера записи.";
КонецЕсли;
Если Колонка85.Данные <> "НомерСтроки" Тогда
ВызватьИсключение "Колонка картинки показывает неизвестное поле.";
КонецЕсли;
Колонка85.ОтображатьСтандартнуюКартинку = Истина;
Поле85.ТолькоПросмотр = Истина;
Этап85 = 0;
Готов85 = Истина;
НеизвестныйИсход85 = Ложь;
КонецПроцедуры
Процедура ПриОткрытии()
ПроверитьИсточник85();
Если Не Список.Отбор.Регистратор.Использование
Или Список.Отбор.Регистратор.ВидСравнения <> ВидСравнения.Равно
Или Список.Отбор.Регистратор.Значение <> Источник85.Документы[0].Ссылка Тогда
ВызватьИсключение "Нативное открытие не подтвердило точный отбор собственного регистратора.";
КонецЕсли;
Ключ85 = ЭлементыФормы.Строки85.ТекущаяСтрока;
Если Ключ85 = Неопределено Тогда
ВызватьИсключение "Текущая строка еще не доставлена; не обещаем немедленное позиционирование.";
КонецЕсли;
Если ТипЗнч(Ключ85) <> Тип("РегистрНакопленияКлючЗаписи.ПриходыСчета85")
Или Ключ85.Регистратор <> Источник85.Документы[0].Ссылка Или Ключ85.НомерСтроки <> 2 Тогда
ВызватьИсключение "Фактическое позиционирование не совпало с собственным AA.";
КонецЕсли;
ПроверитьРезультат85();
КонецПроцедуры
Процедура ПроверитьИсточник85()
Если Готов85 <> Истина Или НеизвестныйИсход85 <> Ложь Тогда
ВызватьИсключение "Просмотр не подготовлен либо прошлый исход неизвестен.";
КонецЕсли;
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
Если ЭлементыФормы.Строки85.Данные <> "Список" Или ЭлементыФормы.Строки85.Значение <> Список
Или Не ЭлементыФормы.Строки85.ТолькоПросмотр
Или Не ЭлементыФормы.Строки85.Колонки.НомерСтроки.ОтображатьСтандартнуюКартинку Тогда
ВызватьИсключение "Изменены собственные источник/привязка/политика отображения списка.";
КонецЕсли;
КонецПроцедуры
Процедура ТочныйКод85(Кнопка)
Если Кнопка <> ЭлементыФормы.ТочныйКод85 Или Кнопка.Имя <> "ТочныйКод85" Тогда
ВызватьИсключение "Нужна настоящая собственная кнопка отбора списка.";
КонецЕсли;
ПроверитьИсточник85();
Если Этап85 > 1 Тогда
ВызватьИсключение "Два собственных этапа уже завершены.";
КонецЕсли;
НеизвестныйИсход85 = Истина;
Попытка
Список.Отбор.Код85.Установить("A", Этап85 = 0);
Список.Обновить();
Этап85 = Этап85 + 1;
ПроверитьРезультат85();
УчПриходыСчета85.СравнитьИсточник85(Источник85, УчПриходыСчета85.Источник85());
НеизвестныйИсход85 = Ложь;
Исключение
НеизвестныйИсход85 = Истина;
ВызватьИсключение;
КонецПопытки;
КонецПроцедуры
Процедура ПроверитьРезультат85()
Для Каждого Условие85 Из Список.Отбор Цикл
Если Условие85.Использование И Условие85.Имя <> "Регистратор" И Условие85.Имя <> "Код85" Тогда
ВызватьИсключение "Неизвестный активный отбор списка не удаляем.";
КонецЕсли;
КонецЦикла;
Если Список.Отбор.Код85.Использование <> (Этап85 = 1)
Или Этап85 = 1 И (Список.Отбор.Код85.ВидСравнения <> ВидСравнения.Равно Или Список.Отбор.Код85.Значение <> "A") Тогда
ВызватьИсключение "Нужен именно точный отбор A, не строковое вхождение.";
КонецЕсли;
ФактСумма85 = 0;
ФактЧисло85 = 0;
Для Индекс85 = 0 По 1 Цикл
Строка85 = Источник85.Строки[Индекс85];
Ключ85 = РегистрыНакопления.ПриходыСчета85.СоздатьКлючЗаписи(Новый Структура("Регистратор,НомерСтроки", Строка85.Регистратор, Строка85.НомерСтроки));
Если ЭлементыФормы.Строки85.ПроверитьСтроку(Ключ85) Тогда
Данные85 = ЭлементыФормы.Строки85.ДанныеСтроки(Ключ85);
Если Данные85 = Неопределено Тогда
ВызватьИсключение "Нативное поле еще не вернуло данные собственной принятой строки.";
КонецЕсли;
Если Данные85.Регистратор <> Строка85.Регистратор Или Данные85.НомерСтроки <> Строка85.НомерСтроки
Или Данные85.Период <> Строка85.Период Или Данные85.Активность <> Строка85.Активность
Или Данные85.ВидДвижения <> Строка85.ВидДвижения Или Данные85.Код85 <> Строка85.Код85
Или Данные85.Количество85 <> Строка85.Количество85 Или Данные85.Сумма85 <> Строка85.Сумма85
Или Данные85.Цена85 <> Строка85.Цена85 Тогда
ВызватьИсключение "Фактические данные поля не совпали с полной сохраненной строкой.";
КонецЕсли;
ФактЧисло85 = ФактЧисло85 + 1;
ФактСумма85 = ФактСумма85 + Данные85.Сумма85;
КонецЕсли;
КонецЦикла;
Если ФактЧисло85 <> ?(Этап85 = 1, 1, 2) Или ФактСумма85 <> ?(Этап85 = 1, 500, 750) Тогда
ВызватьИсключение "Нативный список не подтвердил собственный числовой результат.";
КонецЕсли;
Состояние85 = "Нативно принятых строк=" + Строка(ФактЧисло85) + "; сумма=" + Строка(ФактСумма85) + "; сохраненный регистр=1500";
КонецПроцедурыНастоящий модуль набора: ЭтотОбъект и полная проверка собственного разрешенного замещения
РегистрНакопления.ПриходыСчета85 → Модуль набора записей
Процедура ПередЗаписью(Отказ, Замещение)
Отказ = Истина;
#Если ТолстыйКлиентОбычноеПриложение Тогда
СвойНабор85 = ЭтотОбъект;
Если ТипЗнч(СвойНабор85) <> Тип("РегистрНакопленияНаборЗаписей.ПриходыСчета85")
Или ТипЗнч(Замещение) <> Тип("Булево") Или Не Замещение
Или ЭтотОбъект.ДополнительныеСвойства.Количество() <> 1 Тогда
ВызватьИсключение "Допустим только свой обычный полный набор и явная замена с единственным разрешением.";
КонецЕсли;
Если Не СвойНабор85.ДополнительныеСвойства.Свойство("УчПриходРазрешение85", Разрешение85) Тогда
ВызватьИсключение "Переданные своей формой данные отсутствуют: отказ, не предполагаем общее состояние клиента/сервера.";
КонецЕсли;
СвойНабор85.ДополнительныеСвойства.Удалить("УчПриходРазрешение85");
Если ТипЗнч(Разрешение85) <> Тип("Структура") Или Разрешение85.Количество() <> 5 Тогда
ВызватьИсключение "Разрешение обязано иметь ровно пять собственных полей.";
КонецЕсли;
Для Каждого Имя85 Из СтрРазделить("Метка,Пользователь,Регистратор,Токен,Подтверждено", ",") Цикл
Если Не Разрешение85.Свойство(Имя85) Тогда
ВызватьИсключение "Отсутствует обязательное поле собственного разрешения.";
КонецЕсли;
КонецЦикла;
Источник85 = УчПриходыСчета85.Источник85();
Если ТипЗнч(Разрешение85.Метка) <> Тип("Строка") Или Разрешение85.Метка <> Источник85.Паспорт.Метка
Или ТипЗнч(Разрешение85.Пользователь) <> Тип("Строка") Или Разрешение85.Пользователь <> Источник85.Паспорт.Пользователь
Или ТипЗнч(Разрешение85.Регистратор) <> Тип("ДокументСсылка.Приход85") Или Разрешение85.Регистратор <> Источник85.Документы[0].Ссылка
Или ТипЗнч(Разрешение85.Токен) <> Тип("Строка") Или СтрДлина(Разрешение85.Токен) <> 36
Или ТипЗнч(Разрешение85.Подтверждено) <> Тип("Булево") Или Не Разрешение85.Подтверждено Тогда
ВызватьИсключение "Разрешение относится не к собственным пользователю/регистратору/нажатию.";
КонецЕсли;
Если НРег(Строка(Новый УникальныйИдентификатор(Разрешение85.Токен))) <> НРег(Разрешение85.Токен) Тогда
ВызватьИсключение "Поврежден UUID собственного одноразового действия.";
КонецЕсли;
Разрешение85.Подтверждено = Ложь;
УчПриходыСчета85.ПроверитьНабор85(СвойНабор85, Источник85, Истина);
Отказ = Ложь;
#Иначе
ВызватьИсключение "Этот учебный обработчик не разрешает запись из других контекстов.";
#КонецЕсли
КонецПроцедурыРазбор по шагам
Подготовьте новый собственный стенд и исходные движения вручную ДО установки запрещающих событий.
Установите все полные модули с точными владельцами и связями native callbacks; запустите только thick ordinary.
Просмотрите и сравните свои реальные числа, затем при желании отдельно подтвердите единственную собственную поправку.
Как проверить результат
Начальный свой набор750. Три настоящих нажатия СледующийОтбор85 даютA→750, AA→250, выключен→750 по nativeCheckRow/RowData; fullDB1500 и fullmemory750 не изменились.
СвояПробнаяСтрока85 создает только actual pending B100 в своем наборе, nativeCheckRow подAA=False; удаляет только эту actual запись и сверяет полный возвращенный набор750/сохраненный источник1500. Это не фактическая запись и не обещание runtime предупреждения.
СохранитьПоправку85 с ответомНет: полные DB/memory исходники неизменны. Да в новом собственном стенде: меняется только ownA qty2→1/sum500→250; настоящий formBeforeWrite1 и setBeforeWrite2 доставляются nativeWriteInForm0. True+fullfreshreadback:ownA500/ownB750/весь1250; повтор запрещен.
False/исключение/неверный результат оставляют UnknownTrue и AuthFalse. Не пытайтесь повторять или закрыть/снова инициализировать ради стирания ошибки; сначала лично выясните фактический результат в своей новой ИБ.
Ожидаемый результат
Метаданные, native фабрики и каждый полный readback принадлежат только этому конечному собственному опыту; пустые getter-обертки не используются.
На что обратить внимание
Только authoredsource и статические проверки. Actual1С/БД/UI/сеть/проведение/запись/файлы/хранилища0; подготовка и опыт — будущие личные ручные действия исключительно в указанной новой ИБ; backups0.
Это толстый ОБЫЧНЫЙ клиент: ТабличноеПоле/КолонкаТабличногоПоля/Форма, не managed ТаблицаФормы. GetForm526 возвращает Form|Undefined и требует имя формы; формы создаются штатным мастером с точными основными реквизитами. Только реальные native объекты и metadata типы, не Новый РегистрНакопленияЗапись/Новый form-extension.
В установленной HBK type description табличного поля ошибочно говорит сведений, а формы набора — расчета. Exact accumulation page paths, свойства, GetForm526, WriteInForm1344 и form/set event pages указывают регистр накопления. Эти две опечатки не исправляются в источнике справки и не используются для перенаправления владельца.
ОтборСтрок и НастройкаОтбораСтрок — readonly контейнеры; меняются только документированные child fields. RowFilter проверяет вхождение: A принимает A иAA; Список.Отбор.Код85 использует Равно. Native CheckRow/RowData доказывают принятие/данные строки, не момент окончательной перерисовки каждого пикселя и не реальный визуальный итог подвала.
NewRowShowCheck предупреждает после интерактивного завершения ввода новой строки. Своя pending проба создана кодом в памяти: native CheckRow проверяется, но появление штатного предупреждения здесь не объявляется runtime доказанным. Это политика интерфейса, не запрет записи. Пробная строка удаляется только штатным Delete(тотжеactualobject) на успешном локальном этапе; при ошибке нет blind cleanup/rollback.
ОбновлятьПриИзмененииОтбора=False не заменяет проверку полного источника и не обещает универсально отсутствие перечитывания. RefreshRows обновляет отображение, не служит доказательством неизменности БД; отдельно сверяются full query source и full unloaded own memory set.
RecordKey содержит только реальные Регистратор/НомерСтроки; код не использует ошибочный пример CreateRecordKey848 с измерениями. Такой ключ неустойчив после замещения записей; после Save новые исходные ключи не переиспользуются и форма списка может стать устаревшей.
Форма передает конечное разрешение в AdditionalProperties именно собственного actual набора. Общие функции не полагаются на разделяемые client/server переменные. Доставка transient данных через возможное преобразование объекта не гарантируется: если callback их не получил, он отказывает. UUID действия не является криптографическим разрешением или security barrier от чужого кода.
Препроцессор ТолстыйКлиентОбычноеПриложение истинен и в client, и в server части File/thick ordinary. Он не означает универсальное не-сервер. COMMON также доступен Сервер+КлиентОбычноеПриложение; другие server/client-server/external контексты без этого символа получают отказ в callback. Shared auth state не предполагается.
WriteInFormFalse/exception/fresh readback mismatch дают sticky неизвестный исход: одноразовое согласие снимается и повтор/слепое восстановление запрещены. Readback не является proof отсутствия конкуренции; используйте один собственный сеанс без других пользователей/фоновых изменений. Успешная замена касается всего отфильтрованного двухстрочного набора A, не только видимой строки.
Пример не запускался в вашей базе. Перед применением проверьте его в указанном учебном контексте.
ПостроительОтчета: собственный полный макет и настоящая расшифровка группы
Обычная форма толстого клиента строит собственный отчёт из трёх literal строк, использует все области макета и по реальному cell callback выводит справа только выбранную собственную категорию. Это старый API построителя, не СКД.
Где и как запускать
Полный модуль собственной обычной формы обработки УчебныйМакетПостроителя85. ТолстыйКлиентОбычноеПриложение 8.5.1.1343; реальное событие собственного поля ТабличныйДокумент с native базовыми двумя параметрами плюс первый Элемент обычного расширения внутри формы. Только own literal query и макеты в памяти.
Подготовка
Вручную создайте отдельную новую пустую базу платформы 8.5.1.1343. Имя конфигурации=УчебныйМакетПостроителя85, основной режим запуска=Обычное приложение. Включите использование модальности для своего обычного клиента. Нет объектов бизнеса, расширений, рабочих данных и внешних источников.
Добавьте собственную обработку УчебныйМакетПостроителя85 и её Обычную форму Основная. Реквизиты формы: ОсновнойДокумент85 и ДетальныйДокумент85 типа ТабличныйДокумент, Состояние85 типа Строка неограниченной длины. Поставьте два ПолеТабличногоДокумента: ОсновнойОтчет85 с данными ОсновнойДокумент85 и ДетальныйОтчет85 с данными ДетальныйДокумент85. Разместите Состояние85 отдельным многострочным полем только для просмотра.
Кнопку СформироватьОсновной85 свяжите с одноимённой процедурой. Событие формы ПриОткрытии — с ПриОткрытии(). У поля ОсновнойОтчет85 событие ОбработкаРасшифровки свяжите с ОсновнойОтчет85ОбработкаРасшифровки(Элемент, Расшифровка, СтандартнаяОбработка). Базовое событие поля имеет два параметра, а обычное расширение любого элемента внутри формы добавляет первым Элемент. Это итоговая ordinary сигнатура с тремя параметрами; код сверяет actual собственное поле, не вызывайте обработчик вручную.
Весь код вставьте в модуль своей обычной формы, обновите только собственную конфигурацию и откройте свою обработку толстым клиентом в обычном приложении. На сервере, в тонком и web клиенте этот UI маршрут не запускается.
Макет создаётся полностью в памяти самим модулем. Настоящие области: ЗаголовокОтчета, ШапкаТаблицы, Категория, Детали, ОбщиеИтоги, ПодвалТаблицы, ПодвалОтчета. Параметры детальных ячеек совпадают с полями собственного literal запроса. Для суммы количества группы используется ПараметрРасшифровки=Расшифровка, и построитель сам заполняет значение native cell.
Свои строки: А85/Альфа85/1/100, А85/Гамма85/3/600, Б85/Бета85/5/1250. У текста построителя есть настоящий расширенный раздел {ГДЕ Д.Категория КАК Категория}; только это измерение доступно методу НастроитьРасшифровку. Не заменяйте запрос таблицами своей рабочей базы.
Оформление Весна получается native ПолучитьМакетОформления и используется отдельным ТабличныйДокумент. Его применение идёт через ОформитьМакет после Выполнить, как в native примере. Цвета/точный вид темы проверьте вручную; исходники УТ подтверждают архитектуру параметров макета, но не доказывают исполнение этого урока на 8.5.1.1343.
#Если ТолстыйКлиентОбычноеПриложение Тогда
Перем СвойОсновнойПостроитель85;
Процедура ПриОткрытии()
ПроверитьСвойПустойСтенд();
СвойОсновнойПостроитель85 = Неопределено;
ОсновнойДокумент85 = Новый ТабличныйДокумент;
ДетальныйДокумент85 = Новый ТабличныйДокумент;
ОсновнойДокумент85.ТолькоПросмотр = Истина;
ДетальныйДокумент85.ТолькоПросмотр = Истина;
Состояние85 = "Сначала СформироватьОсновной85. Затем двойной щелчок по количеству в строке группы А85 или Б85.";
КонецПроцедуры
Процедура СформироватьОсновной85(Кнопка)
ПроверитьСвойПустойСтенд();
НовыйПостроитель = СоздатьСвойПостроитель85();
НовыйПостроитель.Выполнить();
ПроверитьСвойЗапрос85(НовыйПостроитель, "");
НовыйПостроитель.ОформитьМакет();
НовыйДокумент = Новый ТабличныйДокумент;
НовыйПостроитель.Вывести(НовыйДокумент);
ПроверитьСвойВывод85(НовыйДокумент, "");
НовыйДокумент.ТолькоПросмотр = Истина;
СвойОсновнойПостроитель85 = НовыйПостроитель;
ОсновнойДокумент85 = НовыйДокумент;
Состояние85 = "Свой отчёт: 3 детальные строки; А85=4/700, Б85=5/1250, общий итог=9/1950. Щёлкните количество группы, не текст подвала.";
КонецПроцедуры
Функция СоздатьСвойПостроитель85()
Построитель = Новый ПостроительОтчета;
Построитель.Текст = "ВЫБРАТЬ Д.Категория, Д.Наименование, Д.Количество, Д.Сумма
|ИЗ (ВЫБРАТЬ ""А85"" КАК Категория, ""Альфа85"" КАК Наименование, 1 КАК Количество, 100 КАК Сумма
| ОБЪЕДИНИТЬ ВСЕ ВЫБРАТЬ ""А85"", ""Гамма85"", 3, 600
| ОБЪЕДИНИТЬ ВСЕ ВЫБРАТЬ ""Б85"", ""Бета85"", 5, 1250) КАК Д
|{ГДЕ Д.Категория КАК Категория}
|УПОРЯДОЧИТЬ ПО Категория, Наименование
|ИТОГИ СУММА(Количество), СУММА(Сумма) ПО ОБЩИЕ, Категория";
Построитель.ДобавлениеПредставлений = ТипДобавленияПредставлений.НеДобавлять;
Построитель.ЗаполнитьНастройки();
Построитель.ВыбранныеПоля.Очистить();
Для Каждого ИмяПоля Из СтрРазделить("Категория,Наименование,Количество,Сумма", ",") Цикл
Построитель.ВыбранныеПоля.Добавить(ИмяПоля, ИмяПоля);
КонецЦикла;
Построитель.ИзмеренияСтроки.Очистить();
Измерение = Построитель.ИзмеренияСтроки.Добавить("Категория", "Категория", ТипИзмеренияПостроителяОтчета.Элементы);
Построитель.ИзмеренияКолонки.Очистить();
Построитель.АвтоДетальныеЗаписи = Ложь;
Построитель.ВыводитьДетальныеЗаписи = Истина;
Построитель.ВыводитьЗаголовокОтчета = Истина;
Построитель.ВыводитьОбщиеИтоги = Истина;
Построитель.ВыводитьШапкуТаблицы = Истина;
Построитель.ВыводитьПодвалТаблицы = Истина;
Построитель.ВыводитьПодвалОтчета = Истина;
Построитель.ОтображатьСостояние = Ложь;
Построитель.ОбрабатыватьПрерываниеПользователя = Ложь;
Построитель.ЗаполнениеРасшифровки = ВидЗаполненияРасшифровкиПостроителяОтчета.Расшифровка;
Построитель.Макет = СоздатьСвойМакет85();
Построитель.МакетЗаголовкаОтчета = "ЗаголовокОтчета";
Построитель.МакетШапкиТаблицы = "ШапкаТаблицы";
Построитель.МакетДетальныхЗаписей = "Детали";
Построитель.МакетОбщихИтогов = "ОбщиеИтоги";
Построитель.МакетПодвалаТаблицы = "ПодвалТаблицы";
Построитель.МакетПодвалаОтчета = "ПодвалОтчета";
Измерение.Макет = "Категория";
Построитель.МакетОформления = ПолучитьМакетОформления(СтандартноеОформление.Весна);
Если ТипЗнч(Построитель.Макет) <> Тип("ТабличныйДокумент")
Или ТипЗнч(Построитель.МакетОформления) <> Тип("ТабличныйДокумент") Тогда
ВызватьИсключение "Оба макета построителя должны быть настоящими табличными документами";
КонецЕсли;
Если Построитель.МакетЗаголовкаОтчета <> "ЗаголовокОтчета"
Или Построитель.МакетШапкиТаблицы <> "ШапкаТаблицы"
Или Построитель.МакетДетальныхЗаписей <> "Детали"
Или Построитель.МакетОбщихИтогов <> "ОбщиеИтоги"
Или Построитель.МакетПодвалаТаблицы <> "ПодвалТаблицы"
Или Построитель.МакетПодвалаОтчета <> "ПодвалОтчета" Тогда
ВызватьИсключение "Имена собственных областей не прочитались обратно";
КонецЕсли;
Возврат Построитель;
КонецФункции
Функция СоздатьСвойМакет85()
Макет = Новый ТабличныйДокумент;
Макет.Область(1, 1, 8, 4).ШиринаКолонки = 22;
Макет.Область(1, 1, 1, 4).Имя = "ЗаголовокОтчета";
Макет.Область(1, 1).Текст = "Свой макет построителя85";
Макет.Область(2, 1, 2, 4).Имя = "ШапкаТаблицы";
Макет.Область(2, 1).Текст = "Категория";
Макет.Область(2, 2).Текст = "Собственная строка";
Макет.Область(2, 3).Текст = "Количество";
Макет.Область(2, 4).Текст = "Сумма";
Макет.Область(3, 1, 3, 4).Имя = "Категория";
Макет.Область(3, 1).Заполнение = ТипЗаполненияОбластиТабличногоДокумента.Параметр;
Макет.Область(3, 1).Параметр = "Категория";
Макет.Область(3, 2).Текст = "Своя группа: открыть расшифровку количества";
Макет.Область(3, 3).Заполнение = ТипЗаполненияОбластиТабличногоДокумента.Параметр;
Макет.Область(3, 3).Параметр = "Количество";
Макет.Область(3, 3).ПараметрРасшифровки = "Расшифровка";
Макет.Область(3, 4).Заполнение = ТипЗаполненияОбластиТабличногоДокумента.Параметр;
Макет.Область(3, 4).Параметр = "Сумма";
Макет.Область(4, 1, 4, 4).Имя = "Детали";
НомерКолонки = 1;
Для Каждого ИмяПоля Из СтрРазделить("Категория,Наименование,Количество,Сумма", ",") Цикл
Ячейка = Макет.Область(4, НомерКолонки);
Ячейка.Заполнение = ТипЗаполненияОбластиТабличногоДокумента.Параметр;
Ячейка.Параметр = ИмяПоля;
НомерКолонки = НомерКолонки + 1;
КонецЦикла;
Макет.Область(5, 1, 5, 4).Имя = "ОбщиеИтоги";
Макет.Область(5, 1).Текст = "Свой общий итог";
Макет.Область(5, 3).Заполнение = ТипЗаполненияОбластиТабличногоДокумента.Параметр;
Макет.Область(5, 3).Параметр = "Количество";
Макет.Область(5, 4).Заполнение = ТипЗаполненияОбластиТабличногоДокумента.Параметр;
Макет.Область(5, 4).Параметр = "Сумма";
Макет.Область(6, 1, 6, 4).Имя = "ПодвалТаблицы";
Макет.Область(6, 1).Текст = "Конец своей таблицы85";
Макет.Область(7, 1, 7, 4).Имя = "ПодвалОтчета";
Макет.Область(7, 1).Текст = "Своё учебное завершение85";
Для Каждого ИмяОбласти Из СтрРазделить("ЗаголовокОтчета,ШапкаТаблицы,Категория,Детали,ОбщиеИтоги,ПодвалТаблицы,ПодвалОтчета", ",") Цикл
Если ТипЗнч(Макет.ПолучитьОбласть(ИмяОбласти)) <> Тип("ТабличныйДокумент") Тогда
ВызватьИсключение "Не создана настоящая собственная область " + ИмяОбласти;
КонецЕсли;
КонецЦикла;
Возврат Макет;
КонецФункции
Процедура ОсновнойОтчет85ОбработкаРасшифровки(Элемент, Расшифровка, СтандартнаяОбработка)
СтандартнаяОбработка = Ложь;
Если Элемент <> ЭлементыФормы.ОсновнойОтчет85 Тогда
ВызватьИсключение "Расшифровка пришла не от собственного actual поля основного отчёта";
КонецЕсли;
ПроверитьСвойПустойСтенд();
Если СвойОсновнойПостроитель85 = Неопределено Тогда
ВызватьИсключение "Сначала сформируйте свой основной отчёт";
КонецЕсли;
Если ТипЗнч(Расшифровка) <> Тип("Структура") Тогда
Состояние85 = "Это не native структура групповой расшифровки: щёлкните количество строки группы А85 или Б85.";
Возврат;
КонецЕсли;
Если Не Расшифровка.Свойство("Категория", Категория) Тогда
Состояние85 = "В native расшифровке нет собственного измерения Категория; ничего не выполнялось.";
Возврат;
КонецЕсли;
Если ТипЗнч(Категория) <> Тип("Строка") Или (Категория <> "А85" И Категория <> "Б85") Тогда
ВызватьИсключение "Допустимы только две реальные категории собственного отчёта";
КонецЕсли;
ДокументДоВопроса = ДетальныйДокумент85;
ТекстДоВопроса = СнимокСвоегоДокумента85(ДетальныйДокумент85);
Ответ = Вопрос("Расшифровать свою категорию " + Категория + "?", РежимДиалогаВопрос.ДаНетОтмена, 30, КодВозвратаДиалога.Отмена);
Если Ответ <> КодВозвратаДиалога.Да Тогда
Если ДетальныйДокумент85 <> ДокументДоВопроса Или СнимокСвоегоДокумента85(ДетальныйДокумент85) <> ТекстДоВопроса Тогда
ВызватьИсключение "Отказ или таймаут не должен изменять прежний детальный результат";
КонецЕсли;
Состояние85 = "Нет/Отмена/таймаут: собственный детальный документ остался прежним. Новый построитель не создавался.";
Возврат;
КонецЕсли;
НовыйПостроитель = СоздатьСвойПостроитель85();
Если НовыйПостроитель = СвойОсновнойПостроитель85 Тогда
ВызватьИсключение "Детальная расшифровка должна иметь отдельный собственный построитель";
КонецЕсли;
СвойОсновнойПостроитель85.НастроитьРасшифровку(НовыйПостроитель, Расшифровка);
НовыйПостроитель.Выполнить();
ПроверитьСвойЗапрос85(НовыйПостроитель, Категория);
НовыйПостроитель.ОформитьМакет();
НовыйДокумент = Новый ТабличныйДокумент;
НовыйПостроитель.Вывести(НовыйДокумент);
ПроверитьСвойВывод85(НовыйДокумент, Категория);
ПроверитьСвойЗапрос85(СвойОсновнойПостроитель85, "");
НовыйДокумент.ТолькоПросмотр = Истина;
ДетальныйДокумент85 = НовыйДокумент;
Состояние85 = "Принята native расшифровка " + Категория + ". Справа только свои строки этой категории, слева исходные три строки сохранены.";
КонецПроцедуры
Процедура ПроверитьСвойЗапрос85(Построитель, Категория)
Результат = Построитель.Результат;
Если ТипЗнч(Результат) <> Тип("РезультатЗапроса") Тогда
ВызватьИсключение "Нужен настоящий результат запроса построителя";
КонецЕсли;
Строки = Результат.Выгрузить(ОбходРезультатаЗапроса.Прямой);
Если ТипЗнч(Строки) <> Тип("ТаблицаЗначений") Тогда
ВызватьИсключение "Прямой native обход должен вернуть таблицу значений";
КонецЕсли;
Если Категория = "" Тогда
ОжидаетсяСтрок = 3;
ОжидаетсяКоличество = 9;
ОжидаетсяСумма = 1950;
ИначеЕсли Категория = "А85" Тогда
ОжидаетсяСтрок = 2;
ОжидаетсяКоличество = 4;
ОжидаетсяСумма = 700;
ИначеЕсли Категория = "Б85" Тогда
ОжидаетсяСтрок = 1;
ОжидаетсяКоличество = 5;
ОжидаетсяСумма = 1250;
Иначе
ВызватьИсключение "Неизвестная категория собственного ожидания";
КонецЕсли;
Если Строки.Количество() <> ОжидаетсяСтрок Или Строки.Итог("Количество") <> ОжидаетсяКоличество
Или Строки.Итог("Сумма") <> ОжидаетсяСумма Тогда
ВызватьИсключение "Native запрос не совпал с собственным числовым ожиданием";
КонецЕсли;
Для Каждого СтрокаДанных Из Строки Цикл
Если Категория <> "" И СтрокаДанных.Категория <> Категория Тогда
ВызватьИсключение "Native отбор пропустил строку чужой категории";
КонецЕсли;
Если СтрокаДанных.Наименование = "Альфа85" Тогда
Верно = СтрокаДанных.Категория = "А85" И СтрокаДанных.Количество = 1 И СтрокаДанных.Сумма = 100;
ИначеЕсли СтрокаДанных.Наименование = "Гамма85" Тогда
Верно = СтрокаДанных.Категория = "А85" И СтрокаДанных.Количество = 3 И СтрокаДанных.Сумма = 600;
ИначеЕсли СтрокаДанных.Наименование = "Бета85" Тогда
Верно = СтрокаДанных.Категория = "Б85" И СтрокаДанных.Количество = 5 И СтрокаДанных.Сумма = 1250;
Иначе
ВызватьИсключение "Запрос вернул неизвестную собственную строку";
КонецЕсли;
Если Не Верно Тогда
ВызватьИсключение "Значения собственной строки не совпали";
КонецЕсли;
КонецЦикла;
Если (Категория = "" Или Категория = "А85") И (Строки.Найти("Альфа85", "Наименование") = Неопределено
Или Строки.Найти("Гамма85", "Наименование") = Неопределено) Тогда
ВызватьИсключение "Потеряна собственная Альфа85 или Гамма85";
КонецЕсли;
Если (Категория = "" Или Категория = "Б85") И Строки.Найти("Бета85", "Наименование") = Неопределено Тогда
ВызватьИсключение "Потеряна собственная Бета85";
КонецЕсли;
КонецПроцедуры
Процедура ПроверитьСвойВывод85(Документ, Категория)
Если Документ.ВысотаТаблицы = 0 Или Документ.ШиринаТаблицы = 0 Тогда
ВызватьИсключение "Native построитель не вывел собственный макет";
КонецЕсли;
Для Каждого Текст Из СтрРазделить("Свой макет построителя85,Конец своей таблицы85,Своё учебное завершение85", ",") Цикл
Если Документ.НайтиТекст(Текст) = Неопределено Тогда
ВызватьИсключение "В настоящем выводе отсутствует собственная область: " + Текст;
КонецЕсли;
КонецЦикла;
Для Каждого ИмяСтроки Из СтрРазделить("Альфа85,Гамма85,Бета85", ",") Цикл
ДолжнаБыть = Категория = "" Или (Категория = "А85" И ИмяСтроки <> "Бета85")
Или (Категория = "Б85" И ИмяСтроки = "Бета85");
ЕстьВВыводе = Документ.НайтиТекст(ИмяСтроки) <> Неопределено;
Если ЕстьВВыводе <> ДолжнаБыть Тогда
ВызватьИсключение "Реальный макет вывел неправильный состав строк: " + ИмяСтроки;
КонецЕсли;
КонецЦикла;
КонецПроцедуры
Функция СнимокСвоегоДокумента85(Документ)
Если Документ.ВысотаТаблицы > 100 Или Документ.ШиринаТаблицы > 20 Тогда
ВызватьИсключение "Этот helper допускает только свой маленький учебный результат";
КонецЕсли;
Части = Новый Массив;
Части.Добавить(Строка(Документ.ВысотаТаблицы));
Части.Добавить(Строка(Документ.ШиринаТаблицы));
Для НомерСтроки = 1 По Документ.ВысотаТаблицы Цикл
Для НомерКолонки = 1 По Документ.ШиринаТаблицы Цикл
Части.Добавить(Документ.Область(НомерСтроки, НомерКолонки).Текст);
КонецЦикла;
КонецЦикла;
Возврат СтрСоединить(Части, Символы.ПС);
КонецФункции
Процедура ПроверитьСвойПустойСтенд()
Если Метаданные.Справочники.Количество() <> 0 Или Метаданные.Документы.Количество() <> 0 Или Метаданные.Перечисления.Количество() <> 0 Или Метаданные.РегистрыСведений.Количество() <> 0 Или Метаданные.РегистрыНакопления.Количество() <> 0 Или Метаданные.РегистрыБухгалтерии.Количество() <> 0 Или Метаданные.РегистрыРасчета.Количество() <> 0 Или Метаданные.ПланыВидовХарактеристик.Количество() <> 0 Или Метаданные.ПланыВидовРасчета.Количество() <> 0 Или Метаданные.ПланыСчетов.Количество() <> 0 Или Метаданные.ПланыОбмена.Количество() <> 0 Или Метаданные.Последовательности.Количество() <> 0 Или Метаданные.БизнесПроцессы.Количество() <> 0 Или Метаданные.Задачи.Количество() <> 0 Или Метаданные.ОбщиеРеквизиты.Количество() <> 0 Или Метаданные.ПодпискиНаСобытия.Количество() <> 0 Или Метаданные.РегламентныеЗадания.Количество() <> 0 Или Метаданные.ВнешниеИсточникиДанных.Количество() <> 0 Тогда
ВызватьИсключение "Нужен только свой новый пустой учебный стенд";
КонецЕсли;
Если Метаданные.ЕстьИзмененияРасширениямиКонфигурации() Тогда
ВызватьИсключение "Свой сеанс не должен изменяться расширениями";
КонецЕсли;
Источники = Новый Массив;
Источники.Добавить(ИсточникРасширенийКонфигурации.БазаДанных);
Источники.Добавить(ИсточникРасширенийКонфигурации.СеансАктивные);
Источники.Добавить(ИсточникРасширенийКонфигурации.СеансОтключенные);
Для Каждого Источник Из Источники Цикл
Расширения = РасширенияКонфигурации.Получить(, Источник);
Если ТипЗнч(Расширения) <> Тип("Массив") Тогда
ВызватьИсключение "Native список расширений должен иметь тип Массив";
КонецЕсли;
Если Расширения.Количество() <> 0 Тогда
ВызватьИсключение "В своём новом стенде нет расширений базы или сеанса";
КонецЕсли;
КонецЦикла;
Если ТранзакцияАктивна() Тогда
ВызватьИсключение "Чужая или вложенная активная транзакция не допускается";
КонецЕсли;
КонецПроцедуры
#КонецЕслиРазбор по шагам
СформироватьОсновной85 создаёт новый собственный ПостроительОтчета. ЗаполнитьНастройки разбирает собственный текст, затем выбор и измерения устанавливаются явно. Все шесть форматных секций включены, детальные записи выводятся независимо от авто-решения.
Макет — полный собственный табличный документ. Каждое секционное свойство содержит настоящее имя уже созданной области, разрешённое native контрактом Строка/ТабличныйДокумент. Группировка Категория имеет собственный макет. Перед выполнением читаем назначения обратно, а не считаем одно присваивание достаточным доказательством.
Выполнить реально исполняет literal запрос. Прямой native Выгрузить возвращает три детальные строки; проверяются каждое имя/число/сумма и общий итог 9/1950. ОформитьМакет применяет native оформление, затем Вывести формирует настоящий документ. FindText в результате контролирует заголовок, оба подвала и реальные имена всех строк.
Слева найдите строку группы А85 и дважды щёлкните её значение Количество=4. Подлинный native ОбработкаРасшифровки получает Структура из сформированной ячейки; код не создаёт вместо неё Новый Структура. Только существующее собственное измерение Категория со значением А85/Б85 разрешает дальнейший маршрут.
Подтвердите Да в настоящем Вопрос с Да/Нет/Отмена. При Нет, Отмена или таймауте 30 секунд проверяются identity и текстовый снимок предыдущего детального документа; ни новый построитель, ни новый вывод ещё не создаются. СтандартнаяОбработка отключена, чтобы система не выполняла вторую самостоятельную расшифровку.
После Да создаётся отдельный новый собственный построитель с тем же literal запросом и своим макетом. Исходный.НастроитьРасшифровку(Новый, Расшифровка) передаёт именно реальное значение callback. Другие поля структуры не превращаются в отбор: native метод ограничен измерениями раздела ГДЕ. Результат проверки должен дать для А85 только Альфа85/Гамма85 с итогом 4/700.
Документ детализации сначала полностью строится и проверяется в локальном кандидате. Только после числового readback и проверки его настоящих ячеек новый документ присваивается ДетальныйДокумент85. Повторная проверка исходного построителя должна по-прежнему видеть все три строки. Двойной щелчок по группе Б85 и Да заменяет правый результат на одну собственную Бета85, итог 5/1250.
Как проверить результат
Слева видны заголовок Свой макет построителя85, шапка, две группы, три имени деталей, общий итог 9/1950, Конец своей таблицы85 и Своё учебное завершение85. Код проверяет появление текстов и состав результатов; конкретное оформление Весна требует визуальной проверки в своём клиенте.
А85 + Да: справа ровно Альфа85 и Гамма85, никаких Бета85; количество 4, сумма 700. Б85 + Да: справа только Бета85, количество 5, сумма 1250. Левый отчёт не должен потерять группу А85 или Б85.
После успешной детализации А85 нажмите расшифровку Б85 и Отмена, затем повторите Нет, затем дождитесь таймаута. Правый документ с Альфа85/Гамма85 должен сохраняться; состояние прямо сообщает нормальный отказ, не ошибку и не успешную перестройку.
Щелчок по тексту заголовка/подвала без native расшифровки не должен вызывать обработчик. Щелчок по ячейке с неподходящим native значением завершает свой обработчик без выполнения нового отчёта. Нельзя считать такой щелчок успешной расшифровкой.
Для собственного негативного опыта в отдельной копии учебного текста удалите только строку {ГДЕ ...}. Native метод больше не обязан применять Категория; readback детализации должен отклонить полный результат, прежний правый документ останется принят. Не меняйте рабочую конфигурацию и не подставляйте фиктивную структуру вместо cell callback.
Ожидаемый результат
Ожидаемый при ручном запуске результат: собственные секции макета реально участвуют в выводе; native структура расшифровки переключает второй отчёт между 2 и 1 детальными строками без изменения исходного отчёта и без записи данных.
На что обратить внимание
ПостроительОтчета и старый ТабличныйДокумент оформление — не СКД. Не подменяйте Структура расшифровки построителя на идентификатор элемента ДанныеРасшифровкиКомпоновкиДанных.
НастроитьРасшифровку фильтрует только разрешённые измерения секции ГДЕ целевого построителя. Наличие ключа в native структуре само по себе не гарантирует отбор: поэтому результат проверяется до принятия.
ПараметрРасшифровки не равен свойству Расшифровка готовой ячейки. В макете задаётся имя параметра, а actual значение создаёт построитель при выводе. Код не вызывает callback напрямую и не назначает вручную его входную структуру.
Снимок документа проверяет размеры и тексты ячеек, не является полной сериализацией оформления. Статические тесты не доказывают визуальный фон, шрифты, клиентские темы и настоящий UI callback.
При повторном выводе построитель учитывает внутренний флаг: новый построитель и Выполнить обеспечивают реальный новый вывод. Не присваивайте readonly Результат и не заполняйте результат вручную ожидаемыми строками.
Никаких файлов, публикаций, запуска 1С, принтеров, сети или записи базы агент не выполнял. Это код и статическая проверка; ручной запуск и визуальный протокол нужны в указанной собственной учебной базе.
Пример не запускался в вашей базе. Перед применением проверьте его в указанном учебном контексте.