code cleanup

This commit is contained in:
vveeps 2021-10-28 17:23:48 +03:00
parent df9ae54e6c
commit 7fda302a31
7 changed files with 106 additions and 125 deletions

View File

@ -1,7 +1,7 @@
"""Pomice wrapper for Lavalink, made possible by cloudwithax 2021"""
import discord
if discord.__version__ != '2.0.0a':
if discord.__version__ != "2.0.0a":
class DiscordPyOutdated(Exception):
pass
@ -22,4 +22,3 @@ from .filters import *
from .objects import *
from .player import Player
from .pool import *

View File

@ -3,14 +3,17 @@ from enum import Enum
class SearchType(Enum):
"""The enum for the different search types for Pomice.
This feature is exclusively for the Spotify search feature of Pomice.
If you are not using this feature, this class is not necessary.
This feature is exclusively for the Spotify search feature of Pomice.
If you are not using this feature, this class is not necessary.
SearchType.ytsearch searches using regular Youtube, which is best for all scenarios.
SearchType.ytsearch searches using regular Youtube,
which is best for all scenarios.
SearchType.ytmsearch searches using YouTube Music, which is best for getting audio-only results.
SearchType.ytmsearch searches using YouTube Music,
which is best for getting audio-only results.
SearchType.scsearch searches using SoundCloud, which is an alternative to YouTube or YouTube Music.
SearchType.scsearch searches using SoundCloud,
which is an alternative to YouTube or YouTube Music.
"""
ytsearch = "ytsearch"
ytmsearch = "ytmsearch"

View File

@ -1,6 +1,7 @@
from .pool import NodePool
from .utils import ClientType
class PomiceEvent:
"""The base class for all events dispatched by a node.
Every event must be formatted within your bot's code as a listener.
@ -49,12 +50,16 @@ class TrackEndEvent(PomiceEvent):
self.handler_args = self.player, self.track, self.reason
def __repr__(self) -> str:
return f"<Pomice.TrackEndEvent player={self.player} track_id={self.track.track_id} reason={self.reason}>"
return (
f"<Pomice.TrackEndEvent player={self.player} track_id={self.track.track_id} "
f"reason={self.reason}>"
)
class TrackStuckEvent(PomiceEvent):
"""Fired when a track is stuck and cannot be played. Returns the player
associated with the event along with the pomice.Track object to be further parsed by the end user.
associated with the event along with the pomice.Track object
to be further parsed by the end user.
"""
name = "track_stuck"
@ -100,6 +105,7 @@ class WebSocketClosedPayload:
return f"<Pomice.WebSocketClosedPayload guild={self.guild!r} code={self.code!r} " \
f"reason={self.reason!r} by_remote={self.by_remote!r}>"
class WebSocketClosedEvent(PomiceEvent):
"""Fired when a websocket connection to a node has been closed.
Returns the reason and the error code.

View File

@ -14,14 +14,14 @@ class Equalizer:
i.e: Applying a bass boost filter to emphasize the bass in a song.
The format for the levels is: List[Tuple[int, float]]
"""
def __init__(self, *, levels: list):
super().__init__()
self.eq = self._factory(self, levels)
self.raw = levels
self.payload = {'equalizer': {'bands': self.eq}}
self.payload = {"equalizer": {"bands": self.eq}}
def _factory(self, levels: list):
_dict = collections.defaultdict(int)

View File

@ -156,7 +156,7 @@ class Player(VoiceProtocol):
self.channel = self.guild.get_channel(int(channel_id))
if not data.get('token'):
if not data.get("token"):
return
await self._dispatch_voice_update({**self._voice_state, "event": data})
@ -274,7 +274,7 @@ class Player(VoiceProtocol):
return self._paused
async def set_volume(self, volume: int) -> int:
"""Sets the volume of the player as an integer. Lavalink accepts an amount from 0 to 500."""
"""Sets the volume of the player as an integer. Lavalink accepts values from 0 to 500."""
await self._node.send(op="volume", guildId=str(self.guild.id), volume=volume)
self._volume = volume
return self._volume

View File

@ -10,7 +10,6 @@ from typing import Dict, Optional, TYPE_CHECKING
from urllib.parse import quote
import aiohttp
import discord
from discord.ext import commands
from . import __version__, spotify
@ -21,9 +20,6 @@ from .exceptions import (
NodeCreationError,
NodeNotAvailable,
NoNodesAvailable,
SpotifyAlbumLoadFailed,
SpotifyPlaylistLoadFailed,
SpotifyTrackLoadFailed,
TrackLoadError
)
from .objects import Playlist, Track
@ -37,10 +33,12 @@ SPOTIFY_URL_REGEX = re.compile(
)
DISCORD_MP3_URL_REGEX = re.compile(
r"https?://cdn.discordapp.com/attachments/(?P<channel_id>[0-9]+)/(?P<message_id>[0-9]+)/(?P<file>[a-zA-Z0-9_.]+)+"
r"https?://cdn.discordapp.com/attachments/(?P<channel_id>[0-9]+)/"
r"(?P<message_id>[0-9]+)/(?P<file>[a-zA-Z0-9_.]+)+"
)
URL_REGEX = re.compile(
r'https?://(?:www\.)?.+'
r"https?://(?:www\.)?.+"
)
@ -205,7 +203,8 @@ class Node:
async def send(self, **data):
if not self._available:
raise NodeNotAvailable(
f"The node '{self.identifier}' is not currently available.")
f"The node '{self.identifier}' is unavailable."
)
await self._websocket.send_str(json.dumps(data))
@ -261,19 +260,19 @@ class Node:
Context object on the track it builds.
"""
async with self._session.get(f'{self._rest_uri}/decodetrack?',
headers={'Authorization': self._password},
params={'track': identifier}) as resp:
data: dict = await resp.json()
async with self._session.get(
f"{self._rest_uri}/decodetrack?",
headers={"Authorization": self._password},
params={"track": identifier}
) as resp:
if not resp.status == 200:
raise TrackLoadError(f'Failed to build track. Status: {data["status"]}, Error: {data["error"]}.'
f'Check the identifier is correct and try again.')
raise TrackLoadError(
f"Failed to build track. Check the identifier is correct and try again."
)
data: dict = await resp.json()
return Track(track_id=identifier, ctx=ctx, info=data)
async def get_tracks(
self,
query: str,
@ -303,70 +302,7 @@ class Node:
spotify_results = await self._spotify_client.search(query=query)
if isinstance(spotify_results, spotify.Playlist):
tracks = [
Track(
track_id=track.id,
ctx=ctx,
search_type=search_type,
spotify=True,
info={
"title": track.name,
"author": track.artists,
"length": track.length,
"identifier": track.id,
"uri": track.uri,
"isStream": False,
"isSeekable": False,
"position": 0,
"thumbnail": track.image
},
) for track in spotify_results.tracks
]
return Playlist(
playlist_info={"name": spotify_results.name, "selectedTrack": tracks[0]},
tracks=tracks,
ctx=ctx,
spotify=True,
thumbnail=spotify_results.image,
uri=spotify_results.uri,
)
elif isinstance(spotify_results, spotify.Album):
tracks = [
Track(
track_id=track.id,
ctx=ctx,
search_type=search_type,
spotify=True,
info={
"title": track.name,
"author": track.artists,
"length": track.length,
"identifier": track.id,
"uri": track.uri,
"isStream": False,
"isSeekable": False,
"position": 0,
"thumbnail": track.image
},
) for track in spotify_results.tracks
]
return Playlist(
playlist_info={"name": spotify_results.name, "selectedTrack": tracks[0]},
tracks=tracks,
ctx=ctx,
spotify=True,
thumbnail=spotify_results.image,
uri=spotify_results.uri,
)
elif isinstance(spotify_results, spotify.Track):
if isinstance(spotify_results, spotify.Track):
return [
Track(
track_id=spotify_results.id,
@ -383,10 +319,38 @@ class Node:
"isSeekable": False,
"position": 0,
"thumbnail": spotify_results.image
},
}
)
]
tracks = [
Track(
track_id=track.id,
ctx=ctx,
search_type=search_type,
spotify=True,
info={
"title": track.name,
"author": track.artists,
"length": track.length,
"identifier": track.id,
"uri": track.uri,
"isStream": False,
"isSeekable": False,
"position": 0,
"thumbnail": track.image
}
) for track in spotify_results.tracks
]
return Playlist(
playlist_info={"name": spotify_results.name, "selectedTrack": tracks[0]},
tracks=tracks,
ctx=ctx,
spotify=True,
thumbnail=spotify_results.image,
uri=spotify_results.uri
)
elif discord_url := DISCORD_MP3_URL_REGEX.match(query):
async with self._session.get(
@ -396,19 +360,22 @@ class Node:
data: dict = await response.json()
track: dict = data["tracks"][0]
info: dict = track.get('info')
info: dict = track.get("info")
return [Track(
track_id=track['track'],
info={
"title": discord_url.group('file'),
"author": "Unknown",
"length": info.get('length'),
"uri": info.get('uri'),
"position": info.get('position'),
"identifier": info.get('identifier')
},
ctx=ctx)]
return [
Track(
track_id=track["track"],
info={
"title": discord_url.group("file"),
"author": "Unknown",
"length": info.get("length"),
"uri": info.get("uri"),
"position": info.get("position"),
"identifier": info.get("identifier")
},
ctx=ctx
)
]
else:
async with self._session.get(
@ -471,9 +438,13 @@ class NodePool:
"""Fetches a node from the node pool using it's identifier.
If no identifier is provided, it will choose a node at random.
"""
available_nodes = {identifier: node for identifier, node in cls._nodes.items() if node._available}
available_nodes = {
identifier: node
for identifier, node in cls._nodes.items() if node._available
}
if not available_nodes:
raise NoNodesAvailable('There are no nodes available.')
raise NoNodesAvailable("There are no nodes available.")
if identifier is None:
return random.choice(list(available_nodes.values()))

View File

@ -26,9 +26,9 @@ from discord import AutoShardedClient, Client
from discord.ext.commands import AutoShardedBot, Bot
__all__ = [
'ExponentialBackoff',
'NodeStats',
'ClientType'
"ClientType",
"ExponentialBackoff",
"NodeStats"
]
ClientType = Union[AutoShardedBot, AutoShardedClient, Bot, Client]
@ -64,24 +64,26 @@ class ExponentialBackoff:
class NodeStats:
"""The base class for the node stats object. Gives critcical information on the node, which is updated every minute."""
"""The base class for the node stats object.
Gives critical information on the node, which is updated every minute.
"""
def __init__(self, data: dict) -> None:
memory = data.get('memory')
self.used = memory.get('used')
self.free = memory.get('free')
self.reservable = memory.get('reservable')
self.allocated = memory.get('allocated')
memory = data.get("memory")
self.used = memory.get("used")
self.free = memory.get("free")
self.reservable = memory.get("reservable")
self.allocated = memory.get("allocated")
cpu = data.get('cpu')
self.cpu_cores = cpu.get('cores')
self.cpu_system_load = cpu.get('systemLoad')
self.cpu_process_load = cpu.get('lavalinkLoad')
cpu = data.get("cpu")
self.cpu_cores = cpu.get("cores")
self.cpu_system_load = cpu.get("systemLoad")
self.cpu_process_load = cpu.get("lavalinkLoad")
self.players_active = data.get('playingPlayers')
self.players_total = data.get('players')
self.uptime = data.get('uptime')
self.players_active = data.get("playingPlayers")
self.players_total = data.get("players")
self.uptime = data.get("uptime")
def __repr__(self) -> str:
return f'<Pomice.NodeStats total_players={self.players_total!r} playing_active={self.players_active!r}>'
return f"<Pomice.NodeStats total_players={self.players_total!r} playing_active={self.players_active!r}>"