Задать вопрос
@Nikitonz
начинающий прогер в сфере бэкэнда

Я не могу решить вопрос с асинхронным выполнением кода. Оптимальное решение?

Взгляните на этот кусок кода:
def play_next(self):

        if len(self.music_queue) > 0:

            self.voice_client.stop()

            FFMPEG_OPTIONS = {'before_options': '-reconnect 1 -reconnect_streamed 1 -reconnect_delay_max 5',
                              'options': '-vn'}
            self.is_playing = True

            track_name, url = self.music_queue[0]['title'], self.music_queue[0]['url']

            if self.embed.fields.__len__() == 0:
                self.embed.add_field(name="Playing now", value=track_name, inline=True)
            else:
                self.embed.set_field_at(index=0, name="Playing now", value=track_name, inline=True)

            self.music_queue.pop(0)

            if self.music_queue.__len__() > 0:
                self.que_fetch()
            else:
                self.embed.remove_field(1)
                self.next_track.disabled = True
            try:

                self.voice_client.play(disnake.FFmpegPCMAudio(source=url, **FFMPEG_OPTIONS,
                                                              executable=r"dependencies\FFMPEG\bin\ffmpeg.exe"),
                                       after=lambda e: print('Player error: %s' % e) if e else self.play_next())
            except disnake.ClientException as e:
                print("already playing aud")
            except Exception as e:
                print(e)
        else:
            self.issent_control_message = False
            self.voice_client.stop()
            self.is_playing = False
            self.message.delete()<b># must be awaited</b>
            self.voice_client.disconnect()<b># must be awaited</b>
            return


здесь необходимо выполнить 2 асинхронных метода внутри синхронной функции. Асинхронной сделать play_next недопустимо, ввиду потоконебезопасности (эта статья тык), а так же невозможности запихнуть корутину (coroutine) внутрь after=... внутри voice_client.play(), так как там недопустимы асинхронники.

Таким образом, необходимо как-то использовать асинхронные методы внутри синхронной функции, и я хз как.

Помогите...

Бонус:

обеспечить паузу в 2 секунды между self.voice_client.stop() и self.voice_client.play(...). Примечание: asyncio.sleep(20) не помог, почему, так же не понял
  • Вопрос задан
  • 431 просмотр
Подписаться 3 Простой Комментировать
Пригласить эксперта
Ответы на вопрос 1
fenrir1121
@fenrir1121
Начни с документации
эта статья тык

Вам внутри вашего же примера дан нужный код
def my_after(error):
    coro = some_channel.send('Song is done!')
    fut = asyncio.run_coroutine_threadsafe(coro, client.loop)
    try:
        fut.result()
    except:
        # an error happened sending the message
        pass

coro - асинхронная функция
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы