У меня есть база данных, в которой хранятся пользователи моего приложения. Когда новый пользователь регистрируется, запись для этого пользователя вставляется в базу данных. У меня есть реплицированная версия (подчиненная) этой базы данных (пока используется mysql).
Меня беспокоит такой сценарий:
Шаг 1: пользователь регистрируется, и пользовательская запись вставляется в базу данных
Шаг 2: затем пользователь пытается войти в систему, и процесс входа в систему запрашивает пользователя в базе данных. однако этот запрос попадает в подчиненную базу данных, но запись пользователя еще не реплицирована в подчиненном устройстве, и он возвращает ошибку о том, что пользователь не существует.
Это довольно тривиальный пример, но я вижу, как его можно применить во многих случаях. Есть ли стратегия настройки реплицированных баз данных, которая поможет предотвратить эту ситуацию?
Это реальная проблема, и она возникает почти сразу после того, как вы начинаете пытаться записывать на ведущее устройство и читать с ведомого. Хотя промежуток времени между регистрацией пользователя и входом в систему, вероятно, достаточно велик, чтобы не беспокоиться об этом, большинство вещей, которые ваши пользователи захотят сделать, вызовут эту проблему.
Такие действия, как создание сообщения на форуме или в блоге, часто приводят к перенаправлению, которое возвращает их на страницу, где они могут просмотреть только что сделанное сообщение. Если эта страница читает с ведомого устройства, между записью и чтением будет только доля секунды, чего часто бывает недостаточно для репликации.
Есть три решения, которые я использовал в прошлом, и одно, которое я не использовал лично.
Вариант 3 был для меня наиболее успешным в прошлом, и я бы выбрал его в будущем.
Не совсем (насколько я знаю); у вас должна быть значительная задержка (или серьезная ошибка, приводящая к рассинхронизации ведомого устройства), чтобы пользователь мог войти в систему и потенциально попасть в подчиненную базу данных быстрее, чем подчиненная база данных может реплицировать сервер.
Единственная альтернатива, которую я могу придумать, - это иметь что-то на уровне приложения, которое запускает ведущее устройство, если ведомое устройство не может найти запись; но это, скорее, в первую очередь противоречит цели возможности запросить подчиненное устройство.
Перед выполнением запроса проверьте, является ли база данных подчиненной, если да, проверьте, запущены ли подчиненные потоки, и если да, проверьте Seconds_Behind_Master
. Все в SHOW SLAVE STATUS;
. Если он не работает или наблюдается значительная задержка, запустите запрос на главном сервере.