Перестают работать кнопки после отмены страницы редактирования
Коллеги, подскажите, как устранить проблему.
Есть 3 кнопки в AcccountSectionV2. Каждая из них вызывает свой бизнес-процесс, первым элементом в которых стоит открытие страницы редактирования (новой Активности, Счёта или Заказа соответственно). Проблема заключается в том, что после нажатия Отмена на странице редактирования (к примеру, страницы редактирования Счёта) все кнопки в карточке контрагента перестают реагировать на нажатия. По журналу бизнес-процессов видно, что привязанные к кнопкам бизнес-процессы не запускаются, т.е. не отрабатывается код кнопок. Он начинает работать, только если обновить страницу.
Часть кода, создающая кнопки:
"operation": "insert",
"parentName": "CombinedModeActionButtonsCardLeftContainer",
"propertyName": "items",
"name": "MakeInvoiceButton",
"values": {
itemType: Terrasoft.ViewItemType.BUTTON,
caption: "+ Счёт",
style: Terrasoft.controls.ButtonEnums.style.BLUE,
click: {bindTo: "onMakeInvoiceButtonClick"},
"layout": {
"column": 1,
"row": 6,
"colSpan": 1
}
}
}
Часть кода - запуск привязанного бизнес-процесса:
debugger;
var AccountId = this.get("ActiveRow");
var processArgs = {
sysProcessName: "UsrOnMakeInvoiceButtonClick",
parameters: {
IncomingAccountId: AccountId
}
};
ProcessModuleUtilities.executeProcess(processArgs);
}
Бизнес-процесс:
Нравится
Антон,
что видно в консоли браузера в момент нажатия на эти кнопки?
P.S. Прикрепите, пожалуйста, скриншот процесса.
в момент вызова нового процесса в браузере видно следующее сообщение:
При выполнении запроса возникла ошибка
статус ответа: 400 (Bad Request)
url запроса: http://crm:82/0/ServiceModel/ProcessEngineService.svc/UsrOnMakeNeedCall…null
метод: POST
данные запроса: {}
Похоже, что после запуска предыдущего при повторном запуске система не передаёт ID Открытой карточки клиента в повторный процесс. Однако - в журнале процессов нет второго запуска процесса.
Добрый день Антон!!!
конечно Бизнес-процесс у вас маленький, но если честно цель данного бизнес-процесса непонятно. Что вы хотели данным процессом достичь? Проконтролировать заполнено ли определенное поле и если да, то открыть карточку редактирования счета? Или же вы хотели сначала проконтролировать наполняемость всех полей, и если определенные поля заполнены, открыть на редактирование карточку счета. Если так, то в процессе не хватает действий для проверки. Это первое, а второе когда вы Первый раз запустили процесс, то в Процесс (через входящие параметры) запоминает Id контрагента, и когда вы не заново, а продолжаете процесс, тогда система уже начинает с того места где остановилась и при этом помнит уже все входящие параметры.
Михаил, цель простая - открыть предзаполненную карточку счёта из карточки клиента. В начале процесса проверяю условия - указан ли ID контрагента, по которому нужно открыть счёт, а также чтобы тип этого контрагента был равен "Клиент". В иных случаях счёт нам не нужен.
По сути, это аналог кнопки "Добавить" в детали Счета в карточке контрагента.
Последний Ваш комментарий не понял - я отменил выполнение предыдущего процесса и запускаю новый из той же карточки. Вот новый у меня и не начинается из-за того, что система не передаёт второй раз ID контрагента, карточка которого открыта в настоящий момент
"Антон Кравченко" написал: Вот новый у меня и не начинается из-за того, что система не передаёт второй раз ID контрагента, карточка которого открыта в настоящий момент
Антон вопрос так откуда вы вызываете бизнес-процесс из Раздела или Открытой карточки редактирования. Так как обращение и получение Id контрагента будут разными. Если из раздела, то нужно еще проверить, а не включен ли режим "Выбора нескольких записей" и если да получить массив Id и передать в процесс, если это карточка редактирования то напрямую получить "this.get(this.entitySchema.primaryColumnName)" и все. И еще один совет если в Бизнес-процесс передаются Массив значений, Id и не только то обязательно, прежде чем вызвать процесс, вы добавьте условия проверки на "Существование" и "Заполненность" передаваемых значений а уже после запускайте процесс. И уже на экране у вас уже не будут появляться ошибки, а вы будите видеть, что процесс запустился или нет. И вот если уже не запустился это уже будет означать, что сработал ваш "IF". Я бы так сделал.
Михаил, хорошо, давайте проверим:
1. Код кнопки у меня расположен и в *Page и в *Section. Из Section в процесс передаётся this.get("ActiveRow"), из Page - this.get("ID")
2. Режим "Выбора нескольких записей не включен 100%
3. При проверке открыта карточка контрагента через Section (т.е. слева есть список других контрагентов, а ссылка в браузере выглядит как .../ ... Section ... / UsrAccountType1Page / edit / ID
4. Вы пишете про проверку на существование и заполненность. Чем Вам первое условие в моём процессе не нравится? в нём как раз и проверяю, что переданный ID != Guid.Empty
Я подозреваю, что после запуска процесса система как бы "выходит" из режима, когда выделена одна из записей реестра (т.е. this.get("ActiveRow") возвращает null), а после обновления страницы снова выделяет того контрагента, чья карточка на экране (т.е. this.get("ActiveRow") возвращает ID выделенной записи).
Как можно проверить данное предположение?
"Антон Кравченко" написал:в нём как раз и проверяю, что переданный ID != Guid.Empty
Антон во первых в процесс может, через входящий параметр, передаться значение ("", String.Empty, т.е пустое значение) или передаться значение "undefined". Можно конечно это все проверить на C# в бизнес-процессе, но зачем если это можно сделать на клиенте. На C# нужно будет не забывать про правила конвертации, чтобы синтаксис был правильный. На JavaScript это проще. Это всего лишь моя рекомендация.
Возвращаясь к вашему вопросу хочу сказать, что по умолчанию в конфигурациях BPMOnline есть маленький баг. Но он быстро правиться. Проверяется этот баг очень просто. Открываете карточку редактирования (к примеру Контрагента) из раздела. И на карточке в любом LookupEdit поле выполняете "Выбор из справочника" и при выборе к примеру редактируете выбираемую запись сохраняете и смотрите. Если слева, где список контрагентов, теряется фокус. То тогда да, ваше предположение может быть, что при подачи команды this.get("ActiveRow")
возвращается "null" или "неопределено", то тогда я вам подскажу где этот маленький баг исправить. Я его уже давно обнаружил, еще в 7.3. Проведите эксперимент если фокус потеряется, я вам подскажу как это поправить.
Михаил, фокус не теряется при Вашем способе с LookupEdit, однако в нашей ситуации с кнопками теряется - см. скриншоты
Добрый день Антон!!!
выполните замещение схемы GridUtilitiesV2, исправьте Функцию "ensureActiveRowVisible"
ниже приведен исправленный текст функции. Жирным выделена строка, что добавлена.
/** * Прокручивает реестр, чтобы была видна активная строка. * @protected */ ensureActiveRowVisible: function() { var grid = this.getCurrentGrid(); var activeRow = this.get("ActiveRow"); if (grid && activeRow) { var activeRowDom = grid.getDomRow(activeRow); if (activeRowDom && activeRowDom.dom) { // TODO: Добавлена строка по фиксации активной записи реестра grid.setActiveRow(activeRow); var el = activeRowDom.dom; if (el.scrollIntoViewIfNeeded) { el.scrollIntoViewIfNeeded(false); } else { el.scrollIntoView(false); } } } },
Выполните пожалуйста замещение схемы и проверьте результат. У меня сейчас фокус никогда не теряется. При замещение схемы не забываем копировать не одну функцию а все. Иначе перестанет работать функционал.
Михаил, доброго утра!
Заместил GridUtilitiesV2, полностью скопировал код из замещаемой в замещающую страницу, исправил функцию ensureActiveRowVisible ... и ничего не изменилось - фокус по-прежнему теряется.
P.S. Вы пишете, что жирным выделена добавляемая в функцию ensureActiveRowVisible строка, но в Вашем коде не вижу строки с жирным шрифтом ..
Добрый день Антон!!!
воспроизвел вашу ситуацию на своей базе данных. Действительно Фокус теряется и информация о текущей записи теряется. Буду сегодня в отладчике искать, где происходит сбой. Как найду выход из данной ситуацию. Опубликую результат с ответом.
Антон самый быстрый способ который я нашел и советую вам его использовать. Это сохранение ID в профиль пользователя. Вот как я сделал и после отмены или закрытия карточки редактирования (вызванная из процесса) фокус сейчас у меня нормально возвращается. вот листинг. так же замещаем схему GridUtilitiesV2.
/** * Восстановление выделенной записи в реестре. */ onAfterReRender: function() { if (this.cachedActiveRow && !this.get("MultiSelect")) { var gridData = this.getGridData(); if (gridData && gridData.contains(this.cachedActiveRow)) { this.set("ActiveRow", this.cachedActiveRow); } } else if (!this.cachedActiveRow && !this.get("MultiSelect")) { var profile = this.getProfile(); var activeRow = !Ext.isEmpty(profile.ActiveRow) ? profile.ActiveRow : this.Terrasoft.GUID_EMPTY; if (!Ext.isEmpty(activeRow)) { this.set("ActiveRow", activeRow); } } },
/** * Событие на изменение значения ActiveRow. */ onActiveRowChange: function() { this.cachedActiveRow = this.get("ActiveRow") || this.cachedActiveRow; if (!Ext.isEmpty(this.cachedActiveRow)) { var profile = this.getProfile(); var key = this.getProfileKey(); if (profile && key) { profile.ActiveRow = this.cachedActiveRow; this.Terrasoft.utils.saveUserProfile(key, profile, false); } } },
приведенные выше 2 функции замещаем. и пробуем исполнить с Нуля свой процесс отменить. Проверить, что вернулся фокус и продолжить с остановленного месте или заново начать как вам удобно.
Михаил, отлично! Ваше решение работает) Спасибо большое
Я рад Антон. Что вам помог. Вы первую мою доработку тоже к себе в код включите, полезна будет. А так я рад. Будут еще вопросы, проблемы пишите, буду рад вам помочь.