Доброго времени суток!
Стоит задача настраивать права доступа к записям раздела с помощью фильтров. Есть карточка со справочным полем "Раздел". Необходимо отобразить фильтры записей для данного раздела, чтобы в дальнейшем запускать БП, настраивающий права доступа к отфильтрованным записям выбранного раздела.
Вопроса два:
1. Как можно хранить значения фильтров в колонке, чтоб потом использовать в БП при раздаче прав?
2. Как отобразить фильтры на карточке? Я создаю контейнер по аналогии с BaseSection, и использую sandbox.loadModule. Ошибок не выдает, как и сами фильтры.
diff:
"operation": "insert",
"name": "ExtendedFiltersContainer",
"parentName": "Header",
"propertyName": "items",
"values": {
"id": "ExtendedFiltersContainer",
"selectors": {"wrapEl": "#ExtendedFiltersContainer"},
"itemType": Terrasoft.ViewItemType.CONTAINER,
"controlConfig": {"visible": {"bindTo": "IsExtendedFiltersVisible"}},
"wrapClass": ["extended-filters-container-wrapClass", "left-inner-el"],
"items": []
}
}
methods:
this.callParent(arguments);
var extendedFilterModuleId = this.getExtendedFilterEditModuleId();
this.sandbox.loadModule("ExtendedFilterEditModuleV2", {
renderTo: "ExtendedFiltersContainer",
id: extendedFilterModuleId
});
}
Нравится
Здравствуйте, на данный момент, в системе не предусмотрено возможности использовать контролл фильтрации, который вы видите на странице секции, на пользовательских страницах другого типа.
Но если Вам необходимо собирать информацию по примененным фильтрам в разделе, а потом их куда-нибудь сохранять, и использовать в тех или иных целях.
Вы можете добавить в действия секции кнопку, которую будет видеть, к примеру, только администратор системы. Перед нажатием применять к разделу фильтрацию. И использовать метод секции «getFilters()» который вернет вам объект, всех, примененных к разделу фильтров.
Как с ним поступать далее, решать вам.
Так же, объект фильтров поддерживает сериализацию и десереализацию.
Ниже прилагаю небольшой пример по получению и сериализации объекта всех примененных к разделу фильтров:
define("OrderSectionV2", [], function() { return { entitySchemaName: "Order", attributes: { }, methods: { getSectionActions: function() { var actionMenuItems = this.callParent(arguments); actionMenuItems.addItem(this.getActionsMenuItem({ "Type": "Terrasoft.MenuSeparator", "Caption": "" })); actionMenuItems.addItem(this.getActionsMenuItem({ "Caption": "testFilters", "Click": { "bindTo": "testFilters" } })); return actionMenuItems; }, testFilters: function() { var filters = this.getFilters(); var serializationInfo = filters.getDefSerializationInfo(); serializationInfo.serializeFilterManagerInfo = true; var filtersJson = filters.serialize(serializationInfo); this.Terrasoft.showInformation(filtersJson); } }, details: /**SCHEMA_DETAILS*/{}/**SCHEMA_DETAILS*/, diff: /**SCHEMA_DIFF*/[]/**SCHEMA_DIFF*/ }; });
простой вариант:
сделайте справочное поле со ссылкой на объект нужных вам фильтров (Например ContactFolder/Группа контакта) и выбирайте нужную группу. В таблицах групп есть поле SearchData - это сохраненные фильтры (для клиентской стороны). В базе они выглядят так:
Перед использованием их значение надо десериализовать:
Terrasoft.deserialize(SearchData)
После этого можете их добавлять в качестве фильтров в запросы:
var searchData = Terrasoft.deserialize(contactGroup.getByIndex(0).SearchData); config.filters.addItem(searchData); ... var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", { rootSchemaName: "Contact" }); esq.addColumn("Id"); esq.filters = config.filters; esq.getEntityCollection(function(result) { if (result.success) { ... } }, this);
Тут есть две проблемы:
1) Группа уже должна быть создана и настроена (это не всегда плохо, но в половине случаев - точно)
2) Если вам надо выбирать из фильтров разных разделов, надо будет сделать переключение схем в зависимости от выбранного раздела ,само справочное поле групп - виртуальным, а фильтры сохранять в другом, скрытом
Сложный вариант:
1) Сделать модуль для настройки и фильтров через интерфейс. Тут логичнее использовать схемы тех разделов, которые будут фильтроваться - так пользователь сможет сразу увидеть результат фильтрации. Но их придется обернуть в отдельный модуль, который будет загружать нужный раздел поверх открытой карточки и иметь как минимум две кнопки - ОК/Отмена - а из схемы раздела надо будет убрать весь остальной функционал (фактически - создать дочернюю схему, например, от contactSectionV2, на которой скрыть все ненужные элементы). Загружать модуль тогда надо будет как-то так
this.sandbox.loadModule("ReportModule", { id: reportModuleId, renderTo: this.renderTo, keepAlive: true });
2) наладить сообщение между модулями карточки и только что созданным для обмена фильтрами
Еще один простой вариант:
создавать вашу сущность с того раздела, который собираетесь фильтровать - открываете Контакты, настраиваете фильтрацию в расширенном режиме и выбрав действие "Создать [Что-то]" передаете туда сразу и раздел и фильтры (их надо будет сначала считать в схеме раздела).
А вот как потом использовать эти фильтры в БП - это вопрос)).
Возможно будет проще сохранять не фильтрацию, а набор ИД отфильтрованных записей. Это простая деталь и в БП проблем особо не будет.
Пример добавления записей по преднастроенному фильтру:
define("SfTestTeamDetail", ["terrasoft", "SfTestTeamDetailResources","ConfigurationConstants", "ConfigurationEnums", "SferaConstants", 'TestingConstants'], function(Terrasoft, resources, ConfigurationConstants, enums, SferaConstants, TestingConstants) { return { entitySchemaName: "SfTestTeam", attributes: {}, messages: { "GetTargetGroup": { mode: Terrasoft.MessageMode.PTP, direction: Terrasoft.MessageDirectionType.PUBLISH } }, methods: { initData: function() { this.callParent(arguments); }, onAddButtonClick: function() { var cardState = this.sandbox.publish("GetCardState", null, [this.sandbox.id]); var isNew = (cardState.state === enums.CardStateV2.ADD || cardState.state === enums.CardStateV2.COPY); if (isNew) { var args = { isSilent: true, messageTags: [this.sandbox.id] }; this.sandbox.publish("SaveRecord", args, [this.sandbox.id]); return; } var SfTargetGroup = this.sandbox.publish("GetTargetGroup", null, [this.sandbox.id]).targetGroup; this.set("SfTargetGroup", SfTargetGroup); this.addContactToTeam(arguments[3] === "byGroup"); }, addContactToTeam: function(byGroup) { if(byGroup) { this.getGroupList(); } else { this.getUsersList(); } }, getUsersList: function() { /*var scope = this; var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", { rootSchemaName: "SfTestTemplate" }); esq.addColumn("SfTargetGroup"); esq.filters.addItem(Terrasoft.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "Id", this.get("MasterRecordId"))); esq.getEntityCollection(function(result) { if (result.success && result.collection.getItems().length>0) { scope.prepareLookupConfig(result.collection.getItems()[0].get("SfTargetGroup").value); } }, scope);*/ this.Terrasoft.chain( function(next) { this.getContactLookupConfig(function() { next(); }, this); }, function(next) { this.openContactLookup(function() { next(); }, this); }, function(next) { this.addContactCallback(function() { next(); }, this); }, function(next) { this.reloadGridData(); next(); }, this); }, getGroupList: function() { this.Terrasoft.chain( function(next) { this.getContactGroupLookupConfig(function() { next(); }, this); }, function(next) { this.openContactGroupLookup(function() { next(); }, this); }, function(next) { this.getContactLookupConfig(function() { next(); }, this); }, function(next) { this.getSelectedGroupFilter(function() { next(); }, this); }, function(next) { this.getFilteredContacts(function() { next(); }, this); },function(next) { this.addContactCallback(function() { next(); }, this); }, function(next) { this.reloadGridData(); next(); }, this); }, getContactLookupConfig: function(callback) { var SfTargetGroup = this.get("SfTargetGroup"); var templateId = this.get("MasterRecordId"); var filters = this.Ext.create("Terrasoft.FilterGroup"); var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", { rootSchemaName: "SfTestTeam", isDistinct: true }); var IdsExists = []; esq.addColumn("SfContact"); esq.filters.addItem(Terrasoft.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "SfTestTemplate", templateId)); esq.getEntityCollection(function(result) { if (result.success) { var items = result.collection.getItems(); IdsExists = []; Terrasoft.each(items, function(item) { var contact = item.get("SfContact"); if (contact && contact.value) { IdsExists.push(contact.value); } }, this); var contactType = SferaConstants.ContactType.Employee.value; if (SfTargetGroup && SfTargetGroup.value) { if (SfTargetGroup.value == TestingConstants.TargetGroupType.Doctor.value) { contactType = SferaConstants.ContactType.Doctor.value; } filters.addItem(Terrasoft.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "Type", contactType)); } filters.addItem(this.getNotExistsInTeamFilter(IdsExists)); var config = { entitySchemaName: "Contact", multiSelect: true, columns: ["Name"], hideActions: true }; config.filters = filters; this.set("ContactLookupConfig", config); if (this.Ext.isFunction(callback)) { callback.call(this); } } }, this); }, getContactGroupLookupConfig: function(callback) { var config = { entitySchemaName: "ContactFolder", //multiSelect: true, columns: ["Id", "Name", "SearchData"], hideActions: true }; var filters = this.Terrasoft.createFilterGroup(); //todo use configconstants filters.addItem(Terrasoft.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "FolderType.Id", "65ca0946-0084-4874-b117-c13199af3b95"));//dynamic config.filters = filters; this.set("ContactGroupLookupConfig", config); if (this.Ext.isFunction(callback)) { callback.call(this); } }, openContactGroupLookup: function(callback) { var config = this.get("ContactGroupLookupConfig"); this.openLookup(config, function(args) { this.set("SelectedContactGroup", args.selectedRows); if (this.Ext.isFunction(callback)) { callback.call(this); } }, this); }, getSelectedGroupFilter: function(callback) { // todo учеть возможность множественного выбора групп var contactGroup = this.get("SelectedContactGroup"); var config = this.get("ContactLookupConfig"); if (contactGroup.getCount()) { var searchData = Terrasoft.deserialize(contactGroup.getByIndex(0).SearchData); config.filters.addItem(searchData); } this.set("ContactLookupConfig", config); if (this.Ext.isFunction(callback)) { callback.call(this); } }, openContactLookup: function(callback) { var config = this.get("ContactLookupConfig"); this.openLookup(config, function(args) { this.set("SelectedContacts", args.selectedRows); if (this.Ext.isFunction(callback)) { callback.call(this); } }, this); }, getFilteredContacts: function(callback) { var ContactLookupConfig = this.get("ContactLookupConfig"); var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", { rootSchemaName: "Contact" }); esq.addColumn("Id"); esq.filters = ContactLookupConfig.filters; esq.getEntityCollection(function(result) { if (result.success) { //Ids = result.collection.getKeys(); this.set("SelectedContacts", result.collection); if (this.Ext.isFunction(callback)) { callback.call(this); } } }, this); }, addContactCallback: function(callback){ this.showBodyMask(); var Ids = this.get("SelectedContacts").getKeys(); var bq = this.Ext.create("Terrasoft.BatchQuery"); this.Terrasoft.each(Ids, function(item) { var insert = this.Ext.create("Terrasoft.InsertQuery", { rootSchemaName: "SfTestTeam" }); var newGuid = Terrasoft.generateGUID(); var testTemplate = this.get("MasterRecordId"); insert.setParameterValue("Id", newGuid , Terrasoft.DataValueType.GUID); insert.setParameterValue("SfContact", item, Terrasoft.DataValueType.GUID); insert.setParameterValue("SfTestTemplate", testTemplate, Terrasoft.DataValueType.GUID); bq.add(insert); }, this); bq.execute(function(result) { this.hideBodyMask(); if (result.success) { if (this.Ext.isFunction(callback)) { callback.call(this); } } else console.log("error"); }, this); }, getNotExistsInTeamFilter: function(IdsExists) { var existsFilter = this.Terrasoft.createNotExistsFilter("[SfTestTeam:SfContact:Id].SfContact"); var subFilter = this.Terrasoft.createColumnInFilterWithParameters( "SfContact", IdsExists); existsFilter.subFilters.addItem(subFilter); existsFilter.subFilters.addItem(Terrasoft.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "SfTestTemplate", this.get("MasterRecordId"))); return existsFilter; } }, diff: /**SCHEMA_DIFF*/[ { "operation": "merge", "name": "AddRecordButton", "values": { "click": {bindTo: "onAddButtonClick"}, "menu": [], "tag": "single" } }, { "operation": "remove", "name": "AddTypedRecordButton" }, { "operation": "remove", "name": "EditRecordMenu" }, { "operation": "remove", "name": "CopyRecordMenu" }, { "operation": "insert", "name": "AddTargetGroupButton", "parentName": "Detail", "propertyName": "tools", "values": { "itemType": Terrasoft.ViewItemType.BUTTON, "click": {"bindTo": "onAddButtonClick"}, "style": Terrasoft.controls.ButtonEnums.style.TRANSPARENT, "caption": {"bindTo": "Resources.Strings.AddTargetGroupButtonCaption"}, "tag": "byGroup" }, "index": 1 } ]/**SCHEMA_DIFF*/ }; } );
Спасибо огромное за идеи! Взяв понемногу из каждой у меня нарисовался алгоритм.
Остается только одна задача: я передаю в бп коллекцию записей, UId схемы раздела и объект администрирования. Не могу понять как правильно их передать в элемент "изменить права доступа". Подскажите, пожалуйста, как правильно реализовать данную задачу.