Вопрос

На детали Email отображаются записи других типов активностей.

Ответ

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

define("EmailDetailV2", ["terrasoft", "ProcessModuleUtilities", "ConfigurationConstants"],
    function(Terrasoft, ProcessModuleUtilities, ConfigurationConstants) {
        return {
            /**
            * Имя схемы объекта
            * @type {String}
            */
            entitySchemaName: "Activity",
            messages: {},
            attributes: {},
            methods: {
                getFilters: function() {
                    var parentfilters = this.callParent(arguments);
                    parentfilters.add(
                        "EmailFilter",
                        this.Terrasoft.createColumnFilterWithParameter(
                            this.Terrasoft.ComparisonType.EQUAL,
                            "Type",
                            ConfigurationConstants.Activity.Type.Email
                        )
                    );
                    return parentfilters;
                }
            },
            diff: /**SCHEMA_DIFF*/[]/**SCHEMA_DIFF*/
        };
});

 

Нравится

Поделиться

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

Вопрос

Как скрыть поле с детали "Средства связи"

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

Ответ

Данный вопрос необходимо решать на уровне конфигурации.

Рассмотрим реализацию на примере.

Кейс:

необходимо скрыть поле «E-mail» из секции «Запрет на использование» в разделе «Контакты».

Решение:

  1. Необходимо заместить схему (Управление конфигурацией – Конфигурация – кнопка «Добавить» - пункт «Замещающий клиентский модуль»).
  2. В открывшимся окне в поле «Родительский объект» указать «Средства связи контакта (устаревшая версия)» (Рис. 1).

ВАЖНО. Необходимо использовать устаревшую версию схемы «Средства связи».

    3. В замещающую схему вставить следующий код:

define("ContactCommunicationDetail", ["ContactCommunicationDetailResources", "terrasoft"],
    function(resources, Terrasoft) {
        return {
            entitySchemaName: "ContactCommunication",
            methods: {
                /**
                * Возвращает запреты на использование.
                * @protected
                * @return {Object} Объект, который содержит свойства запретов на использование.
                */
                getRestrictions: function() {
                    return {
                        "DoNotUseEmail": { /*Не использовать E-mail*/
                            "RestrictCaption": this.get("Resources.Strings.DoNotUseEmail"),
                            "Caption": this.get("Resources.Strings.DoNotUseEmailCaption")
                        },
                        "DoNotUseCall": { /*Не использовать телефон*/
                            "RestrictCaption": this.get("Resources.Strings.DoNotUseCall"),
                            "Caption": this.get("Resources.Strings.DoNotUseCallCaption")
                        },
                        "DoNotUseSms": { /*Не использовать SMS*/
                            "RestrictCaption": this.get("Resources.Strings.DoNotUseSms"),
                            "Caption": this.get("Resources.Strings.DoNotUseSmsCaption")
                        },
                        "DoNotUseFax": { /*Не использовать факс*/
                            "RestrictCaption": this.get("Resources.Strings.DoNotUseFax"),
                            "Caption": this.get("Resources.Strings.DoNotUseFaxCaption")
                        },
                        "DoNotUseMail": { /*Не использовать почту*/
                            "RestrictCaption": this.get("Resources.Strings.DoNotUseMail"),
                            "Caption": this.get("Resources.Strings.DoNotUseMailCaption")
                        }
                    };
                }
            },
            diff: /**SCHEMA_DIFF*/[]/**SCHEMA_DIFF*/
        };
    });

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

Рис. 1

4. Затем выделяем с помощью компьютерной мышки часть кода, которая изображен на рисунке 2 (начиная от названия "DoNotUseEmail" и заканчивая }, ).

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

Рис. 2

5. В итоге должно выглядеть как рисунке 3. Затем мы сохраняем схему.

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

Рис. 3

6. Затем очищаем кэш браузера и проверяем результат.

 7. В результате поле "E-mail" не отобразиться (Рис. 4).

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

Рис. 4

Примечание. Скрытие других полей или реализация в разделе «Контрагенты» происходит аналогичным путем. 

Нравится

Поделиться

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

Вопрос

Каким образом можно хранить URL (в каком поле) и как возможно (если это возможно в принципе) сделать так, чтобы на форме это поле стало "кликабельным"?

Ответ

URL можно хранить в текстовом поле.

Основные нюансы реализации описаны в ответе на комьюнити: http://www.community.terrasoft.ru/forum/topic/9686#comment-54881

Для поля необходимо добавить следующие свойства в свойство values элемента массива diff:

"showValueAsLink": true,
"href": {
        "bindTo": "UsrFieldName",
        "bindConfig": {"converter": "getUsrFieldNameLink"}
},
"controlConfig": {
        "className": "Terrasoft.TextEdit",
        "linkclick": { bindTo: "onUsrFieldNameLinkClick"}
}

Где UsrFieldName - название поля, которое мы хотим отображать как гиперссылку.

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

getUsrFieldNameLink: function(value) {
    return {
        "url": value,
        "caption": value
    };
},
onUsrFieldNameLinkClick: function(url) {
    if (url != null) {
        window.open(url, "_blank""height=" + this.get("WindowHeight") + ",width=" + this.get("WindowWidth"));
        return false;
    }
}

Необходимо также следить за тем, чтобы значение данного поля начиналось с http или https, иначе система будет добавлять к содержимому путь к приложению. Можно также анализировать значение входящего параметра value в первом методе и в случае необходимости добавлять эту приставку.

Полный пример элемента diff:

{
    "operation": "insert",
    "name": "UsrURLpage22872546-f334-4b46-a445-112b532455c4",
    "values": {
        "layout": {
            "colSpan": 12,
            "rowSpan": 1,
            "column": 0,
            "row": 3,
            "layoutName": "Header"
        },
        "labelConfig": {},
        "enabled": true,
        "bindTo": "UsrURLpage",
        "showValueAsLink": true,
        "href": {
            "bindTo": "UsrURLpage",
            "bindConfig": {"converter": "getUsrURLpageLink"}
        },
        "controlConfig": {
            "className": "Terrasoft.TextEdit",
            "linkclick": { bindTo: "onUsrURLpageLinkClick"}
        }
    },
    "parentName": "Header",
    "propertyName": "items",
    "index": 6
}

 

Нравится

Поделиться

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

Вопрос

Мобильное приложение.

Интересует вопрос по настройке порядка отображения заказов в мобильном приложении.

Список заказов не отображается в нужной последовательности. Как следует настроить приложение, чтобы шла последовательность по дате регистрации? И вначале (сверху) показывался последний заказ?

 В чём была причина хаотичного расположения заказов?

Ответ

Для сортировки по определенной колонке необходимо в манифеесте прописать дополнительно логику.

Пример:

Terrasoft.sdk.GridPage.setOrderByColumns("Order", {
    column: "CreatedOn",
    orderType: Terrasoft.OrderTypes.DESC
});

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

Ниже пример:

 

- добавляет объект «UsrTestOrderMobile» с нужными колонками 

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

- регистрируем деталь в мастере деталей;

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

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

- далее нам необходимо настроить сортировку. Создаем новую клиентскую схему, например, «UsrMobileUsrTestOrderMobileModuleConfig» с необходимым кодом:

 

Terrasoft.sdk.GridPage.setOrderByColumns("UsrTestOrderMobile", {
    column: "UsrName",
    orderType: Terrasoft.OrderTypes.DESC
});

- сохраняем изменения;

- подключаем в манифест в секции «Models» нужного объекта детали в «PagesExtensions»

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

- очищаем кэш и заново синхронизируется (чтобы получить актуальные настройки) и проверяем.

 

Важные моменты:

- убедиться, что в настройках импорта (ModelDataImportConfig) синхронизируете все необходимые колонки

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

- была первичная колонка (которая используется в сортировке) для отображения в объекте либо на уровне кода (ниже пример):

 

Terrasoft.sdk.GridPage.setPrimaryColumn("UsrTestOrderMobile", "UsrName");

Terrasoft.sdk.RecordPage.addColumn("UsrTestOrderMobile", {

        name: "UsrName",

        position: 1

    }, "primaryColumnSet");

 

Проверили на последней сборке 7.11.3 и все работает корректно.



Также используйте следующую документацию:

https://academy.terrasoft.ru/documents/technic-sdk/7-11/manifest-mobilnogo-prilozheniya;

https://academy.terrasoft.ru/documents/technic-sdk/7-11/kak-dobavit-polzovatelskiy-razdel-v-mobilnoe-prilozhenie;

https://academy.terrasoft.ru/documents/technic-sdk/7-11/sdk-reestra.

Нравится

Поделиться

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

Кейс

Добавил кастомное поле «Проект» в Активность, которое является обязательным.

Из за этого не могу теперь внеси Активность через мобильное приложение.  Можно ли это исправить оставив поле «Проект» обязательным?

Причина

Настройка полей в меню [Мастер мобильного приложения] для разделов Активности/Контрагенты работает некорректно. Исправлено в последних релизных версиях.

Цель

Добавить пользовательское поле в раздел Активность для мобильного приложения.

Необходимые условия

Доступ в систему с правами администратора.

Выполнение

1. Обновить систему до последней релизной версии, выпущенной после 01.05.2015.

2. В [Мастер мобильного приложения] настроить соответствующие колонки.

В настройке мобильного приложения важно:

1. Сохранить изменение на странице раздела.

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

2. Сохранить изменения для мобильного приложения в целом.

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

 3. Выполнить повторную синхронизацию.

Нравится

Поделиться

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

Основные причины потери производительности:

  1. IIS
  2. Процесс приложения
  3. SQL
  4. Redis
  5. Сеть

1. Приложение может виснуть от превышения количество запросов в очереди (по умолчанию 1000).

2. Проверить загруженность системы (ЦП и память). Процесс W3wp. Утилиты DotMemory, DotTrace и др.

3. Проверка выполнения скорости запросов в БД.

В профайлере настроить по условию время выполнения больше 2000 мс, так как большая часть запросов выполняются очень быстро можно отсеять только те, что могут тормозить наше приложение. Также можна проверить выполнение запросов напрямую в БД. Может быть проблема с индексами или не оптимизирован запрос.

4. Проверить Редис. При достаточно больших объёмах данных и неправильное работы, редис часть данных сохраняет на диск. Очевидным становится проблема медленных дисков, ибо при не нахождении в оперативной памяти начинает искать на медленном диске.

5. Проверка сети. С помощью утилит посылать пакеты разных размеров и следить за временем ответа сервера. Если ответы слишком долгие, то нужно смотреть.

Нравится

Поделиться

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

Симптомы

Вопрос по обработке часовых поясов.

В карточке торговой точки есть поля "Воемя доставки от" и "Время доставки до" с типом Время. При создании точки на планшете ставим в них 17:00 и 18:00, в базу они синхронизируются как 14:00 и 15:00. Более того, после синхронизации и на планшете в этих полях оказываются значения 14:00 и 15:00.

В интерфейсе веб-версии они тоже видны как 14:00 и 15:00

Причина

Исправлено в версии 7.8 

Решение

Ниже предоставлен фикс, исправляющие проблему без переноса серверных изменений 7.8 по часовым поясам.

 

Порядок действий следующий:

 

- создать схему UsrSyncExtension (тип «Модуль») в пользовательском пакете;

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

- добавить в нее следующий код:

 

var sysAdminUnitStore = Ext.create("Ext.data.Store", {model: "SysAdminUnit"});
sysAdminUnitStore.setProxy("odata");
sysAdminUnitStore.load({
    queryConfig: Ext.create("Terrasoft.QueryConfig", {
        modelName: "SysAdminUnit",
        autoSetProxy: false,
        columns: ["TimeZoneId"]
    }),
    filters: Ext.create("Terrasoft.Filter", {
        property: "Contact",
        value: Terrasoft.CurrentUserInfo.contactId
    }),
    callback: function(records, operation, success) {
        if (success === true && records.length > 0) {
            var firstRecord = records[0];
            var timeZoneCode = firstRecord.get("TimeZoneId");
            if (!Ext.isEmpty(timeZoneCode)) {
                var timeZoneStore = Ext.create("Ext.data.Store", {model: "TimeZone"});
                timeZoneStore.setProxy("odata");
                timeZoneStore.load({
                    queryConfig: Ext.create("Terrasoft.QueryConfig", {
                    modelName: "TimeZone",
                    autoSetProxy: false,
                    columns: ["Offset"]
                }),
                filters: Ext.create("Terrasoft.Filter", {
                    property: "Code",
                    value: timeZoneCode
                }),
                callback: function(timeZoneRecords, timeZoneOperation, timeZoneSuccess) {
                    if (timeZoneSuccess === true && timeZoneRecords.length > 0) {
                        var timeZoneRecord = timeZoneRecords[0];
                        var offset = timeZoneRecord.get("Offset");
                        var offsetValue = 0;
                        if (!Ext.isEmpty(offset)) {
                            offset = offset.replace("GMT", "");
                            if (!Ext.isEmpty(offset)) {
                                var sign = (offset.substring(0, 1) === "-") ? 1 : -1;
                                var hours = parseInt(offset.substr(1, 2));
                                var minutes = parseInt(offset.substr(4, 2));
                                offsetValue = sign * (hours * 60 + minutes);
                            }
                        }
                        Terrasoft.Configuration.CurrentUserTimeZoneOffset = offsetValue;
                    }
                },
                scope: this
            });
        }
    }
},
scope: this
});
 
if (!Terrasoft.Configuration.processColumn) {
                Terrasoft.Configuration.processColumn = Terrasoft.OData.ResponseParser.processColumn;
}
 
Terrasoft.OData.ResponseParser.processColumn = function(data, queryConfig, record, columnName) {
                var model = record.self;
                var columnConfig = model.ColumnConfigs.get(columnName);
                var columnValue = data[columnName];
                if ((columnConfig.columnType === Terrasoft.ColumnTypes.date ||
                               columnConfig.columnType === Terrasoft.ColumnTypes.datetime) &&
                               !Ext.isEmpty(Terrasoft.Configuration.CurrentUserTimeZoneOffset)) {
                               if (columnValue.indexOf("/") !== -1) {
                                               var timeZoneOffset = Terrasoft.Configuration.CurrentUserTimeZoneOffset;
                                               columnValue = new Date(parseInt(columnValue.substr(6)));
                                               columnValue = new Date(columnValue.getTime() + timeZoneOffset * 60 * 1000);
                               } else {
                                               columnValue = Terrasoft.util.convertISOStringToDate(columnValue);
                               }
                               record.set(columnName, columnValue);
                } else {
                               Ext.callback(Terrasoft.Configuration.processColumn, Terrasoft.OData.ResponseParser, arguments);
                }
};

- добавить в текущий пакет манифест мобильного приложения (манифест соответствующего рабочего места) и в нем прописать схему UsrSyncExtension, а именно добавить ее в SyncExtensions и CustomSchemas:

"SyncExtensions": [
                               "UsrSyncExtension"
                ],
                "CustomSchemas": [
                               "UsrSyncExtension"
                ],

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

Что делает вышеуказанный код:

- получает из SysAdminUnit часовой пояс текущего пользователя;

- при получении дат во время синхронизации использует этот часовой пояс.

Нравится

Поделиться

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

Вопрос

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

Ошибка при компиляции Элемент Системная настройка с кодом "CodeCompilerWarningLevel" не найдена не найден.

Ответ

Все дело в том что пользователь удалил пользователя Supervisor.

Решение, восстановить супервизора:

------
INSERT INTO Contact (Id, Name, AccountId, OwnerId, GenderId, TypeId) VALUES ('410006E1-CA4E-4502-A9EC-E54D922D2C00',
'Supervisor', 'E308B781-3C5B-4ECB-89EF-5C1ED4DA488E', '410006E1-CA4E-4502-A9EC-E54D922D2C00',
'EEAC42EE-65B6-DF11-831A-001D60E938C6', '60733EFC-F36B-1410-A883-16D83CAB0980')
------
 
INSERT INTO [dbo].[SysAdminUnit]
  ([Id]
  ,[CreatedOn]
  ,[CreatedById]
  ,[ModifiedOn]
  ,[ModifiedById]
  ,[Name]
  ,[Description]
  ,[ParentRoleId]
  ,[ContactId]
  ,[TimeZoneId]
  ,[UserPassword]
  ,[SysAdminUnitTypeValue]
  ,[AccountId]
  ,[Active]
  ,[LoggedIn]
  ,[SynchronizeWithLDAP]
  ,[LDAPEntry]
  ,[LDAPEntryId]
  ,[LDAPEntryDN]
  ,[IsDirectoryEntry]
  ,[ProcessListeners]
  ,[SysCultureId]
  ,[LoginAttemptCount])
VALUES
  ('7F3B869F-34F3-4F20-AB4D-7480A5FDF647'
  ,'2008-12-25 10:30:00.0000000'
  ,'22C5540C-D9B1-49EF-8EB7-72419B78E57C'
  ,'2012-09-11 04:52:13.3962744'
  ,'410006E1-CA4E-4502-A9EC-E54D922D2C00'
  ,'Supervisor'
  ,''
  ,NULL
  ,'410006E1-CA4E-4502-A9EC-E54D922D2C00'
  ,''
  ,'eF4f7sfUgBuNFei7bk+3djw/zXkaB1ODf3huR0RJDD4='
  ,4
  ,NULL
  ,1
  ,0
  ,0
  ,''
  ,''
  ,''
  ,0
  ,0
  ,'1A778E3F-0A8E-E111-84A3-00155D054C03'
  ,0)
GO
 
------

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

Нравится

Поделиться

0 комментариев
Показать все комментарии
Публикация

Вопрос

Суть ошибки: не компилируется один из Package (пакет оракла, а не нашего приложения) с ошибкой, содержащей текст:

ORA-00932: inconsistent datatypes

или

После входа ошибка Authorization Failed

Ответ

Cсылка на багу оракла и патч, который нужно скачать и установить на сервер при возникновении ошибки. Воспроизводится точно на версии 11.2.0.4 (и, судя по описанию патча, еще и 11.2.0.3).

https://support.oracle.com/knowledge/Oracle%20Database%20Products/2003626_1.html

Дополнительно:

There's a known bug related to this see - MOS note 2003626.1. 

It's fixed in patch 18139621. 

https://asktom.oracle.com/pls/apex/f?p=100:11:0::::P11_QUESTION_ID:9519164900346280654

https://stackoverflow.com/questions/43589677/ora-00932-expected-number-got/43591908

Нравится

Поделиться

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

Вопрос

После выбора необходимых значений они не отображаются в лукапе, хотя я их могу получить через this.get('ResponsibleLookUp').

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

Ответ

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

define("CasePage", ["CasePageResources", "terrasoft", "LookupUtilities"],
    function(resources, Terrasoft, LookupUtilities) {
        return {
            entitySchemaName: "Case",
            details: /**SCHEMA_DETAILS*/{}/**SCHEMA_DETAILS*/,
            attributes: {
                "UsrVirtualCity": {
                    dataValueType: Terrasoft.DataValueType.TEXT,
                    type: Terrasoft.ViewModelColumnType.VIRTUAL_COLUMN
                },
                "UsrVirtualCityArray": {
                    dataValueType: Terrasoft.DataValueType.CUSTOM_OBJECT,
                    type: Terrasoft.ViewModelColumnType.VIRTUAL_COLUMN
                }
            },
            diff: /**SCHEMA_DIFF*/[
                {
                    "operation": "insert",
                    "name": "Number",
                    "values": {
                        "layout": { "colSpan": 24, "rowSpan": 1, "column": 0, "row": 4 },
                        "bindTo": "UsrVirtualCity",
                        "caption": "virtual city",
                        "controlConfig": {
                            "className": "Terrasoft.TextEdit",
                            "rightIconClasses": ["custom-right-item", "lookup-edit-right-icon"],
                            "rightIconClick": {
                                "bindTo": "testClick"
                            }
                        }
                    },
                    "parentName": "SolutionTab_gridLayout",
                    "propertyName": "items",
                    "index": 6
                }
            ]/**SCHEMA_DIFF*/,
            methods: {
                onEntityInitialized: function() {
                    this.callParent(arguments);
                    // just for debug:
                    document.scope = this;
                },
                testClick: function() {
                    var config = {
                        entitySchemaName: "City",
                        multiSelect: true
                    };
                    LookupUtilities.Open(this.sandbox, config, this.onTestClickComplete, this, null, false, false);
                },
                onTestClickComplete: function(cities) {
                    if (cities.selectedRows.getCount() > 0) {
                        var citiesItems = cities.selectedRows.getItems();
                        var displayValue = "";
                        for (var i = 0; i < citiesItems.length; i++) {
                            displayValue = displayValue + citiesItems[i].displayValue + "; ";
                        }
                        displayValue = displayValue.substring(0, displayValue.length - 2);
                        this.set("UsrVirtualCity", displayValue);
                        var citiesKeys = cities.selectedRows.getKeys();
                        this.set("UsrVirtualCityArray", citiesKeys);
                    }
                }
            },
            rules: {}
        };
});

 

Нравится

Поделиться

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