Skip to content

mrazza/smoc

Repository files navigation

SMoC

Steaming Music on Console

License .NET Status

A terminal-based music player (TUI) for streaming services, currently supporting Subsonic-compatible APIs and YouTube Music. Spotify, Apple Music, and other services are future features.

FeaturesInstallationConfiguration and SetupUsage

screenshot


Note

This project is not supported or endorsed by any streaming music service or major company. It is a hobby project and has no affiliation with Spotify, Apple, Google, or YouTube. The same warnings and disclaimers for the well-known yt-dlp project apply here.

🌟 Features

  • TUI Interface: Built with Terminal.Gui for a rich console experience.
  • Cross-Platform Audio: Powered by SoundFlow.
  • YouTube Music Integration: Powered by YouTubeMusicAPI. Search, stream, and manage your library.
  • Subsonic API Integration: Streaming client for any Subsonic-compatible server. For instance, Navidrome, Airsonic Advanced, Gonic, or Madsonic.
  • Visuals: Displays album art using Sixel graphics (requires a compatible terminal).

Feature Progress

While most basic functionality is available and SMoC is totally usable, there's a lot left to do.

Feature Plan (Click to expand)
  • UI
    • Search Support
    • Command Bar
    • Song Table
    • Now Playing Bar
    • Album Art (Sixel)
    • Status Bar
    • Visualizations
    • Now Playing Screen
  • Playback
    • Play
    • Pause
    • Stop
    • Skip
    • Previous
    • Start Over
    • Repeat Track
    • Volume
    • Playback Device Selection
    • Gapless Playback
  • Queue
    • Add to End of Queue
    • Queue Next (after current song)
    • Remove
    • Advance to Next at End of Song
    • Repeat Queue
    • Shuffle
  • Search
    • Artist
    • Track
    • Playlist
    • URL
  • YouTube Music
    • Authentication
    • POToken
    • VisitorData
    • Metadata
    • Searching
    • Play Audio Stream
    • Album Art
    • Caching
    • History Tracking
    • Like
    • Dislike
  • Subsonic API-compatible Servers
    • Authentication
    • Metadata
    • Searching
    • Play Audio Stream
    • Album Art
    • Caching
    • History Tracking
    • Like
    • Dislike
  • Apple Music (gamdl as a reference)
    • Authentication
    • Play Audio Stream
    • Metadata
    • Searching
    • Play Audio Stream
    • Album Art
    • Caching
    • History Tracking
    • Like
    • Dislike
  • Spotify (librespot as a reference)
    • Authentication
    • Play Audio Stream
    • Metadata
    • Searching
    • Play Audio Stream
    • Album Art
    • Caching
    • History Tracking
    • Like
    • Dislike

🚀 Installation

Once installed some setup is required to use SMoC. See the Configuration and Setup section for more information.

Binary Release (Windows/Linux/MacOS)

Current release is v0.1.0.

Available for Windows x64, Linux x64, and MacOS ARM64.

Gentoo via Portage

SMoC is available via my overlay. To install, add my overlay and emerge it.

eselect repository add razza git https://github.com/mrazza/razza-overlay.git
emerge media-sound/smoc

Building from Source

# Clone the repository
git clone https://github.com/mrazza/smoc.git
cd smoc

# Build and run
dotnet run --project smoc/smoc.csproj

🎮 Usage

SMoC operates with a Vim-style command bar. Press : to enter command mode.

Navigation & Commands

Command Description
:a Switch to Artist mode
:a/<artist> Switch to Artist mode and search for <artist>
:t Switch to Track mode
:t/<track> Switch to Track mode and search for <track>
:p Switch to Playlist mode
:p/<playlist> Switch to Playlist mode and search for <playlist>
:likes Load your Liked Songs playlist
:url Switch to Playlist mode from URL
:url/<url> Load songs from a specific YouTube Music URL
:pq View the Playback Queue
:np View Now Playing screen
:v/<0-100> Set volume (e.g., :v/80)
:q Quit application

Playback Controls

Hotkey Action
Space Play / Pause
Ctrl+Space Stop
, (Comma) Previous Track (Restart if > 10s played)
. (Period) Next Track
[ Seek Backward 10s
] Seek Forward 10s
Up/Down/Left/Right Navigate Tables
h/j/k/l Navigate Tables (Vim style)
Tab Switch active pane
Enter Open action menu for selected item

⚙️ Configuration and Setup

SMoC stores configuration and authentication data in ~/.config/smoc/ (on Linux).

Subsonic

To use a Subsonic-compatible service (like Navidrome, Gonic, or Airsonic):

  1. Ensure your server has the Subsonic API enabled.
  2. Configure your server hostname, port, scheme, username, and password in config.json (see below).
  3. Set SmocConfiguration.ActiveService to Subsonic.

YouTube Music

To use YouTube Music:

  1. Set SmocConfiguration.ActiveService to YouTubeMusic.
  2. Setup required settings for YouTube Music authentication (see below).

Authentication

Note

You need a YouTube Music Premium subscription to play most content.

To access your YouTube Music account, you need to extract your cookies from YouTube Music (these steps are copied from YouTube.js):

  1. Open YouTube Music in your browser (Incognito recommended).
  2. Open Developer Tools (F12) -> Network tab.
  3. Find a POST request to music.youtube.com.
  4. Copy the value of the cookie request header.
  5. Save it to ~/.config/smoc/cookie.txt.

Tip

It is recommended to open an incognito window or separate browser profile when getting your cookie information to avoid other browser sessions from invalidating the tokens. Once cookies are retrieved, close the session without logging out.

More recently, additional tokens beyond just cookies are often needed. POToken and Visitor Data are required in the tokens.json file in the same directory as your cookie.txt.

Tip

Run smoc --gentokens after setting up the cookie to generate necessary PO Tokens and Visitor Data automatically.

Config File

Create or edit ~/.config/smoc/config.json to customize settings.

Example Configuration (Click to expand)
{
    "SmocConfiguration.LogLevel": "Warning",
    "SmocConfiguration.SongCacheSizeBytes": 1073741824,
    "SmocConfiguration.AlbumCoverCacheSizeBytes": 1073741824,
    "SmocConfiguration.SongCacheMaxElements": 1000,
    "SmocConfiguration.AlbumCoverCacheMaxElements": 1000,
    "SmocConfiguration.ActiveService": "Subsonic",
	"SubsonicConfig.ServerHost": "localhost",
	"SubsonicConfig.ServerPort": 8080,
	"SubsonicConfig.Username": "username",
	"SubsonicConfig.Password": "password",
    "Theme": "gruvbox-custom",
    "Themes": [
        {
            "gruvbox-custom": {
                "Schemes": [
                    {
                        "Accent": {
                            "Normal": { "Foreground": "#ebdbb2", "Background": "#00000000" },
                            "Focus": { "Foreground": "#ebdbb2", "Background": "#639494" },
                            "Active": { "Foreground": "#ebdbb2", "Background": "#394e4e" }
                        }
                    }
                    // ... (other schemes)
                ]
            }
        }
    ]
}

Common Settings

Category Key Type Description
Streaming SmocConfiguration.ActiveService StreamingService Active service (YouTubeMusic, Subsonic)
Subsonic SubsonicConfig.ServerScheme string URI Scheme for the Subsonic API (default: http)
SubsonicConfig.ServerHost string Hostname of your Subsonic server
SubsonicConfig.ServerPort int Port of your Subsonic server (default: 80)
SubsonicConfig.Username string Subsonic username
SubsonicConfig.Password string Subsonic password
SubsonicConfig.UseToken bool Whether to use token auth instead of plaintext password (default: true)
Caching SmocConfiguration.SongCacheSizeBytes long Max size of song cache in bytes (0 = no limit)
SmocConfiguration.AlbumCoverCacheSizeBytes long Max size of album cover cache in bytes (0 = no limit)
SmocConfiguration.SongCacheMaxElements int Max number of songs to cache (0 = no limit)
SmocConfiguration.AlbumCoverCacheMaxElements int Max number of album covers to cache (0 = no limit)
Logging SmocConfiguration.LogLevel LogLevel Min log level (Trace, Debug, Information, Warning, Error, Critical)
Listen History ListenHistory.Enabled bool Whether listen history tracking is enabled
ListenHistory.MinimumPositionSeconds int Minimum position (seconds) to consider listened
ListenHistory.MinimumFraction double Minimum fraction of a song to consider listened
UI Theme string The name of the theme to use (default: default)

Custom Themes

If specifying a custom theme (as in the example config above), you will need to specify styling for all schemes.

Example Theme (Click to expand)
{
    "Theme": "gruvbox-custom",
    "Themes": [
        {
            "gruvbox-custom": {
                "Schemes": [
                    {
                        "Accent": {
                            "Normal": {
                                "Foreground": "#ebdbb2",
                                "Background": "#00000000"
                            },
                            "Focus": {
                                "Foreground": "#ebdbb2",
                                "Background": "#639494"
                            },
                            "Active": {
                                "Foreground": "#ebdbb2",
                                "Background": "#394e4e"
                            }
                        }
                    },
                    {
                        "Base": {
                            "Normal": {
                                "Foreground": "#ebdbb2",
                                "Background": "#00000000"
                            }
                        }
                    },
                    {
                        "TableCurrentTrack": {
                            "Normal": {
                                "Foreground": "#ebdbb2",
                                "Background": "#394e4e",
                                "Style": "Bold"
                            },
                            "Focus": {
                                "Foreground": "#ebdbb2",
                                "Background": "#639494",
                                "Style": "Bold"
                            },
                            "Active": {
                                "Foreground": "#ebdbb2",
                                "Background": "#394e4e",
                                "Style": "Bold"
                            }
                        }
                    },
                    {
                        "TableNormalTracks": {
                            "Normal": {
                                "Foreground": "#ebdbb2",
                                "Background": "#00000000"
                            },
                            "Focus": {
                                "Foreground": "#ebdbb2",
                                "Background": "#639494"
                            },
                            "Active": {
                                "Foreground": "#ebdbb2",
                                "Background": "#394e4e"
                            }
                        }
                    },
                    {
                        "Menu": {
                            "Normal": {
                                "Foreground": "#ebdbb2",
                                "Background": "#3a3a3a"
                            },
                            "Focus": {
                                "Foreground": "#ebdbb2",
                                "Background": "#639494"
                            },
                            "Active": {
                                "Foreground": "#ebdbb2",
                                "Background": "#394e4e"
                            }
                        }
                    },
                    {
                        "StatusBar": {
                            "Normal": {
                                "Foreground": "#949494",
                                "Background": "#3a3a3a"
                            }
                        }
                    },
                    {
                        "StatusBar_Mode": {
                            "Normal": {
                                "Foreground": "#262626",
                                "Background": "#949494",
                                "Style": "Bold"
                            }
                        }
                    },
                    {
                        "CommandLine": {
                            "Normal": {
                                "Foreground": "#ebdbb2",
                                "Background": "#00000000"
                            },
                            "Editable": {
                                "Foreground": "#ebdbb2",
                                "Background": "#00000000"
                            }
                        }
                    },
                    {
                        "CommandLineError": {
                            "Normal": {
                                "Foreground": "#262626",
                                "Background": "#d75f5f",
                                "Style": "Bold"
                            }
                        }
                    }
                ]
            }
        }
    ]
}

🤝 Contributing

Contributions are welcome!

📄 License

Distributed under the Apache-2.0 License. See LICENSE for more information.

About

Steaming Music on Console: cross-platform TUI-based streaming music player

Topics

Resources

License

Stars

Watchers

Forks

Contributors

Languages