Мы рассмотрим распространенные причины, по которым бизнес-процесс или задача могут не стартовать в нетиповой конфигурации 1С, и разберем подходы к диагностике и устранению таких проблем. В нашем случае, проблема связана с ошибкой передачи второго параметра в процедуру записи задачи, что является частой причиной сбоев в работе автоматизированных процессов.
Давайте разберем типичную ситуацию: бизнес-процесс, работающий для одного документа, отказывается стартовать для другого, несмотря на кажущуюся аналогичность кода и настроек. Часто это указывает на тонкие различия в данных или обработке, которые приводят к сбою. Нам было указано, что проблема заключается в ошибке при передаче второго параметра в процедуру на 28-й строчке кода.
ПриЗаписи или ПередЗаписью, где происходит взаимодействие с другими процедурами и передача параметров.Особое внимание следует уделить переменной Отказ, которая часто передается вторым параметром в обработчики событий и вспомогательные процедуры. Ее некорректная обработка или передача по значению вместо передачи по ссылке может привести к неожиданному поведению системы, когда запись объекта или старт бизнес-процесса блокируется без видимой причины.
Рассмотрим фрагмент кода, который был предоставлен из процедуры ПриЗаписи модуля объекта задачи. Этот код важен, так как он демонстрирует логику, которая может быть причиной проблемы.
///////////////////////////////////////////////////////////////////////////////////////////////////////
// Copyright © 2024, ООО 1С-Софт
// Все права защищены. Эта программа и сопроводительные материалы предоставляются
// в соответствии с условиями лицензии Attribution 4.0 International (CC BY 4.0)
// Текст лицензии доступен по ссылке:
//
///////////////////////////////////////////////////////////////////////////////////////////////////////
#Если Сервер Или ТолстыйКлиентОбычноеПриложение Или ВнешнееСоединение Тогда
#Область ОбработчикиСобытий
Процедура ОбработкаПроверкиЗаполнения(Отказ, ПроверяемыеРеквизиты)
ЗадачаБылаВыполнена = ОбщегоНазначения.ЗначениеРеквизитаОбъекта(Ссылка, "Выполнена");
Если Выполнена И ЗадачаБылаВыполнена <> Истина И НЕ РеквизитыАдресацииЗаполнены Тогда
ОбщегоНазначения.СообщитьПользователю(
НСтр("ru = 'Укажите исполнителя задачи.'"),,, "Объект.Исполнитель", Отказ);
Возврат;
КонецЕсли;
Если СрокИсполнения <> '00010101' И ДатаНачала > СрокИсполнения Тогда
ОбщегоНазначения.СообщитьПользователю(
НСтр("ru = 'Дата начала исполнения не должна превышать крайний срок.'"),,, "Объект.ДатаНачала", Отказ);
Возврат;
КонецЕсли;
КонецПроцедуры
Процедура ПриКопировании(ОбъектКопирования)
Дата = ТекущаяДатаСеанса;
КонецПроцедуры
Процедура ПередЗаписью(Отказ)
Если ОбменДанными.Загрузка Тогда
Возврат;
КонецЕсли;
Если НЕ Ссылка.Пустая Тогда
ИсходныеРеквизиты = ОбщегоНазначения.ЗначенияРеквизитовОбъекта(Ссылка, "Выполнена, ПометкаУдаления, СостояниеБизнесПроцесса");
Иначе
ИсходныеРеквизиты = Новый Структура(
"Выполнена, ПометкаУдаления, СостояниеБизнесПроцесса",
Ложь, Ложь, Перечисления.СостоянияБизнесПроцессов.ПустаяСсылка);
КонецЕсли;
Если ИсходныеРеквизиты.ПометкаУдаления <> ПометкаУдаления Тогда
БизнесПроцессыИЗадачиСервер.ПриПометкеУдаленияЗадачи(Ссылка, ПометкаУдаления);
КонецЕсли;
Если НЕ ИсходныеРеквизиты.Выполнена И Выполнена Тогда
Если СостояниеБизнесПроцесса = Перечисления.СостоянияБизнесПроцессов.Остановлен Тогда
ВызватьИсключение НСтр("ru = 'Нельзя выполнять задачи остановленных бизнес-процессов.'");
КонецЕсли;
// Если задача выполнена, то запишем в реквизит Исполнитель того
// пользователя, который фактически выполнил задачу. Это нам потом
// потребуется для отчетов. Такую запись делаем только в том
// случае, если в базе было не выполнено, а в объекте стало выполнено.
Если НЕ ЗначениеЗаполнено(Исполнитель) Тогда
Исполнитель = Пользователи.АвторизованныйПользователь;
КонецЕсли;
Если ДатаИсполнения = Дата(1, 1, 1) Тогда
ДатаИсполнения = ТекущаяДатаСеанса;
КонецЕсли;
ИначеЕсли НЕ ПометкаУдаления И ИсходныеРеквизиты.Выполнена И Выполнена Тогда
ОбщегоНазначения.СообщитьПользователю(
НСтр("ru = 'Эта задача уже была выполнена ранее.'"),,,, Отказ);
Возврат;
КонецЕсли;
Если Важность.Пустая Тогда
Важность = Перечисления.ВариантыВажностиЗадачи.Обычная;
КонецЕсли;
Если НЕ ЗначениеЗаполнено(СостояниеБизнесПроцесса) Тогда
СостояниеБизнесПроцесса = Перечисления.СостоянияБизнесПроцессов.Активен;
КонецЕсли;
ПредметСтрокой = ОбщегоНазначения.ПредметСтрокой(Предмет);
Если НЕ Ссылка.Пустая И ИсходныеРеквизиты.СостояниеБизнесПроцесса <> СостояниеБизнесПроцесса Тогда
УстановитьСостояниеПодчиненныхБизнесПроцессов(СостояниеБизнесПроцесса);
КонецЕсли;
Если Выполнена И Не ПринятаКИсполнению Тогда
ПринятаКИсполнению = Истина;
ДатаПринятияКИсполнению = ТекущаяДатаСеанса;
КонецЕсли;
// СтандартныеПодсистемы.УправлениеДоступом
УстановитьПривилегированныйРежим(Истина);
ГруппаИсполнителейЗадач = БизнесПроцессыИЗадачиСервер.ГруппаИсполнителейЗадач(РольИсполнителя, ОсновнойОбъектАдресации, ДополнительныйОбъектАдресации);
УстановитьПривилегированныйРежим(Ложь);
// Конец СтандартныеПодсистемы.УправлениеДоступом
// Заполнение реквизита ДатаПринятияКИсполнению.
Если ПринятаКИсполнению И ДатаПринятияКИсполнению = Дата('00010101') Тогда
ДатаПринятияКИсполнению = ТекущаяДатаСеанса;
КонецЕсли;
Если ДополнительныеСвойства.Свойство("ТолькоПроверка") И ДополнительныеСвойства.ТолькоПроверка Тогда
Выполнена = Ложь;
КонецЕсли;
КонецПроцедуры
Процедура ОбработкаЗаполнения(ДанныеЗаполнения, ТекстЗаполнения, СтандартнаяОбработка)
Если ТипЗнч(ДанныеЗаполнения) = Тип("ЗадачаОбъект.ЗадачаИсполнителя") Тогда
ЗаполнитьЗначенияСвойств(ЭтотОбъект, ДанныеЗаполнения, "БизнесПроцесс,ТочкаМаршрута,Наименование,Исполнитель,РольИсполнителя,ОсновнойОбъектАдресации," +
"ДополнительныйОбъектАдресации,Важность,ДатаИсполнения,Автор,Описание,СрокИсполнения," +
"ДатаНачала,РезультатВыполнения,Предмет");
Дата = ТекущаяДатаСеанса;
КонецЕсли;
Если НЕ ЗначениеЗаполнено(Важность) Тогда
Важность = Перечисления.ВариантыВажностиЗадачи.Обычная;
КонецЕсли;
Если НЕ ЗначениеЗаполнено(СостояниеБизнесПроцесса) Тогда
СостояниеБизнесПроцесса = Перечисления.СостоянияБизнесПроцессов.Активен;
КонецЕсли;
КонецПроцедуры
#КонецОбласти
#Область СлужебныеПроцедурыИФункции
Процедура УстановитьСостояниеПодчиненныхБизнесПроцессов(НовоеСостояние)
НачатьТранзакцию;
Попытка
ПодчиненныеБизнесПроцессы = БизнесПроцессыИЗадачиСервер.БизнесПроцессыГлавнойЗадачи(Ссылка, Истина);
Для Каждого ПодчиненныйБизнесПроцесс Из ПодчиненныеБизнесПроцессы Цикл
БизнесПроцессОбъект = ПодчиненныйБизнесПроцесс.ПолучитьОбъект;
БизнесПроцессОбъект.Заблокировать;
БизнесПроцессОбъект.Состояние = НовоеСостояние;
БизнесПроцессОбъект.Записать;
// АПК:1327 Блокировка установлена в БизнесПроцессыИЗадачиСервер.БизнесПроцессыГлавнойЗадачи.
КонецЦикла;
ЗафиксироватьТранзакцию;
Исключение
ОтменитьТранзакцию;
ВызватьИсключение;
КонецПопытки;
КонецПроцедуры
// Определяет, заполнены ли реквизиты адресации: исполнитель или роль исполнителя
//
// Возвращаемое значение:
// Булево - возвращает Истина, если в задаче указан исполнитель или роль исполнителя.
//
Функция РеквизитыАдресацииЗаполнены
Возврат ЗначениеЗаполнено(Исполнитель) ИЛИ НЕ РольИсполнителя.Пустая;
КонецФункции
Процедура ПриЗаписи(Отказ)
Если ТочкаМаршрута = БизнесПроцессы.ОбработкаДокументаКЭДО.ТочкиМаршрута.ДействиеВыполнитьЭтапПроцесса Тогда//это задача процесса обработки документа КЭДО
БизнесПроцессы.ОбработкаДокументаКЭДО.ОбработкаЗаписиЗадачи(ЭтотОбъект, Отказ);
ИначеЕсли ТочкаМаршрута = БизнесПроцессы.Согласование.ТочкиМаршрута.ДействиеСогласовать Тогда//это задача процесса согласования
БизнесПроцессы.Согласование.ОбработкаЗаписиЗадачи(ЭтотОбъект, Отказ);
КонецЕсли;
КонецПроцедуры
#КонецОбласти
#Иначе
ВызватьИсключение НСтр("ru = 'Недопустимый вызов объекта на клиенте.'");
#КонецЕсли
В этом коде, в конце модуля объекта задачи, находится процедура ПриЗаписи. Внутри нее мы видим вызовы процедур из общих модулей бизнес-процессов:
БизнесПроцессы.ОбработкаДокументаКЭДО.ОбработкаЗаписиЗадачи(ЭтотОбъект, Отказ);БизнесПроцессы.Согласование.ОбработкаЗаписиЗадачи(ЭтотОбъект, Отказ);Вероятно, "28-я строчка" и "второй параметр" указывают на проблему с переменной Отказ, которая передается в эти вспомогательные процедуры. Передача переменной Отказ по ссылке крайне важна, чтобы в вызывающей процедуре (ПриЗаписи модуля задачи) можно было остановить запись объекта, если внутри вспомогательной процедуры обнаружены какие-либо ошибки или несоответствия.
Если в одной из этих процедур ОбработкаЗаписиЗадачи переменная Отказ устанавливается в Истина, а в коде, который эти процедуры вызывает (то есть в самой ПриЗаписи модуля объекта задачи), нет проверки этого значения Отказ или переменная передается по значению, то бизнес-процесс может не стартовать или задача не будет записана.
Давайте разберем наиболее частые причины, по которым бизнес-процессы и задачи могут вести себя некорректно, основываясь на нашем случае и общей практике разработки на платформе 1С:Предприятие.
Некорректная передача параметров: Как в нашем случае, ошибка при передаче данных в процедуры, особенно параметров, передаваемых по ссылке (например, переменная Отказ), может препятствовать корректному выполнению. Рассмотрим подробнее:
Перем, он передается по значению. Это значит, что любые изменения этого параметра внутри процедуры не повлияют на исходную переменную в вызывающем коде. Для таких параметров, как Отказ, это критично, так как мы ожидаем, что вспомогательная процедура сможет сигнализировать об ошибке обратно в основной код.Отсутствие вызова метода Старт(): Бизнес-процесс не начнет работу и не создаст задачи, если для него не был вызван метод Старт(). Это фундаментальное требование для запуска любого бизнес-процесса в 1С.
Старт(), либо нажать соответствующую кнопку в форме объекта..Старт() для нового экземпляра бизнес-процесса.Стартован = Истина не приводит к созданию задач. Если после такой установки попытаться вызвать Старт(), возникнет ошибка, так как система уже считает процесс стартованным. Такой подход используется только для бизнес-процессов со свободной маршрутизацией, где задачи создаются произвольно.ПередСтартом: В модуле объекта бизнес-процесса существует обработчик ПередСтартом(Отказ, СтандартнаяОбработка). Если в этом обработчике по каким-либо условиям Отказ устанавливается в Истина, бизнес-процесс не стартует.Проблемы с адресацией задач: Если реквизиты, отвечающие за адресацию задачи (Исполнитель, РольИсполнителя, ОсновнойОбъектАдресации, ДополнительныйОбъектАдресации), не заполнены или заполнены некорректно, система может отказаться создавать задачу, или задача будет создана, но останется без назначенного исполнителя, что эквивалентно неработоспособности.
Ошибки в обработчиках событий объекта задачи или бизнес-процесса: Процедуры ПередЗаписью, ПриЗаписи, ОбработкаПроверкиЗаполнения, ОбработкаЗаполнения модуля объекта задачи или бизнес-процесса могут содержать логику, которая блокирует старт или запись.
Отказ = Истина: Тщательно проверьте все места, где переменная Отказ может быть установлена в Истина. Это прерывает стандартную обработку и может быть причиной того, что задача или бизнес-процесс не записывается или не стартует.Несоответствие данных или условий: Бизнес-процесс может быть настроен на старт при определенных условиях (например, при определенном статусе документа, заполнении конкретного реквизита или выполнении определенной функции).
Предмет: Убедитесь, что реквизит Предмет у задачи и бизнес-процесса заполнен корректно и указывает на нужный объект (например, документ-основание).Нетиповые изменения и конфликты: В нетиповых конфигурациях часты ситуации, когда измененный или добавленный код конфликтует с обновлениями платформы или конфигурации, или с другими доработками. Аналогия с "первым документом" может быть ложной, если контексты или данные, для которых он запускался, различаются (например, разные виды документов, разные пользователи, разные даты).
Недостаток прав пользователя: Убедитесь, что у пользователя, под которым происходит попытка старта бизнес-процесса или создания задачи, есть все необходимые права на соответствующие объекты и действия (создание, чтение, изменение, проведение документов, запуск бизнес-процессов, создание задач).
Повреждение кэша: Иногда проблемы с запуском 1С, включая работу бизнес-процессов, могут быть вызваны поврежденным кэшем клиента или сервера. Очистка кэша является одной из первых мер при поиске причины многих необъяснимых сбоев.
%LOCALAPPDATA%\1C\1CE\).Для эффективного выявления причин неработоспособности бизнес-процесса или задачи, активно используем встроенные средства отладки 1С. Это ваш главный инструмент для понимания того, что происходит "под капотом".
Отладчик 1С: Незаменимый инструмент для любого программиста 1С. Он позволяет пошагово выполнять код и отслеживать значения переменных, а недавние разработки позволяют научить ИИ помогать в процессе отладки, просматривая стек и значения переменных.
ПередСтартом модуля объекта бизнес-процесса.ПриЗаписи, ПередЗаписью модуля объекта задачи. В нашем случае, это процедура ПриЗаписи в модуле объекта задачи (где мы видели вызовы ОбработкаЗаписиЗадачи).Отказ (например, БизнесПроцессы.ОбработкаДокументаКЭДО.ОбработкаЗаписиЗадачи), чтобы пошагово отследить, при каких условиях и в какой момент значение Отказ меняется на Истина.Отказ.Отладка на сервере: Если проблема происходит в серверном коде (что очень вероятно для логики бизнес-процессов и фоновых заданий), убедитесь, что включена отладка на сервере 1С:Предприятия. По умолчанию, в клиент-серверном варианте она отключена. Для включения необходимо добавить ключ -debug в строку запуска сервера 1С в реестре или параметрах службы. Существуют также специфические методики для отладки внешних печатных форм и обработок, которые часто выполняются на сервере.
Журнал регистрации: Регулярно просматривайте журнал регистрации 1С. Там могут быть записаны ошибки, исключения, предупреждения или информационные сообщения, которые явно укажут на причину проблемы или ее предпосылки.
Сравнение объектов и кода: В нашем случае, когда "в первом стартует, во втором нет", тщательно сравните настройки бизнес-процессов, данные документов, и, главное, весь код, отвечающий за старт для обоих случаев. Возможно, есть тонкие различия в условиях, передаваемых параметрах, или даже в версиях метаданных.
ОтказЕсли проблема действительно связана с некорректной передачей или обработкой второго параметра (Отказ) в процедурах, следующие шаги помогут ее выявить и решить:
Проверьте объявление процедуры: Убедитесь, что вспомогательная процедура (например, ОбработкаЗаписиЗадачи в нашем примере) принимает второй параметр по ссылке. В 1С это делается явно с использованием ключевого слова Перем.
Пример корректного объявления:
Процедура ИмяПроцедуры(Параметр1, Перем Отказ)
// ... логика, которая может изменить Отказ ...
Если УсловиеОшибки Тогда
Отказ = Истина;
ОбщегоНазначения.СообщитьПользователю("Обнаружена ошибка при обработке.");
КонецЕсли;
КонецПроцедуры
Если Перем отсутствует, параметр передается по значению, и любые изменения Отказ внутри процедуры не отразятся на исходной переменной в вызывающем коде, что приведет к тому, что система не узнает об отказе и продолжит выполнять дальнейшие действия.
Анализируйте логику внутри процедуры: Используя отладчик, пошагово отследите выполнение кода внутри процедур ОбработкаЗаписиЗадачи. Выясните, при каких условиях Отказ устанавливается в Истина. Возможно, для "второго документа" срабатывают какие-то специфические условия проверки, которых нет для "первого", и они приводят к отмене операции.
Если ... Тогда, где могут выполняться проверки и устанавливаться значение Отказ.Использование ОбщегоНазначения.СообщитьПользователю: Если Отказ устанавливается в Истина, обязательно сопровождайте это информативным сообщением пользователю. Это поможет не только вам при отладке, но и конечным пользователям понять причину отказа записи или старта бизнес-процесса.
Пример:
Если УсловиеОшибки Тогда
Отказ = Истина;
ОбщегоНазначения.СообщитьПользователю("Невозможно стартовать бизнес-процесс: не заполнен обязательный реквизит 'ТипОперации'.");
Возврат;
КонецЕсли;
Такое сообщение значительно упрощает диагностику проблемы и улучшает пользовательский опыт.
Добавьте проверку Отказ после вызова: В вызывающей процедуре (например, ПриЗаписи модуля объекта задачи), после вызова вспомогательной процедуры, которая могла бы изменить Отказ, добавьте явную проверку.
Пример:
Процедура ПриЗаписи(Отказ)
// ...
Если ТочкаМаршрута = БизнесПроцессы.ОбработкаДокументаКЭДО.ТочкиМаршрута.ДействиеВыполнитьЭтапПроцесса Тогда
БизнесПроцессы.ОбработкаДокументаКЭДО.ОбработкаЗаписиЗадачи(ЭтотОбъект, Отказ);
Если Отказ Тогда // Проверяем, был ли установлен отказ
Возврат; // Прерываем дальнейшую запись, если была ошибка
КонецЕсли;
ИначеЕсли ТочкаМаршрута = БизнесПроцессы.Согласование.ТочкиМаршрута.ДействиеСогласовать Тогда
БизнесПроцессы.Согласование.ОбработкаЗаписиЗадачи(ЭтотОбъект, Отказ);
Если Отказ Тогда // Проверяем, был ли установлен отказ
Возврат; // Прерываем дальнейшую запись, если была ошибка
КонецЕсли;
КонецЕсли;
// ... дальнейшая логика, если Отказ не был установлен
КонецПроцедуры
Такая явная проверка гарантирует, что при возникновении ошибки во вспомогательной процедуре, основная логика записи объекта будет прервана.