from typing import cast, Optional from googleapiclient.discovery import build as gapi_discovery_build from googleapiclient.errors import Error as GoogleApiError from edmond.plugin import Plugin from edmond.plugins.playlist_of_the_day import PlaylistOfTheDayPlugin class YoutubePlugin(Plugin): REQUIRED_CONFIGS = ["commands", "api_key"] VIDEO_URL_FMT = "https://www.youtube.com/watch?v={}" CHANNEL_URL_FMT = "https://www.youtube.com/channel/{}" PLAYLIST_URL_FMT = "https://www.youtube.com/playlist?list={}" def __init__(self, bot): super().__init__(bot) self._youtube = None self._playlist_of_the_day_plugin = None @property def youtube(self): if self._youtube is None: self._youtube = gapi_discovery_build( "youtube", "v3", developerKey=self.config["api_key"], ) return self._youtube @property def playlist_of_the_day_plugin(self) -> Optional[PlaylistOfTheDayPlugin]: if self._playlist_of_the_day_plugin is None: self._playlist_of_the_day_plugin = cast( PlaylistOfTheDayPlugin, self.bot.get_plugin("playlistoftheday"), ) return self._playlist_of_the_day_plugin def on_welcome(self, _): if not self.config["api_key"]: self.bot.log_w("Youtube API key unavailable.") self.is_ready = False def on_pubmsg(self, event): if self.should_handle_command(event.arguments[0]): self.handle_commands(event.target) return True return False def handle_commands(self, target): if self.command.ident != self.config["commands"][0]: return try: search_response = ( self.youtube.search() .list( q=self.command.content, part="id,snippet", maxResults=1, ) .execute() ) except GoogleApiError: self.signal_failure(target) return link = "" icon = "" title = "" for result in search_response.get("items", []): kind = result["id"]["kind"] if kind == "youtube#video": video_id = result["id"]["videoId"] link = self.VIDEO_URL_FMT.format(video_id) icon = "📼" elif kind == "youtube#channel": channel_id = result["id"]["channelId"] link = self.CHANNEL_URL_FMT.format(channel_id) icon = "📺" elif kind == "youtube#playlist": playlist_id = result["id"]["playlistId"] link = self.PLAYLIST_URL_FMT.format(playlist_id) icon = "➕" if link: title = result["snippet"]["title"] break else: self.signal_failure(target) return self.bot.say(target, f"{icon} {link} {title}") if self.playlist_of_the_day_plugin: self.playlist_of_the_day_plugin.add_line(f"{link} {title}")