Принудительное обновление записи

Обсуждение возникших проблем, предложений и ошибок SDAC компонентов
Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Принудительное обновление записи

Сообщение Rajoe » Сб 20 окт 2012 13:05

У открытого TMSQuery в состоянии dsBrowse заполняю нужным мне запросом SQLRefresh и выполняю RefreshRecord - ничего не происходит, и dbMonitor ничего не показывает. Есть какие-то ограничения, правила, условия выполнения обновления с помощью RefreshRecord? Версия 6.1.3 для Delphi 7.

AndreyZ
Devart Team
Сообщения: 328
Зарегистрирован: Чт 08 сен 2011 13:18

Re: Принудительное обновление записи

Сообщение AndreyZ » Пн 22 окт 2012 07:36

Здравствуйте,

dbMonitor отображает запросы если включены опции TMSSQLMonitor.Active и TMSSQLMonitor.Options.moDBMonitor . Убедитесь что они включены. Я выполнил следующий код:

Код: Выделить всё

MSQuery1.SQL.Text := 'select * from test';
MSQuery1.Open;
MSQuery1.SQLRefresh.Text := 'select * from test where id=:old_id';
MSQuery1.RefreshRecord;
, и dbMonitor показал оба запроса.

Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Re: Принудительное обновление записи

Сообщение Rajoe » Вт 23 окт 2012 10:33

dbMonitor включен правильно и работает. По крайней мере, остальные запросы он показывает. Это наводит на мысль, что RefreshRecord не посылает запроса на сервер. Ключевое поле не заполнено, это может быть причиной? Сам запрос на обновление составлен так, что необходимости в ключевом поле нет.

AndreyZ
Devart Team
Сообщения: 328
Зарегистрирован: Чт 08 сен 2011 13:18

Re: Принудительное обновление записи

Сообщение AndreyZ » Вт 23 окт 2012 11:07

TMSQuery посылает запрос на обновление записи на сервер только при использовании клиентского курсора ctDefaultResultSet. Проверьте пожалуйста что свойство TMSQuery.CursorType установлено в ctDefaultResultSet.

Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Re: Принудительное обновление записи

Сообщение Rajoe » Вт 23 окт 2012 17:17

Так и настроено. Это единственное условие?

AndreyZ
Devart Team
Сообщения: 328
Зарегистрирован: Чт 08 сен 2011 13:18

Re: Принудительное обновление записи

Сообщение AndreyZ » Ср 24 окт 2012 09:02

Я не могу повторить данную проблему. Пришлите пожалуйста тестовый пример который демонстрирует эту проблему на andreyz*devart*com .

Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Re: Принудительное обновление записи

Сообщение Rajoe » Ср 24 окт 2012 14:17

Вопрос снимается: начал готовить пример и нашёл у себя ошибку. Спасибо за терпение!

AndreyZ
Devart Team
Сообщения: 328
Зарегистрирован: Чт 08 сен 2011 13:18

Re: Принудительное обновление записи

Сообщение AndreyZ » Ср 24 окт 2012 14:23

Пожалуйста, я рад что Вы нашли решение данной проблемы. Если возникнут дальнейшие вопросы по SDAC, пишите нам.

Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Re: Принудительное обновление записи

Сообщение Rajoe » Чт 25 окт 2012 09:35

В завершение, RefreshRecord() не выполняла обращение к серверу при CachedUpdates = true и Options.UpdateBatchSize > 1. При Options.UpdateBatchSize = 1 запрос из SQLRefresh на сервер отправляется нормально.

AndreyZ
Devart Team
Сообщения: 328
Зарегистрирован: Чт 08 сен 2011 13:18

Re: Принудительное обновление записи

Сообщение AndreyZ » Чт 25 окт 2012 12:58

Rajoe писал(а):RefreshRecord() не выполняла обращение к серверу при CachedUpdates = true и Options.UpdateBatchSize > 1. При Options.UpdateBatchSize = 1 запрос из SQLRefresh на сервер отправляется нормально.
Пришлите пожалуйста пример который демонстрирует данное поведение на andreyz*devart*com .

Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Re: Принудительное обновление записи

Сообщение Rajoe » Чт 25 окт 2012 13:28

Отправил.

AndreyZ
Devart Team
Сообщения: 328
Зарегистрирован: Чт 08 сен 2011 13:18

Re: Принудительное обновление записи

Сообщение AndreyZ » Пт 26 окт 2012 09:01

Я исследовал Ваш пример. Вы пытаетесь обновлять новые записи до их отправки на сервер, поэтому SDAC и не выполняет никаких действий. В данном случае попытка выполнить запрос на обновление записей с сервера не имеет смысла, ведь таких записей еще нет на сервере. Поэтому установка свойства TMSQuery.Options.UpdateBatchSize в 1 является корректным решением данной проблемы. При TMSQuery.Options.UpdateBatchSize равным 1 SDAC выполняет обновление новых записей так как они уже отправлены на сервер.

Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Re: Принудительное обновление записи

Сообщение Rajoe » Пн 29 окт 2012 15:33

В примере выполняется вот такой код:

Код: Выделить всё

procedure TForm4.MSQuery1UpdateRecord(DataSet: TDataSet;
  UpdateKind: TUpdateKind; var UpdateAction: TUpdateAction);
begin
  case UpdateKind of
    DB.ukInsert: InsertRecord(DataSet);
    DB.ukModify: ModifyRecord(DataSet);
    DB.ukDelete: DeleteRecord(DataSet);
  end;
  UpdateAction := uaApplied;
end;

procedure TForm4.InsertRecord(DataSet: TDataSet);
var
  i: integer;
begin
  SQLExecutor.SQL.Clear();
  SQLExecutor.SQL.Add('insert into vwApplication (sName, sDescription) values (:sName, :sDescription);');
  SQLExecutor.SQL.Add('set :idApplication = scope_identity();');
  SQLExecutor.ParamByName('idApplication').ParamType := ptInputOutput;
  for i := 0 to SQLExecutor.ParamCount - 1 do
    SQLExecutor.Params[i].Value := DataSet[SQLExecutor.Params[i].Name];

  SQLExecutor.Execute();

  MSQuery1.SQLRefresh.Text := Format('select idApplication from vwApplication where idApplication = %s',
                            [SQLExecutor.ParamByName('idApplication').AsString]);
  MSQuery1.RefreshRecord();
end;
Из него видно, что RefreshRecord всегда, при любых условиях вызывается строго после отправки запроса на вставку записи на сервер. То есть, к моменту выполнения RefreshRecord запись на сервере уже есть. Да и значения это не имеет, поскольку RefreshRecord не делает никаких прямых проверок наличия записи на сервере, во всяком случае, в Wireshark я ничего такого не увидел. Или не разглядел?

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

AndreyZ
Devart Team
Сообщения: 328
Зарегистрирован: Чт 08 сен 2011 13:18

Re: Принудительное обновление записи

Сообщение AndreyZ » Вт 30 окт 2012 10:21

Свойство UpdateBatchSize определяет количество команд которые отправятся на сервер в одном пакете. Например, Вы установили UpdateBatchSize в 2. Это означает что при вызове ApplyUpdates, SDAC соберет все изменения в пакеты по две команды в каждом (например два INSERT запроса). В Вашем примере Вы выполняете запрос на сервер для каждой команды, что противоречит логике работы UpdateBatchSize при его значении больше 1. Поэтому при вызове RefreshRecord, SDAC видит что количество команд в пакете не равно UpdateBatchSize и не выполняет данную команду.

Rajoe
Сообщения: 24
Зарегистрирован: Пн 24 сен 2012 15:16

Re: Принудительное обновление записи

Сообщение Rajoe » Вт 30 окт 2012 16:08

А если число изменений меньше, чем UpdateBatchSize? То есть, UpdateBatchSize = 10, а изменили 7 записей и нажали кнопку "Сохранить". Работа уже в принципе завершена, больше ничего делать не нужно, а RefreshRecord по-прежнему будет отказываться работать? Как её заставить обновить запись в таком случае?

Ответить