Tuesday, October 17, 2017

ArchLinux + Raspberry Pi Zero W + "Mopidy & MusicBox & SpotifyPlugin" (as a Service)


The info about how to turn a Raspberry Pi Zero W into a tiny, headless, web-browser controlled player for a Spotify premium account is scattered in too many places, and a little painful to find, so I'm bringing it all together here.

High Level Overview

  • Pre-requisite - Raspberry Pi Zero W (wireless) with ArchLinux installed and updated, with the WiFi configured and connected (not covering that stuff here).
  • Pre-requisite - A Spotify premium (paid) account.
  • Get audio working over HDMI output
  • Get ALSA installed as the "sink" for MPD
  • Set up yaourt to help with installs from AUR
  • Install mopidy and mopidy-musicbox
  • Install mopidy-spotify
  • Tweak permissions and config so it will all work

Set up Raspberry Pi Zero W with ArchLinux and WiFi

Ok, fine, at least a few links in case that's the only thing keeping you from the rest of this.
  • https://archlinuxarm.org/platforms/armv6/raspberry-pi
  • https://gist.github.com/andreibosco/8246142

Get audio working over HDMI

The Raspberry Pi Zero W doesn't have an audio jack, so the cheapest, easiest way to connect audio is through an HDMI input on a TV or Blu-Ray player, to built-in or external speakers, headphones, etc.

Add these lines to /boot/config.txt and reboot the Pi.
dtparam=audio=on
hdmi_drive=2

Get ALSA installed as the "sink" for MPD

pacman -S alsa-firmware alsa-lib alsa-plugins alsa-utils alsaplayer

Test HDMI Audio

To see whether there is actually a sound device activated, this command...

aplay -l

     ...should show output like...

**** List of PLAYBACK Hardware Devices ****
card 0: ALSA [bcm2835 ALSA], device 0: bcm2835 ALSA [bcm2835 ALSA]
  Subdevices: 7/8
  Subdevice #0: subdevice #0
  Subdevice #1: subdevice #1
  Subdevice #2: subdevice #2
  Subdevice #3: subdevice #3
  Subdevice #4: subdevice #4
  Subdevice #5: subdevice #5
  Subdevice #6: subdevice #6
  Subdevice #7: subdevice #7
card 0: ALSA [bcm2835 ALSA], device 1: bcm2835 ALSA [bcm2835 IEC958/HDMI]
  Subdevices: 1/1
  Subdevice #0: subdevice #0

With the sound-capable HDMI device connected to the Pi, test sound output with this command...

aplay /usr/share/sounds/alsa/Front_Center.wav

Set up yaourt to help with installs from AUR

First, install the development tools and libraries required to compile code and create packages.

      pacman -S base-devel binutils yajl wget

Install package-query from AUR.
Change to a non-root user (in case you're logged in as root, or currently in a "su" session).  makepkg cannot be run as root. (But, you could try it if you want to see the error messages for yourself.)
      su alarm
Change to the home directory of the alarm account.
      cd
 Create a directory to download and unpack build script/resources.
      mkdir install && cd install
Download the package build start script.
      wget https://aur.archlinux.org/cgit/aur.git/snapshot/package-query.tar.gz
Unpack it
       tar -xzvf package-query.tar.gz
Change to the unpack directory.
       cd package-query
Run makepkg.
       makepkg -Acs
Install the AUR package just retrieved and built.
       su
       pacman -U package-query-1.9-2-armv6h.pkg.tar.xz

Install yaourt from AUR
(Same steps as above for package-query, but for yaourt.)
      su alarm
      cd ~/install
      wget https://aur.archlinux.org/cgit/aur.git/snapshot/yaourt.tar.gz
      tar -xzvf yaourt.tar.gz
      cd yaourt
      makepkg -Acs
      su
      pacman -U yaourt-1.9-1-armv6h.pkg.tar.gz

Install mopidy and mopidy-musicbox

  • Note: With yaourt installed, the remaining AUR installs are a little easier.
  • Note: These installs must be run from a non-root user, but they'll prompt for the root password when they reach the point where the package is built and needs to be installed.
  • Note: The default prompt-answers during these scripts are usually what you want, except for the offer to edit/modify the build.  You probably want to answer 'n' (no) to that one unless you really want to tweak the instructions in the package build, or just want to open it in an editor and take a look at what it does.

      yaourt -S mopidy
      yaourt -S mopidy-musicbox
      yaourt -S mopidy-spotify

  • Note: If any of these go sideways midway (like maybe you accidentally hit something other than the enter key at one of the prompts), just run them again and they'll pick up more-or-less where they left off.

Tweak permissions and config so it will all work


No installer ever seems to get everything quite right, so here's the rest.

Create the "mopidy" user.

(Assuming one of the installers didn't already do this.) 

useradd --create-home --groups audio mopidy

IMPORTANT: Don't miss the extra group audio or, later on, the mopidy user won't have permissions to use sound devices.

Change the owner of the mopidy lib, log, and cache directories

These files must be owned by mopidy:mopidy (or the mopidy service won't be able to write stuff into them, because it will be run as the mopidy user).
      chown -R mopidy:mopidy /var/lib/mopidy
      chown -R mopidy:mopidy /var/log/mopidy
      chown -R mopidy:mopidy /var/cache/mopidy

Add a systemd service for mopidy


  • Edit /etc/systemd/system/mopidy.service
[Unit]
Description=Mopidy
After=network.target

[Service]
User=mopidy
ExecStart=/usr/bin/mopidy --config=/etc/mopidy/mopidy.conf
Restart=on-abort

[Install]
WantedBy=multi-user.target
  • systemctl enable mopidy
  • systemctl start mopidy
  • systemctl status mopidy
  • WARNING: Since mopidy runs as the mopidy user, it may generate an empty mopidy.conf file in /home/mopidy/.config/mopidy/ which will interfere with the config settings in /etc/mopidy/mopidy.conf.
    • If things don't seem to be operating as configured, leave the .../.config/mopidy/mopidy.conf file there but delete all of its contents.

Bind mopidy's listeners to all network interfaces

The default is to just listen on 127.0.0.1 but that isn't very useful if you want to control mopidy using the MusicBox web interface.
  • Note: This assumes the Pi will be accessible via private LAN only.
  1. edit /etc/mopidy/mopidy.conf
  2. Add
    [mpd]
    hostname = 0.0.0.0
    [http]
    hostname = 0.0.0.0

Add config for the spotify plugin.

First, authorize the mopidy-extensions to access your premium Spotify account at:
     https://www.mopidy.com/authenticate/#spotify
Then edit /etc/mopidy/mopidy.conf again and add (substituting your credentials, id,
secret, etc. for the fake examples given here as an example of what it would look like).
     [spotify]
     username = myspotifyid
     password = mypw
     client_id = eieio1d7d-fefe-4ccc-8ccc-404040ff10f
     client_secret = HhRR2eeMQ0jRsX77fm62ma5Kw2rABCDeFG-HIJKLMNOP=


Final restart and Tryout

  • systemctl restart mopidy
  • systemctl status mopidy(check for errors)

Point a browser, to the Pi's ip address on port 6680 and click the link to switch over to MusicBox (something like this).
    
      http://192.168.0.10:6680


Conclusion


Let me know if anything major is missing.  I tried to get all the necessary steps in here with enough detail to get it done, but not so much extra noise.  I couldn't find any setup guide that was focused on getting mopidy set up with ArchLinux on a Raspberry Pi Zero W, but IMO, mopidy is the perfect single-app use of a Pi Zero W, and ArchLinux is a bit better than Raspbian for a headless setup, so I'm assuming someone else out there feels the same.  Also leave a comment if this helped you make your own Music streamer/player out of a Pi Zero W.  HTH.