Django channels: обновление базы данных удаляет старые данные из той же сессии на сокете

Я создаю игру tic tac toe, в которую можно играть онлайн, но я хотел сохранить счетчик побед/поражений каждого пользователя, и я использую django 3.2, channels 3 и channels_presence с python 3.9

Я успешно собрал сокет и клиент, и теперь вы можете играть столько игр, сколько захотите... Я думаю

Проблема заключается в том, что счет, который я пытаюсь сохранить, сохраняется в базе данных, но после очередной игры счет возвращается к нулю

так, если два пользователя играют в комнате и пользователь 1 выиграл 2 игры, счет будет обновлен, тогда если другой пользователь выиграет игру, его счет будет равен 1, а счет пользователя 1 будет сброшен на ноль

Моя модель пользователя

class CustomUser(AbstractUser):
    won_games = models.IntegerField(default=0)
    lost_games = models.IntegerField(default=0)
    draw_games = models.IntegerField(default=0)

    def win(self):
        self.won_games += 1
        self.save() 

    def lose(self):
        self.lost_games += 1
        self.save() 

    def draw(self):
        self.draw_games += 1
        self.save() 

Я поместил это в функцию receive в моем consumers.py

class GameConsumer(WebsocketConsumer):
    #some code
    def receive(self, text_data):

        if text_data['type'] == 'completed':
            self_channel = Presence.objects.get(channel_name=self.channel_name)
            competitor = self_channel.room.presence_set.filter(
                                    ~Q(channel_name=self_channel)
                                   ).first().user
            user = self.scope['user']
            if competitor:
                competitor.win()
            if user.is_authenticated:
                user.lose()
    return

**Примечание: **Я полагаюсь на сообщение другого пользователя для подтверждения выигрыша, чтобы никто не мог послать фальшивые выигрыши на сокет

Я пытался удалить всех пользователей из базы данных, перенести базу данных, изменить способ изменения свойства won_games, как вы можете видеть, но проблема в том, что оно возвращается к умолчанию после проигрыша

Если вы можете помочь мне, вот полный исходный код https://github.com/ahmedyasserays/XO-online

Я исправил это, проблема была в части user = self.scope['user']. Как вы сейчас говорите, при инициировании соединения с потребителем в памяти создается новый экземпляр потребителя из вашего класса с некоторыми атрибутами, как это self.scope обновление базы данных новыми данными при получении от другого экземпляра не влияет на все экземпляры, вместо этого у других экземпляров все еще будут объекты, которые еще не обновили свои данные, в нашем случае это self.scope['user'], которые все еще будут иметь старые значения won_games, которые переопределят обновленные значения, когда мы попытаемся сохранить его, поэтому исправление заключается в том, чтобы просто добавить user = CustomUser.objects.get(id=user.id) перед применением метода user.lose()

Вернуться на верх