Skip to content

Instantly share code, notes, and snippets.

@swarley
Last active March 19, 2019 15:25
Show Gist options
  • Save swarley/e4ad2cfeb4a15d9374ece820372e95cf to your computer and use it in GitHub Desktop.
Save swarley/e4ad2cfeb4a15d9374ece820372e95cf to your computer and use it in GitHub Desktop.
A YouTube example container for discordrb
# frozen_string_literal: true
# Use `bot.include! YouTubeContainer` to use this in your CommandBot
# This requires you to have youtube-dl installed as well as other voice prerequisites.
#
# This example is extremely slow, but could potentially be sped up if the youtube-dl
# `-o -` option actually worked. If you can get it to work, hit me up because other people's
# older examples always fail when I run them locally.
require 'discordrb'
module YouTubeContainer
extend Discordrb::Commands::CommandContainer
# This regex is used to validate that we're actually trying to play a video
# The base regex, before I made it non capturing, is from this stack overflow answer
# https://stackoverflow.com/a/41029451
YOUTUBE_URL = /^(?:http(s)??\:\/\/)?(?:www\.)?(?:(?:youtube\.com\/watch\?v=)|(?:youtu.be\/))(?:[a-zA-Z0-9\-_])+/
YOUTUBE_DL_OPTIONS = '--no-playlist --extract-audio --max-filesize 50M --audio-format vorbis'
command :yt do |event, url|
unless url =~ YOUTUBE_URL
return 'This is not a valid youtube url'
end
unless event.author.voice_channel
return 'You must be in a voice channel to use this command'
end
voice_bot = event.bot.voice(event.server)
voice_bot ||= event.bot.voice_connect(event.author.voice_channel)
Dir.mktmpdir("#{event.server.id}-yt") do |dir|
result = `youtube-dl #{YOUTUBE_DL_OPTIONS} -o \"#{dir}/%(title)s.%(ext)s\" #{url}`
title = `youtube-dl --get-filename -o \"%(title)s\" #{url}`.chomp
return 'There was an issue downloading this song' unless title
event.send_embed do |embed|
embed.title = 'YouTube'
embed.description = title
end
10.times { sleep 1 unless File.exist? "#{dir}/#{title}.ogg" }
voice_bot.play_file("#{dir}/#{title}.ogg")
end
voice_bot.destroy
nil
end
command :yt_stop do |event|
voice = event.bot.voice(event.server)
return 'Nothing is playing' unless voice
voice.stop_playing
voice.destroy
nil
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment