Скрученный питон: принудительное соединение одного идентификатора
У меня есть витой сервер, использующий сокеты SSL и использующий сертификаты для идентификации разных клиентов, которые подключаются к серверу. Я хотел бы обеспечить состояние, когда существует только одно соединение с каждым возможным идентификатором. Два способа, о которых я могу думать, это отслеживать подключенные идентификаторы, а затем не разрешать второе соединение с тем же идентификатором или разрешать второе соединение и немедленно завершать первое. Я пытаюсь сделать позже, но у меня есть некоторые проблемы (я объясню свой выбор в конце)
Я храню список соединений в фабричном классе, а затем после рукопожатия SSL сравниваю идентификатор клиента с этим списком. Если это уже в этом списке, я пытаюсь позвонить .transport.abortConnection()
в теме. Затем я хочу сделать обычные вещи, чтобы записать новое соединение в моей базе данных. Тем не менее, призыв к abortConnection()
похоже не звонит connectionLost()
непосредственно, где я делаю свою очистку и обращаюсь к базе данных, чтобы сказать, что соединение было потеряно. Итак, мой код затем записывает, что идентификатор подключен, но позже делается вызов connectionLost()
в результате база данных, кажется, отключила этот идентификатор.
Есть ли какой-то способ заблокировать входящее второе соединение от дальнейшей обработки, пока первое соединение не завершит обработку разъединения?
Объяснение выбора: единственная причина, по которой я это делаю, состоит в том, что у меня есть клиенты за NAT, которые, кажется, меняют свой IP-адрес довольно регулярно (один раз в 1-3 дня). Подключающиеся устройства будут просто нечисто разорваны, а затем они попытаются восстановить соединение с новым IP. Тем не менее, мой сервер не уведомляется об отключении и обычно должен прервать соединение. Однако, прежде чем сервер установит тайм-аут соединения, клиенту иногда удается восстановить соединение, и тогда сервер находится в состоянии с двумя очевидными соединениями одного и того же клиента. Поэтому обычно первое соединение - это то, которое я действительно хочу разорвать.
1 ответ
После того как вы определили идентификатор соединения, вы можете позвонить self.transport.pauseProducing()
на "новом" транспорте соединения, которое будет предотвращать любые уведомления, пока вы не позвоните self.transport.resumeProducing()
, Вы можете позвонить newConnection.transport.resumeProducing()
от oldConnection.connectionLost()
, если существует новое соединение.