В данный момент вы используете разрешение конфликтов по умолчанию на сервере MobiLink, поэтому по умолчанию последняя синхронизация выигрывает. Для этого вам необходимо реализовать собственную схему разрешения конфликтов.
Для этого потребуется две вещи в удаленной базе данных:
1) В удаленной базе данных должен быть столбец таблицы, который синхронизируется с консолидированной базой данных и отслеживает время обновления записей на удаленном сайте.
2) Вам придется доверять системным часам на удаленных сайтах. Если люди выясняют, как разрешаются конфликты, и хотят, чтобы их данные побеждали в конфликте, то ничто не мешает пользователю изменить системное время на своем удаленном устройстве на следующую неделю, обновить свои данные, изменить системное время и затем синхронизация.
В консолидированном, вам нужно реализовать разрешение конфликтов, что не так сложно. Пока ваша таблица не содержит больших двоичных объектов, вы можете записать разрешение конфликта в событие upload_update для этой таблицы. Давайте предположим, что таблица в удаленной базе данных выглядит следующим образом:
create table Admin (
admin_id bigint default global autoincrement(1000000) primary key,
data varchar(64) not null,
rem_last_modified timestamp not null default timestamp
);
Давайте также предположим, что таблица в консолидированной форме выглядит очень похожей, но в ней есть еще один последний измененный столбец для отслеживания изменений строк в консолидированной.
create table Admin (
admin_id bigint default global autoincrement(1000000) primary key,
data varchar(64) not null ,
rem_last_modified timestamp not null default ‘1900-01-01’,
cons_last_modified timestamp default timestamp
);
Как правило, ваше событие upload_update будет выглядеть примерно так:
call ml_add_table_script( 'v1', 'Admin', 'upload_update',
'update Admin set data = {ml r.data},
rem_last_modified = {ml r.rem_last_modified}
where admin_id = {ml r.admin_id}'
);
Вместо этого мы переписываем ваше событие upload_update для вызова хранимой процедуры, а также передаем старые значения строк из удаленной базы данных.
call ml_add_table_script( 'v1', 'Admin', 'upload_update',
'call admin_upload_update( {ml r.admin_id},
{ml r.data}, {ml r.rem_last_modified},
{ml o.data}, {ml o.rem_last_modified}’
);
Ключ к вашей хранимой процедуре заключается в том, что мы собираемся выполнить обновление, но условие where обновления будет включать в себя как значения первичного ключа, так и старые значения строки из удаленной базы данных. Если кто-то изменил строку в объединенном, это обновление обновит ноль строк, и мы знаем, что возникает конфликт. Если он обновляет строку, то не было никакого конфликта. Ваша хранимая процедура будет выглядеть примерно так (псевдо-SQL ниже):
create procedure admin_upload_update (
@admin_id bigint,
@new_data varchar(64),
@new_rem_lmod timestamp,
@old_data varchar(64),
@old_rem_lmod timestamp
)
begin
declare @cur_rem_lmod timestamp;
update admin set data = @new_data, rem_last_modified = @new_rem_lmod
where admin_id = @admin_id
and data = @old_data
and rem_last_modified = @old_rem_lmod;
if @@rowcount = 0 then
// conflict !!
select rem_last_modified into @cur_rem_lmod
from admin where admin_id = @admin_id;
if @new_rem_lmod > @cur_rem_lmod then
// update using new_data and new_rem_lmod
else
// do nothing, current values in cons wins
end if;
end if;
end;
Подробнее о разрешении конфликтов см. В следующем разделе документации v10:
MobiLink - Администрирование сервера
Методы синхронизации
Обработка конфликтов
http://dcx.sybase.com/index.php#http%3A%2F%2Fdcx.sybase.com%2Fhtml%2Fdbmlen10%2Fml-conflicts-synch.html