В общем случае вы не можете завершить транзакцию на подключении tcp, которое может выйти из строя. Единственный способ реализовать такой протокол в подключении tcp - добавить простую команду в commit
(подтвержденная команда) и поместить ее в конце каждой такой команды (они могут быть буферизованы группами по tcp). Команда должна быть двумя командами рукопожатия (commit -> ack
), и вы должны зафиксировать всю транзакцию при получении command
и откат, если время ожидания до получения сообщения commit
. Мобильное устройство должно принимать во внимание сообщение, получающее сообщение ack
(ну, вам не нужно указывать транзакции, поскольку TCP обеспечивает порядок прибытия и последовательность пакетов), и подумайте о совершении всех транзакций, за которые он получил сообщение ack
. Учтите, что tcp выполняет тайм-аут и переадресацию, поэтому вам нужно использовать только одну отправку на сообщение и никогда не отправлять повторно отправленное сообщение. Если вы тайм-аут, просто снимите соединение и снова его откройте, учитывая, что последняя транзакция прервана.
Нумерация транзакций будет в порядке, чтобы учесть потерю последних ack
с сервера. Если первый идентификатор транзакции в следующем соединении совпадает с последним последним соединением, вы можете предположить, что клиент потерял свой последний тайм-аут и снова повторяет последнюю транзакцию. В этом случае вам нужно ответить с ack
на него и игнорировать все команды, выданные клиентом (так как они уже были выполнены сервером.)
Это все необходимо, чтобы быть правым в обоих местах (сервер и клиент) и не пытайтесь что-то сэкономить или потеряете данные.
Последнее замечание: у вас нет чего-то вроде тайм-аута для подключения tcp, вы должны реализовать его в своем протоколе внутри протокола. Соединение tcp может находиться в состоянии READY в течение недель или даже лет без обмена одним пакетом только потому, что обеим сторонам нечего сказать друг другу. Для этого есть опция KEEP_ALIVE, но вы можете ее активировать, у вас нет возможности исправить задержку таймаута, чтобы она не срабатывала.
Хорошим примером всех этих протоколов для обнаружения сбоев является протокол X. Это протокол, основанный на транзакции, где есть команды, выданные клиентом (есть как стили, команды с ответом, так и команды, которые не запрашивают такой ответ), а также асинхронные события (сигналы, поступающие с сервера на клиент без подтверждения приема или команда с просьбой)
в этом протоколе, у вас есть так называемая SYNC
команды/сервис, который позволяет клиенту получить в синхронизации с сервером (вы его используете, когда вы хотите, чтобы заверить сервер обрабатывал все команды до сих пор).Кроме того, сервер всегда посылает ответы/события с неявным запросом id (приращения для каждой клиентской команды) последнего запрошенного клиента , поэтому это позволяет сэкономить много команд SYNC
(и задержек на оба конца) клиенту.