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

Мне нужно предварительно выделить краткие целые первичные ключи (из непрерывного диапазона) для моих синхронизированных клиентов базы данных.

Вариант использования довольно прост: мне нужно распечатать билеты с короткими серийными номерами в ситуации, когда мобильные клиенты имеют прерывистое соединение. Номера должны быть достаточно короткими, чтобы их можно было прочитать через плохую систему громкой связи в шумной обстановке, чтобы получить призы за дверь.

Realm идеально подходит для этой задачи, но мне нужно позволить каждому клиенту предварительно выделить себе пул гарантированно-уникальных серийных номеров, когда они подключены к серверу, чтобы они могли печатать билеты позже, даже в автономном режиме.

class TicketNumber extends RealmObject { 
    @PrimaryKey int serialNumber;
    String clientId; // instance identifier unique to each client
}

Мое намерение состоит в том, чтобы клиент A выполнил транзакцию для создания набора объектов TicketNumber, начиная с max(serialNumber)+1, установив для каждого свой собственный clientId. Я надеялся, что смогу рассчитывать на то, что транзакция завершится неудачно (выбросит ObjectExists), если клиент B уже создал TicketNumber объектов в этом диапазоне.

Однако, если клиент A или клиент B отключены во время создания, он будет легко создавать локальные копии в том же диапазоне. Когда происходит синхронизация, она устанавливает clientId конфликтующего объекта в зависимости от того, какой клиент «создал» его последним. Очевидно, что для меня это проблема, если оба клиента уже распечатали билет с одним и тем же серийным номером.

На мой взгляд, чтобы гарантировать право собственности клиента на номера тикетов, мне нужно будет создавать объекты «сначала онлайн», чтобы я мог наблюдать за конфликтами и реагировать на них. Есть ли способ узнать состояние подключения клиента области? Возможно ли то, что я пытаюсь сделать? Должен ли я ждать, пока счетчики будут доступны?


person Autumn    schedule 04.12.2016    source источник


Ответы (1)


Самый простой способ сгенерировать локальные идентификаторы для распределенных устройств — это не использовать целые числа и ограниченные диапазоны, а использовать UUID: UUID.randomUUID().toString() должно быть достаточно, поскольку это 128-битное значение. Вероятность того, что неисправное оборудование испортит работу или заменят биты земных лучей, больше, чем два одинаковых ключа на двух устройствах.

Это в основном то, что делают все другие распределенные базы данных.

person Christian Melchior    schedule 05.12.2016
comment
Это говорит о том, что для 100 билетов среди 4 клиентов я бы создал составной ключ с UUID + локально увеличенное число 0-24. Это увеличивает длину моего ключа в 19 раз, с 7 бит до 128+5. На самом деле это не отвечает моей потребности в предварительном распределении последовательных серийных номеров. Отредактирован вопрос, чтобы включить, что серийные номера должны быть краткими и предпочтительно из непрерывного диапазона чисел. - person Autumn; 05.12.2016