Зміна значення для всіх в датасеті

Необхідна ця функція, щоб працювати з даними відібраними користувачем. Достатньо просто передати посилання на датасет.
Зауважу, потрібно ще підключити scr_WindowUtils і scr_Processings.

Використовую цю функцію:

 

function WriteFieldValueToDataset(Dataset, FieldName, FieldValue) {
       
        var ProgressBar = new Object;
       
        ProgressBar.Caption = 'Внесення змін';
        ProgressBar.Prompt = ' Виконується...';
        ProgressBar.Window = System.EmptyValue;
       
        var DatasetCount = Dataset.RecordsCount;
        var OldFetchSetting = Dataset.FetchRecordsCount;
        var StartCount = DatasetCount;
        var i = 0;
               
        BeginProcessingProgress(ProgressBar.Window, ProgressBar.Caption,
          ProgressBar.Prompt, true, false);

        Dataset.DisableEvents();
        Dataset.FetchRecordsCount = -1;
        RefreshDataset(Dataset);
       
        Dataset.GotoFirst();
        while (!Dataset.IsEOF){
                Dataset.Edit();
                Dataset(FieldName) = FieldValue;
                Dataset.Post();
                Dataset.GotoNext();
                var ProgressWindow = MoveProcessingProgress(ProgressBar.Window,
                  (i++)*100/StartCount, true);
                if (ProgressWindow.Attributes('CancelledByUser')) break;
        }
       
        Dataset.FetchRecordsCount = OldFetchSetting;
        RefreshDataset(Dataset);
        Dataset.EnableEvents();

        EndProcessingProgress(ProgressBar.Window, true);
}

Мав проблему з тим, що датасет по замовчуванню вибирає частину записів. Тому потрібно тимчасово виконати:

    Dataset.FetchRecordsCount = -1;
    RefreshDataset(Dataset);

А потім повернути старе значення. Інакше будуть "тормоза".

Дякую, Денису Масалову за вчасну пораду!

Нравится

Поделиться

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

Юрий, а почему не выполнить UpdateQuery с фильтрами, которые используются для открытия DataSet?
1. Это ускорит работу обновления на порядок - не надо будет "гонять" данные на клиент
2. А как Вы откатываете изменения? Почему без транзакции? Получается часть данных пользователь изменил, а часть нет. Это может привести данные в противоречивое состояние. А в случае UpdateQuery это исключено, так как будут обновлены сразу все или не одной записи.

1. Давайте спробуєм, ви можете викласти функцію, яка б збирала дані фільтру для будь-якого датасету і використовуючи відповідний автиматично створюємий UpdateQuery датасета для зміни значення поля всім відфільтрованим записам?
2. Зміни не відміняються, а припиняються. На скільки я розумію транзакція виконується при зміні кожного запису.

1. В случае если у Вас фильтры по Join в DBDataset, то такое нельзя будет сделать, в остальных реально. Главное использовать метод AssignObject, который скопирует за Вас всю структуру фильтров и параметров.
2. Правильно, если Вы не указали явно, то каждая операция с БД выполняется в рамках неявной транзакции. но если Вы сделаете старт транзакции явно, то все операции будут выполняться в рамкой Вашей транзакции и Вы сможет откатить все изменения или подтвердить их.

Дякую, Олександр, за корисний комент. Обов'язково врахую при необхідності.

К слову, зачем копировать фильтры, если можно пройтись по набору, собрать ИДшники записей в этом наборе и послать запрос вида

update table set ...
where ID in ( ... )

Юрий, их может быть много, а фильтре IN есть ограничения на кол-во параметров на уровне сервера, Вашу идею необходимо трансформировать - в фильтре IN можно использовать сразу весь запрос из DBDataset.

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