pomice/FEATURES.md

624 lines
15 KiB
Markdown

# Pomice Advanced Features Guide
## 🎉 Overview
This guide covers the advanced features added to Pomice to enhance your music bot capabilities. These features include track history, queue statistics, playlist management, and advanced track utilities.
### What's New
- **Track History**: Keep track of previously played songs with navigation and search
- **Queue Statistics**: Detailed analytics about queue contents (duration, requesters, etc.)
- **Playlist Manager**: Export/import playlists to JSON and M3U formats
- **Track Utilities**: Advanced filtering, searching, and sorting capabilities
All features are **fully backward compatible** and **optional** - use what you need!
---
## 📚 Table of Contents
1. [Track History](#-track-history)
2. [Queue Statistics](#-queue-statistics)
3. [Playlist Manager](#-playlist-manager)
4. [Track Utilities](#-track-utilities)
5. [Complete Examples](#-complete-examples)
6. [Quick Reference](#-quick-reference)
---
## 🕐 Track History
Keep track of previously played songs with navigation and search capabilities.
### Features
- Configurable maximum history size
- Navigation (previous/next)
- Search through history
- Filter by requester
- Get unique tracks (remove duplicates)
### Basic Usage
```python
import pomice
# Create a history tracker
history = pomice.TrackHistory(max_size=100)
# Add tracks as they play
history.add(track)
# Get last 10 played tracks
recent = history.get_last(10)
# Search history
results = history.search("Imagine Dragons")
# Get tracks by specific user
user_tracks = history.get_by_requester(user_id=123456789)
# Navigate through history
previous_track = history.get_previous()
next_track = history.get_next()
# Get all unique tracks (removes duplicates)
unique = history.get_unique_tracks()
# Clear history
history.clear()
```
### Properties
- `is_empty` - Check if history is empty
- `current` - Get current track in navigation
### Use Cases
- "What was that song that just played?"
- "Show me the last 10 songs"
- "Play the previous track"
- "Show all songs requested by User X"
---
## 📊 Queue Statistics
Get detailed analytics about your queue contents.
### Features
- Total and average duration
- Longest/shortest tracks
- Requester statistics
- Author distribution
- Duration breakdown
- Stream detection
- Playlist distribution
### Basic Usage
```python
import pomice
# Create stats for a queue
stats = pomice.QueueStats(player.queue)
# Get total duration
total_ms = stats.total_duration
formatted = stats.format_duration(total_ms) # "1:23:45"
# Get average duration
avg_ms = stats.average_duration
# Find longest and shortest tracks
longest = stats.longest_track
shortest = stats.shortest_track
# Get requester statistics
requester_stats = stats.get_requester_stats()
# Returns: {user_id: {'count': 5, 'total_duration': 900000, 'tracks': [...]}}
# Get top requesters
top_requesters = stats.get_top_requesters(limit=5)
# Returns: [(requester, count), ...]
# Get author distribution
authors = stats.get_author_distribution()
# Returns: {'Artist Name': track_count, ...}
# Get top authors
top_authors = stats.get_top_authors(limit=10)
# Returns: [('Artist Name', count), ...]
# Get duration breakdown
breakdown = stats.get_duration_breakdown()
# Returns: {'short': 10, 'medium': 25, 'long': 5, 'very_long': 2}
# Get stream count
streams = stats.get_stream_count()
# Get comprehensive summary
summary = stats.get_summary()
```
### Summary Dictionary
```python
{
'total_tracks': 42,
'total_duration': 7200000, # milliseconds
'total_duration_formatted': '2:00:00',
'average_duration': 171428.57,
'average_duration_formatted': '2:51',
'longest_track': Track(...),
'shortest_track': Track(...),
'stream_count': 3,
'unique_authors': 15,
'unique_requesters': 5,
'duration_breakdown': {...},
'loop_mode': LoopMode.QUEUE,
'is_looping': True
}
```
### Use Cases
- "How long is the queue?"
- "Who added the most songs?"
- "What's the longest track?"
- "Show me queue statistics"
---
## 💾 Playlist Manager
Export and import playlists to/from JSON and M3U formats.
### Features
- Export queue to JSON
- Import playlists from JSON
- Export to M3U format
- Merge multiple playlists
- Remove duplicates
- Playlist metadata
### Export Queue
```python
import pomice
# Export current queue
pomice.PlaylistManager.export_queue(
player.queue,
filepath='playlists/my_playlist.json',
name='My Awesome Playlist',
description='Best songs ever',
include_metadata=True # Include requester info
)
```
### Import Playlist
```python
# Import playlist data
data = pomice.PlaylistManager.import_playlist('playlists/my_playlist.json')
# Get just the URIs
uris = pomice.PlaylistManager.get_track_uris('playlists/my_playlist.json')
# Load tracks into queue
for uri in uris:
results = await player.get_tracks(query=uri)
if results:
await player.queue.put(results[0])
```
### Export Track List
```python
# Export a list of tracks (not from queue)
tracks = [track1, track2, track3]
pomice.PlaylistManager.export_track_list(
tracks,
filepath='playlists/favorites.json',
name='Favorites',
description='My favorite tracks'
)
```
### Merge Playlists
```python
# Merge multiple playlists into one
pomice.PlaylistManager.merge_playlists(
filepaths=['playlist1.json', 'playlist2.json', 'playlist3.json'],
output_path='merged_playlist.json',
name='Mega Playlist',
remove_duplicates=True # Remove duplicate tracks
)
```
### Export to M3U
```python
# Export to M3U format (compatible with many players)
tracks = list(player.queue)
pomice.PlaylistManager.export_to_m3u(
tracks,
filepath='playlists/my_playlist.m3u',
name='My Playlist'
)
```
### Get Playlist Info
```python
# Get metadata without loading all tracks
info = pomice.PlaylistManager.get_playlist_info('playlists/my_playlist.json')
# Returns: {'name': '...', 'track_count': 42, 'total_duration': 7200000, ...}
```
### JSON Format
```json
{
"name": "My Playlist",
"description": "Best songs",
"created_at": "2024-01-15T12:30:00",
"track_count": 10,
"total_duration": 1800000,
"version": "1.0",
"tracks": [
{
"title": "Song Title",
"author": "Artist Name",
"uri": "https://...",
"identifier": "abc123",
"length": 180000,
"thumbnail": "https://...",
"isrc": "USRC12345678",
"requester_id": 123456789,
"requester_name": "User#1234"
}
]
}
```
### Use Cases
- "Save this queue for later"
- "Load my favorite playlist"
- "Merge all my playlists"
- "Export to M3U for my media player"
---
## 🔧 Track Utilities
Advanced filtering, searching, and sorting utilities for tracks.
### TrackFilter
Filter tracks by various criteria.
```python
import pomice
tracks = list(player.queue)
# Filter by duration (milliseconds)
short_tracks = pomice.TrackFilter.by_duration(
tracks,
min_duration=60000, # 1 minute
max_duration=300000 # 5 minutes
)
# Filter by author
artist_tracks = pomice.TrackFilter.by_author(
tracks,
author='Imagine Dragons',
exact=False # Case-insensitive contains
)
# Filter by title
title_tracks = pomice.TrackFilter.by_title(
tracks,
title='Thunder',
exact=True # Exact match
)
# Filter by requester
user_tracks = pomice.TrackFilter.by_requester(tracks, requester_id=123456789)
# Filter by playlist
playlist_tracks = pomice.TrackFilter.by_playlist(tracks, playlist_name='Rock Hits')
# Get only streams
streams = pomice.TrackFilter.streams_only(tracks)
# Get only non-streams
non_streams = pomice.TrackFilter.non_streams_only(tracks)
# Custom filter with lambda
long_tracks = pomice.TrackFilter.custom(
tracks,
predicate=lambda t: t.length > 600000 # > 10 minutes
)
```
### SearchHelper
Search, sort, and organize tracks.
```python
import pomice
tracks = list(player.queue)
# Search tracks
results = pomice.SearchHelper.search_tracks(
tracks,
query='imagine',
search_title=True,
search_author=True,
case_sensitive=False
)
# Sort by duration
sorted_tracks = pomice.SearchHelper.sort_by_duration(
tracks,
reverse=True # Longest first
)
# Sort by title (alphabetically)
sorted_tracks = pomice.SearchHelper.sort_by_title(tracks)
# Sort by author
sorted_tracks = pomice.SearchHelper.sort_by_author(tracks)
# Remove duplicates
unique_tracks = pomice.SearchHelper.remove_duplicates(
tracks,
by_uri=True, # Remove by URI
by_title_author=False # Or by title+author combo
)
# Group by author
grouped = pomice.SearchHelper.group_by_author(tracks)
# Returns: {'Artist Name': [track1, track2, ...], ...}
# Group by playlist
grouped = pomice.SearchHelper.group_by_playlist(tracks)
# Get random tracks
random_tracks = pomice.SearchHelper.get_random_tracks(tracks, count=5)
```
### Use Cases
- "Show me all songs by Artist X"
- "Find tracks between 3-5 minutes"
- "Sort queue by duration"
- "Remove duplicate songs"
- "Play 5 random tracks"
---
## 🎯 Complete Examples
### Example 1: Basic Music Bot with History
```python
import pomice
from discord.ext import commands
class Music(commands.Cog):
def __init__(self, bot):
self.bot = bot
self.history = pomice.TrackHistory(max_size=100)
@commands.Cog.listener()
async def on_pomice_track_end(self, player, track, _):
# Add to history when track ends
self.history.add(track)
@commands.command()
async def history(self, ctx, limit: int = 10):
"""Show recently played tracks."""
recent = self.history.get_last(limit)
tracks_list = '\n'.join(
f"{i}. {track.title} by {track.author}"
for i, track in enumerate(recent, 1)
)
await ctx.send(f"**Recently Played:**\n{tracks_list}")
```
### Example 2: Queue Statistics Command
```python
@commands.command()
async def stats(self, ctx):
"""Show queue statistics."""
player = ctx.voice_client
stats = pomice.QueueStats(player.queue)
summary = stats.get_summary()
embed = discord.Embed(title='📊 Queue Statistics', color=discord.Color.green())
embed.add_field(name='Total Tracks', value=summary['total_tracks'], inline=True)
embed.add_field(name='Total Duration', value=summary['total_duration_formatted'], inline=True)
embed.add_field(name='Average Duration', value=summary['average_duration_formatted'], inline=True)
if summary['longest_track']:
embed.add_field(
name='Longest Track',
value=f"{summary['longest_track'].title} ({stats.format_duration(summary['longest_track'].length)})",
inline=False
)
# Top requesters
top_requesters = stats.get_top_requesters(3)
if top_requesters:
requesters_text = '\n'.join(
f'{i}. {req.display_name}: {count} tracks'
for i, (req, count) in enumerate(top_requesters, 1)
)
embed.add_field(name='Top Requesters', value=requesters_text, inline=False)
await ctx.send(embed=embed)
```
### Example 3: Export/Import Playlists
```python
@commands.command()
async def export(self, ctx, filename: str = 'playlist.json'):
"""Export current queue to a file."""
player = ctx.voice_client
pomice.PlaylistManager.export_queue(
player.queue,
f'playlists/{filename}',
name=f"{ctx.guild.name}'s Playlist",
description=f'Exported from {ctx.guild.name}'
)
await ctx.send(f'✅ Queue exported to `playlists/{filename}`')
@commands.command()
async def import_playlist(self, ctx, filename: str):
"""Import a playlist from a file."""
player = ctx.voice_client
data = pomice.PlaylistManager.import_playlist(f'playlists/{filename}')
uris = [track['uri'] for track in data['tracks'] if track.get('uri')]
added = 0
for uri in uris:
results = await player.get_tracks(query=uri, ctx=ctx)
if results:
await player.queue.put(results[0])
added += 1
await ctx.send(f'✅ Imported {added} tracks from `{data["name"]}`')
```
### Example 4: Filter and Sort Queue
```python
@commands.command()
async def filter_short(self, ctx):
"""Show tracks shorter than 3 minutes."""
player = ctx.voice_client
tracks = list(player.queue)
short_tracks = pomice.TrackFilter.by_duration(
tracks,
max_duration=180000 # 3 minutes in ms
)
await ctx.send(f'Found {len(short_tracks)} tracks under 3 minutes!')
@commands.command()
async def sort_queue(self, ctx, sort_by: str = 'duration'):
"""Sort the queue by duration, title, or author."""
player = ctx.voice_client
queue_tracks = list(player.queue)
if sort_by == 'duration':
sorted_tracks = pomice.SearchHelper.sort_by_duration(queue_tracks)
elif sort_by == 'title':
sorted_tracks = pomice.SearchHelper.sort_by_title(queue_tracks)
elif sort_by == 'author':
sorted_tracks = pomice.SearchHelper.sort_by_author(queue_tracks)
else:
return await ctx.send('Valid options: duration, title, author')
# Clear and refill queue
player.queue._queue.clear()
for track in sorted_tracks:
await player.queue.put(track)
await ctx.send(f'✅ Queue sorted by {sort_by}')
```
---
## 📖 Quick Reference
### Track History
```python
history = pomice.TrackHistory(max_size=100)
history.add(track)
recent = history.get_last(10)
results = history.search("query")
previous = history.get_previous()
unique = history.get_unique_tracks()
```
### Queue Statistics
```python
stats = pomice.QueueStats(queue)
total = stats.total_duration
formatted = stats.format_duration(total)
top_users = stats.get_top_requesters(5)
summary = stats.get_summary()
```
### Playlist Manager
```python
# Export
pomice.PlaylistManager.export_queue(queue, 'playlist.json')
# Import
data = pomice.PlaylistManager.import_playlist('playlist.json')
# Merge
pomice.PlaylistManager.merge_playlists(['p1.json', 'p2.json'], 'merged.json')
# M3U
pomice.PlaylistManager.export_to_m3u(tracks, 'playlist.m3u')
```
### Track Utilities
```python
# Filter
short = pomice.TrackFilter.by_duration(tracks, max_duration=180000)
artist = pomice.TrackFilter.by_author(tracks, "Artist Name")
# Search & Sort
results = pomice.SearchHelper.search_tracks(tracks, "query")
sorted_tracks = pomice.SearchHelper.sort_by_duration(tracks)
unique = pomice.SearchHelper.remove_duplicates(tracks)
random = pomice.SearchHelper.get_random_tracks(tracks, 5)
```
---
## 📝 Notes
- All duration values are in **milliseconds**
- History should be maintained per-guild
- Exported playlists are in JSON format by default
- M3U export is compatible with most media players
- All utilities work with standard Pomice Track objects
---
## 🚀 Getting Started
1. **Import the features you need**:
```python
import pomice
```
2. **Use them in your commands**:
```python
history = pomice.TrackHistory()
stats = pomice.QueueStats(player.queue)
```
3. **Check the examples** in `examples/advanced_features.py` for a complete bot
4. **Experiment** and customize to fit your needs!
---
## 🎓 Additional Resources
- **Full Example Bot**: See `examples/advanced_features.py`
- **Main Documentation**: See the main Pomice README
- **Discord Support**: Join the Pomice Discord server
---
**Happy coding! 🎵**