Симптомы

Bpm'online mobile bug report

Type: Terrasoft.SourceCodeException

Message: TypeError: undefined is not an object (evaluating 'columnConfig.columnType')

Причина

Ошибка возникает из-за того, что Вы не верно настроили параметры встроенной деталей, например, в разделе «Объекты».

Изображение удалено.

Рис. 1

 Изображение удалено.

Рис. 2

Решение

Для решения необходимо корректно настроить все детали.

Например, как настроить деталь «Файлы и примечания» в разделе «Лиды»:

- Для отображения в мобильном приложении необходимо выбрать деталь «Файлы и ссылки Лида»

- В поле «Колонка детали» указать «Лид»

- В поле «Колонка объекта Лид» указать «Id»

Также как примеры можно посмотреть как реализованы детали в других разделах.

Следует обратить внимание, что в результате данная деталь будет работать в основном для отображения названия файлов и работы с веб-ссылками.

Например, Вы может попробовать следующие настройки детали:

 Изображение удалено.

Рис. 3

Изображение удалено.

Рис. 4

Нравится

Поделиться

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

Вопрос:

Создал процесс для перемещения сотрудников (объектов обслуживания) из одного сервисного договора в другой по содержанию строки «адрес».

В результате выполнения этого БП "Объекты обслуживания" попали в "Сервисный договор", но при создании нового обращения нельзя выбрать этот Сервисный договор, который был изменен БП.

Ответ:

Такой БП не предусматривает один момент, а именно: когда БП добавляет "Объект обслуживания", то не заполняет "Тип".

Как это увидеть?

1. Зайдите в Справочники

2. Нажмите "ДОБАВИТЬ СПРАВОЧНИК"

3. В "Объект" выберете "Объект обслуживания" в "Название" тоже пропишите "Объект обслуживания" и сохраните.

4.Появился справочник "Объект обслуживания", откройте его.

5. Через ВИД - Настроить колонки отобразите колонки : Контакт, Сервисный договор, Тип

6. Посмотрите, что у тех, контактов, которых сюда добавили бизнес процессом не заполнено поле "Тип".

Это и есть причина, по которой при создании обращения не подтягивается "Сервисный договор". Необходимо заполнить по всем "Тип" = "Контакт".

Можно просто выгрузить объекты обслуживания в Excel, заполнить и загрузить назад. Так будут исправлены те контакты. которые уже ранее добавили при помощи БП.

Нравится

Поделиться

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

Вопрос

Как можно такое сделать? Нужно поместить кнопку под одним из полей или сбоку, по нажатию на которую открывался бы реестр справочника.

Мне нужно открывать справочник, не связанный со страницей, и перед этим ещё могут потребоваться доп. действия. Просто справочным полем не получится это реализовать.

Есть возможность поместить кнопку именно где-то посреди страницы? Действие для пользователя будет довольно неудобным. Или это принципиально невозможно?

Коммьюнити - https://community.terrasoft.ru/questions/dobavit-knopku-na-stranicu-redaktirovania-v-mobilnom-prilozenii

Ответ

Можете посмотреть алгоритм реализации в похожем топике: https://community.terrasoft.ru/questions/dobavlenie-kastomnyh-elementov-v-mobilnom-prilozenii

Например, в конфиге вью определяем нужный контрол + метод для его отображения, а в контроллере завязываем на него обработчик:

Ext.define("...вью...", {
    config: {
       refreshButton: {
            id: 'usr_order_refresh_btn',
            cls: "x-button-primary-blue",
            text: 'Обновить'
        }
    },
    showRefreshButton: function (isShow) {
        var navigationPanel = this.getNavigationPanel(); /*компонент в котором нужно отобразить контрол*/
        var refreshButton = this.getRefreshButton();
        if (isShow) {
            this._refreshButton = navigationPanel.addButton(refreshButton);
        } else {
            navigationPanel.removeButton(refreshButton);
        }
        return this._refreshButton;
    }
});
Ext.define("...контроллер...", {
    initializeView: function (view) {
        this.callParent(arguments);
        var btn = view.showRefreshButton(true);
        btn.on("tap", this.onRefreshButtonTap, this);
    },
    onRefreshButtonTap: function() {
        /* сабж */
    }
});

Если нужно открыть пикер для выбора значения, то посмотрите MobileActivityGridPageControllerV2. Там много пример открытия пикеров. Например, для выбора «Ответственного» (метод getEmployeePicker()

) или выбора режима расписания (метод getGridModePicker()).

Нравится

Поделиться

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

Вопрос

Кейс:

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

Входе анализа выяснилось, что основной тип файлов это изображения, которые присутствуют в подписи писем (имеют название «image»).

Можно ли настроить так фильтрацию, чтобы мобильное приложение не затягивало лишние файлы?

Ответ

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

Добавить в манифест мобильного приложения (MobileApplicationManifestDefaultWorkplace) следующий код:

{
    "SyncOptions": {
        "SysSettingsImportConfig": [],
        "ModelDataImportConfig": [
            {
                "Name": "ActivityFile",
                "SyncFilter": {
                    "property": null,
                    "valueIsMacros": false,
                    "value": null,
                    "isNot": true,
                    "type": "Terrasoft.FilterTypes.Group",
                    "logicalOperation": "Terrasoft.FilterLogicalOperations.Or",
                    "subfilters": [
                        {
                            "property": "Name",
                            "funcType": "Terrasoft.FilterFunctions.SubStringOf",
                            "funcArgs": ["image"] //по какому слову не будут попадать значения
                        },
                        {
                            "property": "Activity.Owner",
                            "isNot": true,
                            "valueIsMacros": true,
                            "value": "Terrasoft.ValueMacros.CurrentUserContact"
                        }
                    ]
                }
            }
        ]
    },
    "Modules": {},
    "Models": {}
}

Если это продукт FieldForce, то также необходимо добавить этот же код в манифест "MobileApplicationManifestFieldForceWorkplace".

Нравится

Поделиться

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

Вопрос

Как сделать все элементы детали Адреса на странице Контрагента недоступными для редактирования? Версия 7.2.0.

Ответ

Пример реализации функционала для схемы AddressDetail:

1) можно добавить новый метод enableDetailControls:

this.methods.enableDetailControls = function(viewConfig, enabled) {
    if (!viewConfig.items) {
        return;
    }
    viewConfig.items.forEach(function(item) {
        item.enabled = enabled;
    }, this);
};

2) далее вызвать этот метод внутри метода getCustomItemView после полного формирования конфигурации представления, добавив необходимые условия. Например, перед строкой return viewConfig:

this.methods.getCustomItemView = function(viewModel, itemKey, action, types, itemViewModel) {
    var viewConfig = {};
    ...
    var enableControls = (action === "edit") && (/*любые другие условия*/);
    this.enableDetailControls(viewConfig, enableControls);
    return viewConfig;
};

Очень желательно до этого момента уже получить значения необходимых условий, так как после выполнения getCustomItemView управление передаётся в модуль базовой детали (DetailModule), в котором уже выполняется привязка модели к представлению и рендеринг детали.

Нравится

Поделиться

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

Вопрос

OData. Как передать параметр со значением NULL

Ответ

PUT http://e-podkovka:9848/0/ServiceModel/EntityDataService.svc/ContactCollection(guid'40f52013-48df-4009-b492-20794e6cb313')HTTP/1.1
Accept: application/atom+xml
Content-Type: application/atom+xml;type=entry;
Host: e-podkovka:9848
Content-Length: 448
Expect: 100-continue
Connection: Keep-Alive
Cookie: BPMSESSIONID=fahxnyitfahzhiryyqwx15fx; BPMLOADER=r543kelbmnri2mqivvfb5opj; .ASPXAUTH=8511A66857D2D6371FD2E76B7FB7EF2FADBC44C2E7E7D7B802171CDE3A12BF4DEB539193184F19DEEA2C9EF01B91DB2B7057748DB8BA843A7264501446C19936C63BD84AEC1E879AAD0FF24194163974B17967E5F9775ADFBD0020EC0E7D89D9E87259680E35183507555DCBF3824C2C25A1ADB44D502FBABF6F7037BC56A35DD574C85D74C0234159ABD87FC6A5E1E280B0F9137DF527A9A66854FE943E4B65E8B9E61AA6190FAB804970BC7B85A1B695528809C35B46D491D942FAC3ECE31635D29FB60481E852FF397F52C4F8AF42E4B8D3582293761C35A32B7F2D7F518D2D1E6F48BB7C1F54BF2EFE584D8FA84C9EA0EF97FAEAD656FCD2C0D48B81884A61EA26D21CC5ED5D96938370BC10B6CE6AEE62867690600013591F1A8D85C9C05CCC0660D6FE2254C7690FC7D4FD6CFF096DD56E98A0C42515BD19B37A25806BD619581FB6F966D30EB4E19EE03AA2D9883F2230C0221E9C3A61743F747F2307E2B5AE25; UserName=83|117|112|101|114|118|105|115|111|114
 
<?xml version="1.0" encoding="utf-8"?>
<entry xmlns="http://www.w3.org/2005/Atom">
<content type="application/xml">
<properties
xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices"
xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata"
xmlns="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata">
<d:Name>New name4</d:Name>
<d:JobId m:null="true" />
</properties>
</content>
</entry>

 

Нравится

Поделиться

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

Вопрос

Как установить значение для активной записи из модуля раздела в режиме редактирования (вертикальный реестр)

Ответ

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

var activeRow = this.getActiveRow();
activeRow.set("YourColumnName", columnValue);
activeRow.saveEntity();

Для работы этого кода необходимо, чтобы в коллекции activeRow.columns была колонка с названием YourColumnName и типом Terrasoft.ViewModelColumnType.ENTITY_COLUMN (данная константа равняется 0).

Также обновление значения можно выполнить через запрос примерно так:

var updateQuery = this.Ext.create("Terrasoft.UpdateQuery"{
        rootSchemaName: "EntitySchemaName"
});
var filters = updateQuery.filters;
filters.addItem(this.Terrasoft.createColumnFilterWithParameter(
        this.Terrasoft.ComparisonType.EQUAL"Id", currentRecordId));
updateQuery.setParameterValue("YourColumnName", columnValue);
updateQuery.execute(callbackFunction, this);

 

Нравится

Поделиться

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

Вопрос

Как открыть MainHeaderExtensions в консоли для дебага? 

Ответ

Если версия 7.5 и выше, то для отладки схемы «MainHeaderExtensions» необходимо в консоли браузера (Ctrl+O) открыть схему «ConfigurationBootstrap»  (представляет из-за себя комплекс схем, которые минимально используются в приложении).

Если версия до 7.5, то открыть нужно схему в консоли «MainHeaderExtensions».

Нравится

Поделиться

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

Вопрос

Метод getEntity класса EntitySchemaQuery работает асинхронно. Можно ли сделать так, чтобы метод getEntity работал синхронно?

Ответ

Метод getEntity клиентской EntitySchemaQuery рассчитан только на асинхронное использование. Тем не менее, можно имитировать синхронное поведение с помощью Terrasoft.chain.

Выглядит это так:

getMyEntity: function(callback) {
    var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", {
        rootSchemaName: schemaName
    });
    ...
    esq.getEntity(recordId, function(response) {
        ...
        if (callback) {
            callback.call(this);
        }
    }, this)
},
globalMethod: function() {
    Terrasoft.chain(
        function(next) {
            this.getMyEntity(function() {
                next();
            });
        },
        function() {
            this.doAfterGettingEntity();
        },
        this
    );
}

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

Terrasoft.chain может содержать сколько угодно аргументов. Важно не забывать указывать в аргументах next, чтобы цепочка не прервалась раньше времени. Последним аргументом передается контекст выполнения.

Нравится

Поделиться

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

Вопрос

Я создал деталь [Документы водителя], схема UsrSchema6Detail, в разделе [Контакты]. Мне необходимо показывать ее если выбрана должность [Водитель]. Если должность не выбрана или выбрана другая, то деталь скрыта.

Я добавил бизнес правило в схему контакты, оно не работает.

rules: {
   "UsrSchema6Detail": {
      BindParametrVisibilePlaceByType: {
         // Тип правила BINDPARAMETER.
         ruleType: BusinessRuleModule.enums.RuleType.BINDPARAMETER,
         // Правило регулирует свойство VISIBLE поля.
         property: BusinessRuleModule.enums.Property.VISIBLE,
         conditions: [{
            // Выражение левой части условия.
            leftExpression: {
               //Тип выражения ATTRIBUTE указывает на то, что в качестве выражения выступает
               // аттрибут (колонка) модели представления.
               type: BusinessRuleModule.enums.ValueType.ATTRIBUTE,
               // Название колонки модели представления, значение которой сравнивается в выражении.
               attribute: "Job"
            },
            // Тип операции сравнения.
            comparisonType: Terrasoft.ComparisonType.EQUAL,
            // Выражение правой части условия.
            rightExpression: {
               type: BusinessRuleModule.enums.ValueType.CONSTANT,
               value: "703e34d6-4113-43b5-84dc-2e1f8635c6d4"
            }
         }]
      }
   }
}

Если я применяю это же правило к колонке [Департамент], то оно работает так как надо. 

Ответ

Для решения Вашей бизнес задачи использование бизнес правил не подходит.

Вот пример кода для скрытия детали [Средства связи] на карточке редактирования [Контрагента].

Создаете замещающий модуль AccountPagev2, в секции diff добавляете следующий код:

{
    "operation": "merge",
    "name": "Communications",
    "values": {
        "visible" : {
            "bindTo": "communicationsVisibility"
        }
    }
}

Объявляете метод отвечающий за видимость детали в секции methods:

communicationsVisibility: function(){
    var type = this.get("Type");
    return !!type && type.displayValue === "Наша компания";
}

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

Нравится

Поделиться

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