Как разорвать цикл while внутри функции, когда условие основано на вызове другой функции? - PullRequest
0 голосов
/ 25 июня 2019

Я использую клиент Signalr Core в Python: https://github.com/mandrewcito/signalrcore

Я использую пример чата из исходного кода git и изменил его для своего приложения.

Я пытаюсь поставитьцикл while в функции, где условие цикла while должно прерываться при вызове другой функции.Но он застревает в цикле while.

Вот мой код:

from signalrcore.hub_connection_builder import HubConnectionBuilder


def input_with_default(input_text, default_value):
    value = input(input_text.format(default_value))
    return default_value if value is None or value.strip() == "" else value

def start_msg(msg):
     while end_event.has_been_called == False:        
          Print("Starting")
          sleep(1)

def end_event(endmsg):
     end_event.has_been_called = True
     pass    
     print("End Event")


server_url = input_with_default('Enter your server url(default: {0}): ', "ws://localhost:62342/chathub")
username = input_with_default('Enter your username (default: {0}): ', "sam")

hub_connection = HubConnectionBuilder().with_url(server_url).with_automatic_reconnect({
        "type": "raw",
        "keep_alive_interval": 10,
        "reconnect_interval": 5,
        "max_attempts": 5
    }).build()
end_event.has_been_called = False
hub_connection.on("StartEvent", start_msg)
hub_connection.on("EndEvent", end_event)
hub_connection.start()
message = None
# Do login

while message != "exit()":
    message = input(">> ")
    if message is not None and message is not "" and message is not "exit()":
        hub_connection.send("SendMessage", [username, message])
hub_connection.stop()

В этом коде, когда он получает сообщение с StartEvent, он переходит в функцию start_msg и начинает печатать "Начало ", но как только получено EndEvent, оно должно перейти к функции end_event, но оно просто застревает в цикле while и никогда не выходит из него.

Если я удаляю цикл while, тогда он работает нормально, но янужно, чтобы он оставался в цикле while внутри start_msg до тех пор, пока не будет вызван end_event.

Как мне этого добиться?

Редактировать: Просто чтобы уточнить, я имею в виду это времяцикл:

def start_msg(msg):
 while end_event.has_been_called == False:        
      Print("Starting")
      sleep(1)

1 Ответ

0 голосов
/ 25 июня 2019

Во-первых, я бы обратился к вашему утверждению if

Вместо того, чтобы усложнять ваше утверждение if, присвойте список

conditions = [None, "", "exit()"]

Затем вы можете выполнить

if message not in conditions:

Что позволит вам расширить ваши условия, если потребуется.Также немного более элегантный IMO

Во-вторых, я бы сделал это классом.end_event.has_been_called присваивает атрибуту функцию, которая является странной.

Наконец, ваше стартовое событие должно вызывать ваше конечное событие.Если этот модуль не работает как-то асинхронно (я не установил его), вы никогда не получите вызов функции end_event, поэтому вы застряли в цикле.Надеюсь, это поможет

from signalrcore.hub_connection_builder import HubConnectionBuilder

class Event_Handler:

    def __init__(self):
        self.conditions = [None, "", "exit()"]
        self.end_call = False

    def input_with_default(self, input_text, default_value):
        value = input(input_text.format(default_value))
        return default_value if value is None or value.strip() == "" else value

    def start_msg(self, msg):
         while self.end_call == False:
              print("Starting")
              self.end_event('Ending')
              sleep(1)

    def end_event(self, endmsg):
         self.end_call = True
         pass
         print("End Event")

    def run_server(self):
        server_url = input_with_default('Enter your server url(default: {0}): ', "ws://localhost:62342/chathub")
        username = input_with_default('Enter your username (default: {0}): ', "sam")

        hub_connection = HubConnectionBuilder().with_url(server_url).with_automatic_reconnect({
                "type": "raw",
                "keep_alive_interval": 10,
                "reconnect_interval": 5,
                "max_attempts": 5
            }).build()
        self.end_call = False
        hub_connection.on("StartEvent", start_msg)
        hub_connection.on("EndEvent", end_event)
        hub_connection.start()
        message = None
        # Do login

        while message != "exit()":
            message = input(">> ")
            if message not in self.conditions:
                hub_connection.send("SendMessage", [username, message])
        hub_connection.stop()
...