Переопределение метода save при сохранении карточки Контрагента
Добрый день.
Задача: при сохранении карточки контрагента производить проверку - а не существует ли уже в системе контрагента с таким же значением поля UsrParametr1.
Я переопределила метод save() в карточке контрагента. Произвожу поиск с помощью EntitySchemaQuery - если в качестве результата мне вернулось кол-во записей > 1, значит запись с таким UsrParametr1 существует и я просто вывожу сообщение и не сохраняю карточку контрагента.
Но если же же записей 1, то я должна вызвать базовый метод save, который произведет сохранение карточки. При вызове this.callParent(arguments); появляется ошибка и карточка не сохраняется.
Подскажите, как решить данную проблему?
Переопределенный метод save():
var param = this.get("UsrParametr1");
var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", {
rootSchemaName: "Account"
});
esq.addColumn("UsrParametr1", "UsrParametr1");
var filter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "UsrParametr1", param);
esq.filters.add("filter", filter);
esq.getEntityCollection(function(result) {
if (!result.success) {
this.showInformationDialog("Ошибка");
return;
}
if (result.collection.collection.items.length > 1)
{
this.showInformationDialog("Нельзя сохранить");
return;
}
this.callParent(arguments); // не отрабатывает, появляется ошибка
}, this);
}
Нравится
Добро пожаловать в мир асинхронных вычислений!
Для наглядности:
esq.getEntityCollection(callback, scope);
т.е программа заходит в функцию save, бежит до esq.getEntityCollection, и после него функция save завершается. Далее спустя некоторое время приходит callback, вызывается функция с параметром result
function(result) { if (!result.success) {....
Беда в том, что внутри неё ни о каком callParent() и речи быть не может. (ибо вы находитесь внутри самописной функции, у неё нет родителя для вызова).
В качестве дико кривого варианта:
save: function(parameter) { if (!parameter) {this.checkField()} else {this.callParent(arguments)} } checkField: function() { //тут esq запрос и в callback-е, если все условия сходятся (записей < 1 в вашем случае), вызываете this.save(true); }
или
сделать по-умному: в объекте создать событийный подпроцесс (перед сохранением или проверка записи, тут надо примеры в конфигурации посмотреть), в подпроцессе проверять условия и в зависимости от них принимать решение... Но это все скучно, к тому же придется кодить на C#.
Как-то так. Костыли - наше все.
Добрый день. В вашем случае надо переопределить getParentMethod, чтобы callParent не вызывался.
Рабочий код будет выглядеть следующим образом:
getParentMethod: function() { var method, superMethod = (method = this.getParentMethod.caller) && (method.$previous || ((method = method.$owner ? method : method.caller) && method.$owner.superclass[method.$name])); return superMethod; }, save: function() { var parentSave = this.getParentMethod(); var parentArguments = arguments; var param = this.get("UsrParametr1"); var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", { rootSchemaName: "Account" }); esq.addColumn("UsrParametr1", "UsrParametr1"); var filter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "UsrParametr1", param); esq.filters.add("filter", filter); esq.getEntityCollection(function(result) { if (!result.success) { this.showInformationDialog("Ошибка"); return; } if (result.collection.collection.items.length > 1) { this.showInformationDialog("Нельзя сохранить"); return; } //this.callParent(arguments); // не отрабатывает, появляется ошибка parentSave.apply(this, parentArguments); }, this); }
Елена, в Вашем первоначальном коде, достаточно в коллбэкке esq-запроса, вызывать не this.callParent(argumеnts); а непосредственный метод "save" у контекста. При необходимости сохранив в текущем контексте аргументы изначально передаваемые в метод, и установив специальный флаг реагируя на повторный вызов.
save: function() { //Проверка на повторный вызов из асинхронной функции запроса. if (this.saveRecallFlag) { //сбросим флаг повторного вызова this.saveRecallFlag = false; //стандартное сохранение this.callParent(arguments); } else { //Если нет - выполняем логику: var param = this.get("UsrParametr1"); var esq = this.Ext.create("Terrasoft.EntitySchemaQuery", { rootSchemaName: "Account" }); esq.addColumn("UsrParametr1", "UsrParametr1"); var filter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "UsrParametr1", param); esq.filters.add("filter", filter); //Перед асинхронным вызовом, сохраним набор аргументов с которым был вызван метод в текущем контексте //Мы именно клонируем массив, т.к. в момент вызова асинхронной функции, псевдомасив arguments будет //содержать параметры вызова коллбэка. this.saveArgumentsRecallBuff = _(arguments).clone(); //Установим в текущий контекст специальный флаг, который позволит проигнорировать логику проверки //при повторном вызове this.saveRecallFlag = true; esq.getEntityCollection(function(result) { if (!result.success) { this.showInformationDialog("Ошибка"); return; } if (result.collection.collection.items.length > 1) { this.showInformationDialog("Нельзя сохранить"); return; } this.save(this.saveArgumentsRecallBuff); // не отрабатывает, появляется ошибка }, this); } }