Поля документа в процессе - списки, файлы, запись обратно
Разбираем работу с полями документа внутри процесса: что именно приходит в действие с кодом и что происходит при записи значений обратно.
Решение
Читаем поля документа в действии с кодом:
$rootActivity = $this->GetRootActivity();$documentId = $rootActivity->GetDocumentId(); // массив из трёх частей$service = CBPRuntime::GetRuntime()->GetService('DocumentService');$document = $service->GetDocument($documentId); // массив полей, а не объектprintf("название=%s статус=%s\n", $document['NAME'], $document['PROPERTY_STATUS'] ?? '-');Документ приходит в код массивом полей, а не объектом. Имена полей совпадают с теми, что показывает дизайнер процессов, и это самый быстрый способ понять, что вообще доступно на этом шаге.
Разворачиваем поле-список:
$key = $document['PROPERTY_STATUS']; // приходит ключ значения$prop = CIBlockProperty::GetByID('STATUS', 5)->Fetch();$res = CIBlockPropertyEnum::GetList([], ['PROPERTY_ID' => $prop['ID'], 'XML_ID' => $key]);$enum = $res->Fetch();printf("подпись значения=%s\n", $enum['VALUE'] ?? $key);// сравнивать в условии процесса нужно именно ключ, а не подпись значенияПоле-список отдаёт в процесс ключ значения, а не его подпись. Сравнение с текстом «В работе» в условии процесса поэтому не срабатывает, и правильное сравнение идёт с кодом значения, а не с тем, что видит человек.
Забираем файл из поля:
$fileId = $document['PROPERTY_SCAN'];$file = CFile::GetFileArray($fileId); // путь получают по идентификаторуprintf("файл=%s размер=%d\n", $file['SRC'] ?? '-', $file['FILE_SIZE'] ?? 0);В поле файла лежит только идентификатор, а не путь. Отправка такого значения во внешнюю систему без разворота даёт число вместо документа, и получатель об этом узнаёт не сразу.
Пишем значение обратно в документ:
$service = CBPRuntime::GetRuntime()->GetService('DocumentService');$service->UpdateDocument($documentId, ['PROPERTY_STATUS' => $newKey], $modifiedBy);// правка документа снова поднимает события и может запустить процесс заново// третий аргумент - от чьего имени сделана правка: он попадёт в журналЗапись в документ поднимает ровно те же события, что и обычное сохранение. Процесс, запускающийся на изменение документа и правящий документ, зацикливается, и останавливает его только признак, по которому он узнаёт собственную правку.
Значения между действиями схемы передают переменными процесса, а не полями документа. Поле - это общее состояние, видимое всем, а переменная живёт внутри экземпляра и никому не мешает.
Действие с кодом стоит держать коротким, а всю логику выносить в свой класс. Тогда её видно в системе контроля версий, а дизайнер процессов остаётся схемой, а не хранилищем исходников.
Имена полей и переменных чувствительны к регистру. Опечатка в имени не даёт ошибки: подстановка молча возвращает пустое значение, и разбор начинается с проверки написания.
Типичные проблемы
Условие по полю-списку никогда не выполняется.
Сравнение идёт с подписью значения, а в процесс приходит его ключ. Сравнивать нужно с кодом значения из справочника этого свойства.
Во внешнюю систему уходит число вместо файла.
В поле файла лежит только идентификатор, а не путь к нему. Сам файл получают отдельным вызовом по этому идентификатору.
Процесс запускается снова и снова.
Он правит документ, на изменение которого сам же и запускается. Нужен признак, по которому процесс узнаёт собственную правку.
Подстановка возвращает пустое значение.
Имя поля написано с другим регистром или просто с опечаткой. Платформа в этом случае об ошибке никак не сообщает.
Значение из первой ветки не видно во второй.
Оно записано в локальную переменную кода, а не в переменную процесса. Между действиями схемы данные передают только переменными процесса.
Частые вопросы
Где посмотреть список доступных полей?
В дизайнере процессов при вставке подстановки. Он показывает и поля документа, и переменные процесса.
Можно ли менять поля документа без правки самого документа?
Нет: любое изменение поля - это сохранение документа со всеми его событиями. Иначе данные разъедутся с индексом и кэшем.
Как передать значение в следующий процесс?
Через поле документа либо через свою таблицу. Переменные процесса живут только внутри своего экземпляра.
Почему множественное поле приходит массивом?
Потому что значений может быть несколько. Код, ожидающий строку, ломается на первом же документе с двумя значениями.
Смежное
- Бизнес-процессы - оглавление подтемы
- Согласование по цепочке: маршрут, замещение, сроки - куда пишут итог согласования
- PHP-код в бизнес-процессе: переменные, типы, отладка - где выполняется этот код
- Бизнес-процесс над элементом списка: поля, раздел, PHP-код - процессы над универсальными списками
- Свойства-списки: значения, сортировка, значение по умолчанию - откуда берутся ключи значений
- Модули и решения - устройство модулей целиком