Были в объекте две колонки, обе обязательные для заполнения.
Сейчас необходимость в обязательности отпала.
Выставил в объекте свойство "Обязателбна для заполнения" в "нет".
Перенес изменения, сгенерировал код, проверил - перенеслось, почистил профиль, редис и кеш браузера.
В странице карточки редактирования записи признаки обязательно для заполнения у полей не стоят.

Все равно поля остаются обязательными и ругается требуя их заполнить.

Это что механизьм как нипель работает? Отменить уже нельзя?

Нравится

4 комментария

Также обязательность могла проставиться в карточке в колонке датасорса. Посмотреть можно в метаданных. Исправить — там же, или же просто удалить в карточке колонку датасорса и создать заново.

о как. Попробую.

Ну у колонки датасорса в карточке редактирвоания такого признака просто нет.

А вот удаление/добавление колонок помогло. :-)
Сенькс.

Он должен быть, если установлен, видимым в метаданных. В дизайнере это свойство не показывается.

Например, поле Name у контакта в режиме редактирования:

{
  "CP1": "c7d8e34a4f1bf4788b57dcad801c2f0bb",
  "UId": "65c7bbe5-2bb3-46b9-8afc-ec988bd13bf8",
  "CP3": "Name",
  "CP5": "10e5b380-25f3-474d-8dec-6b4084180ac7",
  "CP6": "10e5b380-25f3-474d-8dec-6b4084180ac7",
  "CP25": "Name",
  "CP27": "a5cca792-47dd-428a-83fb-5c92bdd97ff8",
  "CP20": 1,
  "CP21": 1,
  "CP28": true
},

Оно же в режиме просотра:

{
  "ID": "c3980e1af43094f35b319f3eccb295ee5",
  "UId": "65c7bbe5-2bb3-46b9-8afc-ec988bd13bf8",
  "Name": "Name",
  "CreatedInSchemaUId": "10e5b380-25f3-474d-8dec-6b4084180ac7",
  "ModifiedInSchemaUId": "10e5b380-25f3-474d-8dec-6b4084180ac7",
  "Path": "Name",
  "MetaPath": "a5cca792-47dd-428a-83fb-5c92bdd97ff8",
  "OrderDirection": 1,
  "OrderPosition": 1,
  "Required": true
},

Я про дизайнер и говорил.
А в метаданных допереть что CP28 это то что нам надо -- та еще задача.
В режиме просмотра оно конечно Required, но это сначала там найти, потом сям, потом поменять. И так два раза. Проще удалить/добавить.
Ладно, проехали, главное все решается быстро и просто.

Показать все комментарии

Как сконструировать условие OR в Select`е? Есть запрос на TSQL:

SELECT *
FROM
[dbo].[WorkUnitAction]
WHERE
[WorkUnitId] = @p1
AND [Id] > @p2
AND [CreatedOn] @p3
AND NOT [ActionResultId] IS NULL
AND ([GroupId] > @p4 OR GroupId IS NULL)
ORDER BY
[CreatedOn] DESC

нужно его написать на шарпе..

Нравится

3 комментария

Как-то так:

...
                .And().OpenBlock("GroupId").IsNotEqual(Column.Parameter(p4))
                        .Or("GroupId").IsNull()
                .CloseBlock()
...

Тут больше по теме.

"Зверев Александр" написал:
Тут больше по теме.

За пример спасибо! А ссылка не открывается, почему-то "У Вас нет доступа к этой странице"(

Алексей, цитирую ту самую страницу.

"Венжик Игорь" написал:

Часто возникает ситуация когда необходимо сделать специфичечкий запрос к БД, который невозможно или сложно воспроизвести с помощью бизнес-сущностей. Например запросы к таблицам прав доступа, к системным таблицам. (Не законченная статья...)

В таких случая необходимо строить кастомные запросы:

Select select =

        new Select(UserConnection)

                .Column("Id")

                .Column("SysSchemaId")

                .Column("Name")

                .Column("SysSchemaManagerName")

                .Column("SysSchemaFolderId")

                .Column("MetaDataModifiedOn")

        .From("VwSysSchemaInSolution")

        .Where("SysSolutionId").IsEqual(new QueryParameter("solutionId", userConnection.Solution.Id))

                .And("SysSchemaId").In(schemas)

                .And("SysSchemaStateInSolution").IsNotEqual(Column.Const((int)StoringObjectState.Deleted))

                .And().OpenBlock("LockedById").IsNull()

                        .Or("LockedById").IsEqual(new QueryParameter("currentUserId", userConnection.CurrentUser.Id))

                .CloseBlock()

                as Select;

Для выполнения запросов к БД в нашей системе есть специальный объект DBExecutor. Экземпляр которого содержится в каждом UserConnection-е. То есть одному пользователю всегда доступен только один экземпляр DBExecutor-а, и пользователь не может сам создавать новые экземпляры.

Что бы получить экземпляр DBExecutor-а необходимо вызвать метод UserConnection.EnsureDBConnection().

using (var dbExecutor = UserConnection.EnsureDBConnection()) {



}

Для вызова всегда необходимо использовать конструкцию using!

Давайте раcсмотрим несколько вариантов работы

Допустим нам необходимо выполнить простой запрос:

Select select =

        new Select(UserConnection)

                .Column("Name")

        .From("Contact")

        .Where("City").IsEqual(Column.Parameter("Киев"))

  1. Получение значения из первой строки, первого столбца выборки

    Есть два способа

    var name = select.ExecuteScalar<string>();

    или

    string name;

    using (var dbExecutor = UserConnection.EnsureDBConnection()) {

            name = select.ExecuteScalar<string>(dbExecutor);

    }

    Оба способа вернут один и тот же результат. Если вы выполняете одиночный запрос тогда используйте первый вариант, он является оберткой над вторым. Второй вариант, с передачей dbExecutor-а, будет полезен если выполнять несколько запросов к БД в рамках одной транзакции.

  2. Получение списка значений:

    List<string> names = new List<string>();

    using (var dbExecutor = UserConnection.EnsureDBConnection()) {

            using (var reader = select.ExecuteReader(dbExecutor)) {

                    while(reader.Read()) {

                            int columnOrdinal = reader.GetOrdinal("Name");

                            names.Add(reader.GetString(columnOrdinal));

                    }

            }

    }

  3. Выполнение запроса в рамках транзакции:

    Оба запроса в базу будут выполнены в рамках транзакции и в случае свала транзакция откатится.

    List<string> names = new List<string>();

    using (var dbExecutor = UserConnection.EnsureDBConnection()) {



    >>      dbExecutor.StartTransaction();

           

            using (var reader = select.ExecuteReader(dbExecutor)) {

                    while(reader.Read()) {

                            int columnOrdinal = reader.GetOrdinal("Name");

                            names.Add(reader.GetString(columnOrdinal));

                    }

            }

            insert.Execute(dbExecutor);



    >>      dbExecutor.CommitTransaction();



    }

    Транзакция начинается вызовом метода dbExecutor.StartTransaction и заканчивается вызовом CommitTransaction или RollbackTransaction. В случае когда выполнение вышло за область видимости блока using и CommitTransaction не был вызван, происходит автоматический откат транзакции. Таким образом нет необходимости оборачивать транзакцию в try/catch блок, т.к. если был свал во время выполнения транзакция автоматически откатится.

    Внимание! В текущей реализации даже если не передавать dbExecutor в метод Execute(), все равно запрос будет выполнен в текущей транзакции, если такая существует. Но для избежания сложностей в будущем, всегда при выполнении нескольких запросов в рамках транзакций - всегда передавайте dbExecutor в методы Execute, ExecuteReader, ExecuteScalar.

Подписаться на обновления этого материала

Показать все комментарии

Создал обьект OpportunityDescription, сохранил, при публикации получаю - Ошибка сохранения: Недопустимое имя объекта "dbo.OpportunityDescription". Смотрел SQL, такой таблицы нет, генерировал исходный код и метаданные для всего, не помогает. Изменил название на ObjData - Ошибка сохранения: Не удалось найти объект "dbo.ObjData", так как он не существует, или отсутствуют разрешения.
В чем может быть дело ?

Нравится

3 комментария

Скорее всего вы столкнулись с ограничением на длину имени таблицы.

Возможно...но почему тогда не получается переименовать ? "Ошибка сохранения: Не удалось найти объект "dbo.ObjData", так как он не существует" ?

Добрый день.

Без отладки тяжело сказать, подобных кейсов не встречали. Попробуйте пересоздать объект с компиляцией после удаления. Вероятно, путаница в метаданных.

Показать все комментарии

Добрый день ! Возникла проблема - перестала грузиться конфигурация, работала, внес изменения на странице, при публикации возникла ошибка: В экземпляре объекта не задана ссылка на объект. После этого все зависло. Закрыл браузер, открыл, зашел на страницу авторизации, ввожу логин\пароль - и все, ничего не происходит, все на месте висит. Другие конфигурации загружаются нормально, в чем может быть дело и можно ли исправить ?

Нравится

1 комментарий

Здравствуйте.
Перед внесением изменений в конфигурацию очень желательно делать резервную копию базы данных. Что бы ответить на вопрос: "в чем может быть дело и можно ли исправить" нужно знать характер внесённых изменений. В идеале отправьте подробнейшее описание ситуации в поддержку.

Показать все комментарии

Добрый день, уважаемые знатоки BPMonline 5.x!
Обращаюсь за советом и идеей.
Есть карточка редактирования, в которой имеется масса контролов. Нужно по факту изменения значения в некотором из них каким-то образом изящно и ненавязчиво привлечь внимание пользователя к тому, что это изменение произошло (если меняем один/несколько реквизитов - непосредственно в карточке есть реестр записей и несколько полей, на которые надо так скажем обратить внимание).

Я так понимаю, что для текста ВНУТРИ поля редактирования TextEdit, FloatEdit параметра цвет нет - было бы здорово сделать текст в них подсвеченным. Также не срабатывает изменение параметра BackColor для них - залить их красивым цветом, как это сделано в обязательных полях тоже было бы вариантом.
Собственно вопрос - можно ли как-то реализовать изменение цвета текста/заливки или придумать что-то еще?
Про MessagePanel я знаю, это запасной вариант. Сообщение во всплывающем окне не хочу, так как задача несколько другая - "подсветить" нужные места карточки.

Нравится

3 комментария

Здравствуйте, Александр!
Можно динамически изменять CSS-стиль контрола. Например, для изменения цвета текста контрола ContactEdit на "LeadEditPage" нужно использовать такой код:

Page.AddScript("PageContainer_ContactEdit.el.dom.style.color = \'blue\'");

По аналогии можно применить любой стиль для любого контрола на странице.
Чтобы вслепую не угадывать имя контрола, можно использовать консоль браузера:

Андрей, спасибо!
Интересный метод, работает.

Кстати, имя контрола можно получить из свойства ClientID:

control_name.ClientID
Показать все комментарии

Возможно глупый вопрос, но BPMonline только изучаю.... Никак не могу понять, как правильно перенести данные из детали одного раздела в деталь другого. А именно - есть Лид, я хочу при квалификации и создании Продажи перенести данные некоторых полей карточки Лида в поля карточки Продажи, но никак не разберусь как это правильно сделать. Гуру, подскажите....

Нравится

3 комментария

Разобрался...внимательнее надо было смотреть на то, что уже есть )

Николай, совет в след. раз объяснять проблему по конкретнее (возможно скрины или куски кода добавить еще), тогда помогут быстрее, а так:
Тема:

"Михайлов Николай" написал:Перенос данных из детали одного раздела в деталь другого

В описании:
"Михайлов Николай" написал:... перенести данные некоторых полей карточки...

Поля карточки и детали - разные вещи. Непонятно, поэтому думаю никто даже не попытался помочь

Прошу прощения, в будущем буду стараться более корректно вопросы формулировать

Показать все комментарии

Добрый вечер, у меня не получаеться открыть страницу после задачи в процесс

DefValuesKey = GetHashCode().ToString();
var parameters = new Dictionarystring, string>();
parameters.Add("defValuesId", DefValuesKey);
UserConnection.UserContext[DefValuesKey] = parameters;
ShowSelectDataWindow.OpenerInstanceId = InstanceUId;
ShowSelectDataWindow.PageParameters = parameters;
ShowSelectDataWindow.PageUId = new Guid("{E8343C66-8488-B471-E040-1AAC3D3ED25C}"); //EnterPeriodWhichRemainsBranchEditPage
ShowSelectDataWindow.CloseMessage= "CloseProcessWindow";
return true;

скриншот тоже прилагаеться, версия BPMOnline 5.1.1.156

Нравится

22 комментария

Здравствуйте, Баглан!
Выгрузите, пожалуйста, процесс и предоставьте файл, а также, опишите, какое окно Вы хотите открыть.

"Андрей Каспаревич" написал:

Здравствуйте, Баглан!

Выгрузите, пожалуйста, процесс и предоставьте файл, а также, опишите, какое окно Вы хотите открыть.

С уважением,

Каспаревич Андрей

Эксперт 3-й линии поддержки


Доброе утро, скидываю файл, сам процесс, страницу, и скриншот страницы

Добре утро!
Спасибо, взял в работу.

Баглан, попробуйите в скрипт перед открытием страницы добавить строки

ShowSelectDataWindow.CloseOpenerOnLoad = false;
ShowSelectDataWindow.UseCurrentActivePage = true;

Также откройте консоль браузера и посмотрите, не возникают ли клиентские ошибки во время открытия страницы.

"Андрей Каспаревич" написал:DefValuesKey = GetHashCode().ToString();
var parameters = new Dictionary();
parameters.Add("defValuesId", DefValuesKey);
UserConnection.UserContext[DefValuesKey] = parameters;
ShowSelectDataWindow.OpenerInstanceId = InstanceUId;
ShowSelectDataWindow.PageParameters = parameters;
ShowSelectDataWindow.PageUId = new Guid("{E8343C66-8488-B471-E040-1AAC3D3ED25C}"); //EnterPeriodWhichRemainsBranchEditPage
ShowSelectDataWindow.CloseMessage= "CloseProcessWindow";
return true;

После этих кодов:

DefValuesKey = GetHashCode().ToString();
var parameters = new Dictionary<string, string>();
parameters.Add("defValuesId", DefValuesKey);
UserConnection.UserContext[DefValuesKey] = parameters;
ShowSelectDataWindow.OpenerInstanceId = InstanceUId;
ShowSelectDataWindow.PageParameters = parameters;
ShowSelectDataWindow.PageUId = new Guid("{E8343C66-8488-B471-E040-1AAC3D3ED25C}"); //EnterPeriodWhichRemainsBranchEditPage
ShowSelectDataWindow.CloseMessage= "CloseProcessWindow";
return true;

этот код:

ShowSelectDataWindow.CloseOpenerOnLoad = false;
ShowSelectDataWindow.UseCurrentActivePage = true;

и результат будет следующим

DefValuesKey = GetHashCode().ToString();
var parameters = new Dictionary<string, string>();
parameters.Add("defValuesId", DefValuesKey);
UserConnection.UserContext[DefValuesKey] = parameters;
ShowSelectDataWindow.OpenerInstanceId = InstanceUId;
ShowSelectDataWindow.PageParameters = parameters;
ShowSelectDataWindow.PageUId = new Guid("{E8343C66-8488-B471-E040-1AAC3D3ED25C}"); //EnterPeriodWhichRemainsBranchEditPage
ShowSelectDataWindow.CloseMessage= "CloseProcessWindow";
 
S<strong>howSelectDataWindow.CloseOpenerOnLoad = false;
ShowSelectDataWindow.UseCurrentActivePage = true;</strong>
return true;

так будет правильно?

Баглан, да. Здесь идет просто установка параметров, так что не принципиально, в каком порядке они будут установлены.

"Андрей Каспаревич" написал:ShowSelectDataWindow

Этот параметр отсутствует UseCurrentActivePage

Баглан, тогда не используйте его.

"Андрей Каспаревич" написал:ShowSelectDataWindow.CloseOpenerOnLoad = false;

Андрей добры день, добавил код просмотрел javaScriptConsole, страница не запустилась ошибку не выдало, высылаю скриншот

Баглан, Вам будет удобно организовать удаленное подключение для скорейшего разрешения проблемы?

"Андрей Каспаревич" написал:

Баглан, Вам будет удобно организовать удаленное подключение для скорейшего разрешения проблемы?

С уважением,

Каспаревич Андрей

Эксперт 3-й линии поддержки


Удаленный доступ есть по vpn, вы можете обратиться Генову Евгений, у него имееться пароли для vpn, как получите напишите мне я доведу до этого шага где открываеться страница.

Баглан, ожидаю упрощенную схему процесса.
В свою очередь, предоставляю стандартную инструкцию по открытию страницы из процесса.


Окно редактирования


Создать Действие процесса (UserTask). Действие = Открыть страницу

Создать скрипт подготовки перед действием и написать в нем следующее:

EntitySchemaUId = Page.DataSource.SchemaUId;
string recordId = Guid.Empty.ToString(); //Id записи
 
UserTaskRunSAObjectEditPage.OpenerPage = Page;
UserTaskRunSAObjectEditPage.OpenerPage = Page;
UserTaskRunSAObjectEditPage.PageUId = EditPageUId; //UID вашей страницы
var parameters = new Dictionary<string, string> {
    {"recordId", recordId.ToString()},
    {"entitySchemaUId", EntitySchemaUId.ToString()}, //UID вашего объекта (не обязательно)
    {"treeGridId", Page.TreeGrid.ClientID}
};
UserTaskRunSAObjectEditPage.PageParameters = parameters;
UserTaskRunSAObjectEditPage.Centered = true;
UserTaskRunSAObjectEditPage.CloseOpenerOnLoad = false;

Открытие простого окна

OpenDetailedPageUserTask.OpenerInstanceId = InstanceUId;
OpenDetailedPageUserTask.UseCurrentActivePage = true;
OpenDetailedPageUserTask.PageUId = EditPageUId;
var parameters = new Dictionary<string, string> {
    {"recordId", "recordId"},
    {"entitySchemaUId", ""},
    {"treeGridId", ""},
    {"SysModuleEditId", ""}
};
OpenDetailedPageUserTask.PageParameters = parameters;
OpenDetailedPageUserTask.Centered = true;
OpenDetailedPageUserTask.CloseOpenerOnLoad = false;

Открытие окна выбора элемента из справочника (с фильтрами)

Создать Действие процесса (UserTask). Действие = Открыть страницу выбора из справочника

Создать скрипт подготовки перед действием и написать в нем следующее:

var SSDocumentOfferingtId = new Guid(SysSettings.GetValue(UserConnection, "SSDocumentOfferingtId").ToString());//UID Объекта
Collection<Dictionary<string, object>> filters = new Collection<Dictionary<string, object>>(); 
filters.Add(new Dictionary<string, object> { 
    {"comparisonType", FilterComparisonType.Equal},
    {"leftExpressionColumnPath", "Document"},
    {"useDisplayValue", false},
    {"rightExpressionParameterValues", new object[] {ParentDocumentSpecificationId}}
});
filters.Add(new Dictionary<string, object> { 
    {"comparisonType", FilterComparisonType.NotEqual},
    {"leftExpressionColumnPath", "IsVsat"},
    {"useDisplayValue", false},
    {"rightExpressionParameterValues", new object[] {true}}
});
filters.Add(new Dictionary<string, object> { 
    {"comparisonType", FilterComparisonType.IsNull},
    {"leftExpressionColumnPath", "[ProductsParts:DocumentOffering].Parent"},
    {"useDisplayValue", false},
    {"rightExpressionParameterValues", new object[] {}}
});
 
OpenSpecOfferingLookupUserTask.ProcessKey = InstanceUId;
OpenSpecOfferingLookupUserTask.PageParameters = new Dictionary<string, object>() {
    {"LookupFilters", filters},
    {"schemaUId", SSDocumentOfferingtId},
    {"customClosedEvent", "SpecOfferingLookupPageClosed"} //Сообщение при закрытии окна
};
OpenSpecOfferingLookupUserTask.UseCurrentActivePage = true;
return true;

Создать скрипт обработки после действия и написать в нем следующее:

var offerings = OpenSpecOfferingLookupUserTask.GetSelectedValues(UserConnection) as Dictionary <string, object>;
var offeringId = Guid.Empty;
foreach (var offering in offerings) {
    offeringId = new Guid(offering.Key.ToString());
    break;
}
if (offeringId == Guid.Empty) {
    return true;
}
return true;

Возможно будет полезно.

"Андрей Каспаревич" написал:

Баглан, ожидаю упрощенную схему процесса.

В свою очередь, предоставляю стандартную инструкцию по открытию страницы из процесса.



Окно редактирования



Создать Действие процесса (UserTask). Действие = Открыть страницу

Создать скрипт подготовки перед действием и написать в нем следующее:

EntitySchemaUId = Page.DataSource.SchemaUId;

string recordId = Guid.Empty.ToString(); //Id записи

 

UserTaskRunSAObjectEditPage.OpenerPage = Page;

UserTaskRunSAObjectEditPage.OpenerPage = Page;

UserTaskRunSAObjectEditPage.PageUId = EditPageUId; //UID вашей страницы

var parameters = new Dictionary<string, string> {

    {"recordId", recordId.ToString()},

    {"entitySchemaUId", EntitySchemaUId.ToString()}, //UID вашего объекта (не обязательно)

    {"treeGridId", Page.TreeGrid.ClientID}

};

UserTaskRunSAObjectEditPage.PageParameters = parameters;

UserTaskRunSAObjectEditPage.Centered = true;

UserTaskRunSAObjectEditPage.CloseOpenerOnLoad = false;

Открытие простого окна

OpenDetailedPageUserTask.OpenerInstanceId = InstanceUId;

OpenDetailedPageUserTask.UseCurrentActivePage = true;

OpenDetailedPageUserTask.PageUId = EditPageUId;

var parameters = new Dictionary<string, string> {

    {"recordId", "recordId"},

    {"entitySchemaUId", ""},

    {"treeGridId", ""},

    {"SysModuleEditId", ""}

};

OpenDetailedPageUserTask.PageParameters = parameters;

OpenDetailedPageUserTask.Centered = true;

OpenDetailedPageUserTask.CloseOpenerOnLoad = false;

Открытие окна выбора элемента из справочника (с фильтрами)

Создать Действие процесса (UserTask). Действие = Открыть страницу выбора из справочника

Создать скрипт подготовки перед действием и написать в нем следующее:

var SSDocumentOfferingtId = new Guid(SysSettings.GetValue(UserConnection, "SSDocumentOfferingtId").ToString());//UID Объекта

Collection<Dictionary<string, object>> filters = new Collection<Dictionary<string, object>>();

filters.Add(new Dictionary<string, object> {

    {"comparisonType", FilterComparisonType.Equal},

    {"leftExpressionColumnPath", "Document"},

    {"useDisplayValue", false},

    {"rightExpressionParameterValues", new object[] {ParentDocumentSpecificationId}}

});

filters.Add(new Dictionary<string, object> {

    {"comparisonType", FilterComparisonType.NotEqual},

    {"leftExpressionColumnPath", "IsVsat"},

    {"useDisplayValue", false},

    {"rightExpressionParameterValues", new object[] {true}}

});

filters.Add(new Dictionary<string, object> {

    {"comparisonType", FilterComparisonType.IsNull},

    {"leftExpressionColumnPath", "[ProductsParts:DocumentOffering].Parent"},

    {"useDisplayValue", false},

    {"rightExpressionParameterValues", new object[] {}}

});

     

OpenSpecOfferingLookupUserTask.ProcessKey = InstanceUId;

OpenSpecOfferingLookupUserTask.PageParameters = new Dictionary<string, object>() {

    {"LookupFilters", filters},

    {"schemaUId", SSDocumentOfferingtId},

    {"customClosedEvent", "SpecOfferingLookupPageClosed"} //Сообщение при закрытии окна

};

OpenSpecOfferingLookupUserTask.UseCurrentActivePage = true;

return true;Создать скрипт обработки после действия и написать в нем следующее:

var offerings = OpenSpecOfferingLookupUserTask.GetSelectedValues(UserConnection) as Dictionary <string, object>;

var offeringId = Guid.Empty;

foreach (var offering in offerings) {

    offeringId = new Guid(offering.Key.ToString());

    break;

}

if (offeringId == Guid.Empty) {

    return true;

}

return true;

Возможно будет полезно.

С уважением,

Каспаревич Андрей

Эксперт 3-й линии поддержки

Андрей я перепробовал все, высылаю простой тестовый процесс, если у вас получиться буду рад,спасибо

Баглан, жду Вашего решения по поводу удаленного доступа.

"Андрей Каспаревич" написал:

Баглан, жду Вашего решения по поводу удаленного доступа.

С уважением,

Каспаревич Андрей

Эксперт 3-й линии поддержки


Андрей я скинул вам на корп почту, прошу посмотерть.

"Бахгельдиев Баглан Абылаевич" написал:
Андрей Каспаревич пишет:

Баглан, жду Вашего решения по поводу удаленного доступа.

С уважением,

Каспаревич Андрей

Эксперт 3-й линии поддержки

Андрей я скинул вам на корп почту, прошу посмотерть.

Андрей я получил ваше сообщение вчера сервер не был доступен, прошу сегодня попробовать подключиться

Спасибо, Баглан!
Сегодня попробуем.

"Андрей Каспаревич" написал:

Спасибо, Баглан!

Сегодня попробуем.

С уважением,

Каспаревич Андрей

Эксперт 3-й линии поддержки

Добрый день, Андрей удалось проблему исправить? вы обещали проблему посмотреть и написать мне, но отвас я так и не получил письма

Здравствуйте, Баглан!
Данное обращение находится в работе в департаменте разработки.
Пока что никаких результатов нет.

"Андрей Каспаревич" написал:

Здравствуйте, Баглан!

Данное обращение находится в работе в департаменте разработки.

Пока что никаких результатов нет.

С уважением,

Каспаревич Андрей

Эксперт 3-й линии поддержки

Здравствуйте Андрей, а когда будут результаты? уже 2-3 месяца прошел.

Баглан, в связи с высокой трудоемкостью процесса воспроизведения и поисков причины возникновения ошибки, не хватает времени и ресурсов для решения проблемы.
Возможно, на следующей неделе получится получить результаты.

Показать все комментарии

Друзья, подскажите как мне про администрировать раздел "Единое окно"

Нравится

4 комментария

Владимир, если Вы имеете ввиду настроить доступ пользователей к разделу, то в базовой версии это не предусмотрено.
Но можно добавить или удалить "Единое окно" из рабочего места, это можно настроить в разделе "Рабочие места".

Андрей, спасибо за быстрый ответ.

И еще есть вопрос:
не могу скрыть раздел Журнад процесов.

Владимир, скрыть раздел можно удалив его регистрацию из таблицы [SysModuleInSysModuleFolder] скриптом

delete from SysModuleInSysModuleFolder where sysmoduleId = (select Id from SysModule where Caption = 'Журнал процессов')

Другим решением было бы удалить его из рабочего места, но так как больше не останется экземпляров, раздел удалится полностью, что нежелательно. Поэтому рекомендую использовать скрипт.

спасибо еще раз, Андрей. Но разобрался сам.

"крыть раздел можно удалив его регистрацию из таблицы [SysModuleInSysModuleFolder] скриптом" - это плохой вариант.

удалось это сделать запретив доступ к разделу Процесы

Показать все комментарии

Добрый день.
Возникла проблема по перехвату закрытия пользователем окна "крестиком" в бизнес процессе.
Вопрос, как реализовать этот перехват и пустить процесс по другой ветке?

Нравится

6 комментариев

Илья, при закрытии окна "крестиком" бизнес-процесс прерывается. Продолжить выполнение бизнес-процесса возможно из раздела "Журнал процессов".

Возможно, для решения Вашей задачи подойдет элемент "Вопрос пользователю"?

Например, задается вопрос пользователю: "Открыть карточку редактирования контакта?". Если пользователь нажимает "Да" - процесс идет по одной ветке. Если пользователь нажимает "Нет" - по другой.

Роман, как раз нужно избавится от варианта "Журнал процессов", и закрытие "крестиком" должно приравнятся к нажатию кнопки "отмена".

Илья, в таком случае необходимо получать от клиента событие закрытия окна и писать обработчик этого события для бизнес-процесса.

В базовой логике такого функционала не предусмотрено, такие события, как закрытие окна не обрабатываются в бизнес-процессе.

Вот как раз это я и хочу сделать.
Вопрос: в какую сторону смотреть на получение события о закрытии окна?
Общая идея, предотвратить остановку процесса в случае закрытия пользователем окна по крестику. (задача, вопрос пользователю и т.д.)

Можно попробовать создать в конфигуарции схему «исходный код», которая будет ловить клиентское нажатие на крестик.

namespace Terrasoft.Configuration
{
    public static class Alert
    {
                public static string RenderScript() {
                          return @"window.onbeforeunload = closingCode;
function closingCode(){
   alert(\"Нажат крестик!\"");

Код "window.onbeforeunload = closingCode" передбачає закриття вікна взагалі.
Там буде і [x], і [OK], і [Cancel].

Отже такий варіант не підійде, бо доведеться повністю переписувати обробку кнопок.

Показать все комментарии

Пытаюсь на странице прятать\показывать группу элементов. Collapse true\false не помогает, не разворачивается почему-то. Прятать\показывать элементы тоже ерунда, как показываю - все наезжают друг на друга. Есть какой-нибудь способ это сделать ?

Нравится

17 комментариев

Здравствуйте, Михаил!
Подскажите, каким образом Вы меняете значение свойства Collapse?

По изменению значения одного из полей устанавливаю Page.ControlLayout.Collapse = false

Михаил, для динамического изменения свойств контрола необходимо использовать функцию Page.ScriptManager.AddScript(). Например,

function onCountryChange(object sender, EventArgs e) {
    Guid countryUId = Page.CountryLookupEdit.Value;
    Guid sityUId = Page.GetCaptitalByCountryUId(countryUId);
    Page.CapitalLookupEdit.SuspendAjaxEvents(); // Отключаем стандартную обработку событий на сервере   
    Page.AddScript(string.Format("{0}.setValue('{1}')", Page.CapitalLookupEdit.ClientID, Json.Serialize(sityUId)));
    Page.CapitalLookupEdit.ResumeAjaxEvents(); // Восстанавливаем стандартную обработку событий на сервере
}

Написал по аналогии с примером.
Page.ControlLayoutRealty.SuspendAjaxEvents();
Page.AddScript(string.Format("{0}.setValue('{1}')",
Page.ControlLayout.Collapse, Json.Serialize(false)));
Page.ControlLayoutRealty.ResumeAjaxEvents();

Получаю ошибку : Terrasoft.UI.WebControls.Controls.ControlLayout не содержит определение для "Collapse" и т.д.....
Что я не так делаю ?....

Исправил на
Page.ControlLayoutRealty.SuspendAjaxEvents();
Page.AddScript(Page.ControlLayout.ClientID + ".Collapsed=false");
Page.ControlLayoutRealty.ResumeAjaxEvents();
ошибок нет, но группа не разворачивается

Михаил, думаю нужно использовать первый вариант, в котором Вы допустили опечатку:

Page.ControlLayout.Collapse, Json.Serialize(false)));

в Collapse. Должно быть Collapsed.
Также попробуйте убрать строки

Page.ControlLayoutRealty.SuspendAjaxEvents();
 
Page.ControlLayoutRealty.ResumeAjaxEvents();

Использовал
Page.AddScript(string.Format("{0}.setValue('{1}')",
Page.ControlLayout.Collapsed, Json.Serialize(false)));
ошибок нет, но и не работает. Внутри этой группы есть еще две - с этим может быть связано ?
Сейчас по умолчанию на группе ControlLayout и двух вложенных стоит галка на пункте Свернуть.
Соответственно по событию прописываю для каждой группы Page.ControlLayout.Collapsed, Json.Serialize(false). Но ничего не происходит, разворачиваться не хотят.

Михаил, каждый контрол на странице доступен по уникальному идентификатору, который формируется так: "PageContainer_страницаНаКоторойРасположенКонтрол_ИмяКонтрола".
Для управления свойством Collapsed используются методы collapse(), expand() и toggleCollapse().
Пример сворачивания для ControlLayout, который расположен на AccountsModulePage:

Page.AddScript("PageContainer_AccountsModulePage_ControlLayout1.collapse();"); 

Также у ControlLayout есть свойство "Отображать кнопку сворачивания", которое также можно использовать для сворачивания.

Написал :
Page.AddScript("PageContainer_LeadEditPage_ControlLayoutRealty.expand();");
ControlLayoutRealty по умолчанию свернут, название страницы LeadEditPage.
Не разворачивает все равно.

Михаил, попробуйте еще так. На EditPage контролы могут быть просто в PageContainer

Page.AddScript("PageContainer_ControlLayoutRealty.expand();");

Если не получится добавьте команду debugger:

Page.AddScript("debugger");

Тогда можно будет в консоли браузера посмотреть название контрола, например:

Спасибо за помощь !
Использование PageContainer_ControlLayoutRealty помогло частично - теперь, если по умолчанию контрол развернут, то сворачивается, но не разворачивается обратно.

Михаил, а какую функцию Вы используете?

Действие на событие Значение изменено контрола. Далее в дизайнере процессов задание-сценарий :

if (Page.LookupEdit1.Value.ToString() == "c7046958-ef32-459a-be31-2bf591fd940c") {
Page.AddScript("PageContainer_ControlLayoutRealty.expand();");
Page.AddScript("PageContainer_ControlLayout13.expand();");
Page.AddScript("PageContainer_ControlLayout14.expand();");
} else {
Page.AddScript("PageContainer_ControlLayoutRealty.collapse();");
Page.AddScript("PageContainer_ControlLayout13.collapse();");
Page.AddScript("PageContainer_ControlLayout14.collapse();");
}
return true;
Соответственно сворачивание отрабатывается, а вот разворачиваться - никак.

Михаил, проблема в условии. Для сравнения с Guid лучше использовать приведение типов. Во-первых, проверьте, что возвращает Page.LookupEdit1.Value (тот ли Guid, с которым идет сравнение).
Во-вторых, попробуйте использовать такое сравнение:

if ((Guid)Page.LookupEdit1.Value == new Guid ("c7046958-ef32-459a-be31-2bf591fd940c"))

Что интересно, условие срабатывает, я для контроля меняю текстовое поле, но сворачивание идет, а разворачивание - нет.

Михаил, тогда сложно сказать, в чем причина.
Попробуйте еще использовать toggleCollapse() для проверки работоспособности.
Если проблема не решится, можно организовать удаленное подключение для анализа и исправления.

Ок, попробую, спасибо

Показать все комментарии