I have been writing a discord.py bot, running on replit.com. I gotten to the music bot part after finishing the queue part. My code is logically correct; however, the code is way too inefficient causing the bot to crash when someone adds another song to the queue. How can I program my bot to be more efficient? If my code must be completely different, then a short explanation would be appreciated.

The code for play:

@bot.command(name='play', aliases=['sing', 'p'])
async def _play(ctx, url : str):
    queueurls = [] #list with the urls
    vc = ctx.voice_client
    if not vc:
      channel = ctx.author.voice.channel
      await channel.connect()
    url = ctx.message.content
    url = ttourl(url) #the message is processed to an url
    queueurls.append(url) #add the url to the list
    voicec = ctx.voice_client
    if not voicec.is_playing(): #when nothing is going on
      while queueurls != []: #as long as the url list isn't empty I want the process to repeat
        voice = discord.utils.get(bot.voice_clients, guild=ctx.guild)
        url = queueurls[0] #url is the first item in the list
        queueurls.pop(0) #now erase the now used first item (url)
        with youtube_dl.YoutubeDL(ytdlopts) as ydl:
          ydl.download([url]) #download the song
        voice.play(discord.FFmpegPCMAudio("songstemp/song.mp3")) #play the song
        vcs = ctx.voice_client
        while vcs.is_playing: #wait for the song to be over
        if os.path.exists("songstemp/song.mp3"):
          path = "songstemp/song.mp3"
    else: #if the bot is already playing, then don't disturb the loops above
  • \$\begingroup\$ Please can you include the entire traceback for the error you're getting. Having the traceback can help us identify the issue and increases the potential for you to get you the feedback you want. \$\endgroup\$
    – Peilonrayz
    May 12, 2021 at 15:30

1 Answer 1

  • Prefer four-space indentation instead of a mix of four and two
  • queueurls should be queue_urls
  • else / pass is redundant and can be deleted
  • It's not a great idea to use a single, statically-named temporary file for your playback. Instead, use tempfile to generate you a random one-off temporary filename. It's possible that the inefficiency you see is actually some kind of contention around your single filename.
  • while queueurls != [] is better-stated as while len(queue_urls) > 0.
  • while vcs.is_playing is a polling loop that's probably going to saturate your CPU. At the least, add a sleep(0.1) to the inside of your loop to release your thread from the OS scheduler. Better yet would be a blocking call to your audio library, though I don't know whether that's possible. Based on the documentation, you could wait until an after finalizer hook is called.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.