[howto] Powermate extension on a Raspberry Pi

This should have been easy. Really easy. It wasn’t.

Start with a freshly installed Raspian. I used NOOBS 2.3.0.
Ensure you have a network connection.

We’ll do 90% of the work from the Terminal.

Update the package manager:

sudo apt-get update; sudo apt-get upgrade

Get a recent version of Node. The latest as of this writing was 7.8.0:

wget https://nodejs.org/dist/v7.8.0/node-v7.8.0-linux-armv7l.tar.gz

Extract it:

tar -xvf node-v7.8.0-linux-armv7l.tar.gz 

Then copy it into place:

cd node-v7.8.0-linux-armv7l/
sudo cp -R * /usr/local/

Check your work:

node -v

should report:

v7.8.0

Powermate requires node-hid, and there isn’t precompiled package for ARM. No big deal. Change back to your home directory:

cd

Grab the dependencies:

sudo apt-get install libudev-dev
sudo apt-get install libusb-1.0-0-dev

Then install. It’ll report errors about not finding a download, and then it’ll fall back to building from source:

npm install node-hid

When it finishes, grab the Roon Powermate package:

 git clone https://github.com/RoonLabs/roon-extension-powermate.git

Run the install:

 cd roon-extension-powermate/
 npm install

To see the Powermate device as a non-administrator, you need to set up permissions. This was by far the trickiest part of the project:

sudo pico /etc/udev/rules.d/50-usb-powermate.rules

Add these lines, watching for typos:

SUBSYSTEM=="input", GROUP="input", MODE="0666"
SUBSYSTEM=="usb", ATTRS{idVendor}=="077d", ATTRS{idProduct}=="0410", MODE:="666", GROUP="plugdev"

Refresh the cached rules:

sudo udevadm control --reload-rules

Unplug the Powermate, then plug it back in to apply the permissions.

Check your work:

node .

Open a Roon client, go to Settings, and select Extensions. You should see the Roon Powermate listed.

Finally, to allow this setup to run headless, we need to create a script to run it, and add it to the startup applications.

Type ^C to stop the extension. Open an editor again:

cd 
pico start-powermate.sh

Add these lines:

#!/bin/sh -e
cd /home/pi/roon-extension-powermate
2>/dev/null 1>/dev/null node . &

Make the script executable:

chmod a+x start-powermate.sh

Now, use the GUI to make this script auto-run:

  • Choose Preferences->Main Menu editor
  • In the left column, click Preferences
  • Enable the checkbox for Default applications for LXSessions
  • Click OK
  • Choose Preferences->Default applications for LXSessions
  • In the left column, click Autostart
  • In the text area next to the Add button, type /home/pi/start-powermate.sh
  • Click Add
  • Close the window

Final test:
Reboot your Pi, and on your Roon controller, open Settings->Extensions, and verify that you see the Powermate extension running:

1 Like

Thanks for sharing!

Will this extension work for the bluetooth powermate as well?

Anyone tested this with iqaudios_Roonready Image?
I am using the Digi-Amp+ in my kitchen and volume Control with Hardware Buttons would be great

Thanks to @Steve_Kalkwarf, I was able to easily install the Griffin Powermate extension into my system. The knob is attached to a Pi, and can be set to control volume on a different Pi / Roon Bridge via API requests over the network to the Core. Very cool! Instead of Raspbian / NOOBS, for the OS I am using DietPi, which has a nice, easy package tool for installing Node.js, and which also does not have several prerequisite packages needed to compile the extension. Consequently, the installation process was a slight bit different in detail from the provided instructions. Here’s the steps I followed; hopefully others will find it useful.

# DietPi uses the 'root' account for routine access.  No need for "sudo"
#
# Install the Node.js package via DietPi's installer: 
dietpi-software install 9

# check the version of Node  (I get v9.0.0) 
node -v
 
# Install a number of prerequisite packages via standard raspbian repositories:
apt-get -y install build-essential git python libudev-dev libusb-1.0-0-dev

# install the HID package to Node, to speak to the powermate:
npm install node-hid

# make sure we're still in root's home dir:
cd 

# Pull down the Powermate Extension code:
git clone https://github.com/RoonLabs/roon-extension-powermate.git

# change into the directory:
cd roon-extension-powermate/

# build & install the extension with Node Package Manager:
npm install

# Create the udev config file with a text editor:
pico /etc/udev/rules.d/50-usb-powermate.rules
      SUBSYSTEM=="input", GROUP="input", MODE="0666"
      SUBSYSTEM=="usb", ATTRS{idVendor}=="077d", ATTRS{idProduct}=="0410", MODE:="666", GROUP="plugdev"

# Plug in the Powermate, check that DietPi system sees the raw device:
# expect:  "Bus 001 Device 004: ID 077d:0410 Griffin Technology PowerMate"
lsusb

# reload the udev rules:
udevadm control --reload-rules

# start the Node server, which sends the Powermate events to the Roon Core API:
node .

# Create a startup script to launch Node, mind the path is different from original instructions:
pico /root/start-powermate.sh 
  #!/bin/sh -e
  cd /root/roon-extension-powermate 
  2>/dev/null 1>/dev/null node . &

#edit  mark script executable
chmod a+x /root/start-powermate.sh

# Add the following to the 2nd-from-bottom line of /etc/rc.local, above final 'exit 0' (caution, this might be overridden by later vendor updates)
   # start powermate HID extension in Node:
   /root/start-powermate.sh
1 Like

Thanks for sharing - my power mate arrived about an hour ago, and it is up and running perfectly!

EDIT: ran perfectly until I closed the SSH session (and rebooted the pi). Needed to

  1. After running node . (and killing it)
    cd

to get back to the root folder (otherwise you’re still in the extension folder).

  1. after creating start-powermate.sh
    chmod a+x start-powermate.sh

I’d recommend to create a systemd service file for the powermate.
(add sudo if you are not root)

nano /etc/systemd/system/powermate.service

Then paste the following content (adjust the path of your extension file):

[Unit]
Description=PowerMate control for Roon
Wants=network-online.target

[Service]
WorkingDirectory=/path/to/extensionfolder
ExecStart=/path/to/node /path/to/extensionfolder/app.js
Restart=always
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=powermate-control
Environment=NODE_ENV=production

[Install]
WantedBy=multi-user.target

Then enable the service file by
systemctl enable powermate
systemctl start powermate

I did not test it yet, but it should do the job.

1 Like

Works well as tested on my DietPi. Thanks for that - it’s less likely to get clobbered if DietPi ever changes the content of rc.local. I guess I’m an old init.d guy unhip to this newfangled systemd stuff. :grin:

Thanks for the post. Almost worked in my case - I guess I installed node.js in the wrong location. Instead of :-

I ran

which node

and changed it to:-

/usr/local/bin/node /path/to/extensionfolder/app.js

Can’t remember manually installing node.js so posting it in case someone else runs into it. But thank you for your post - I did wonder how to turn a node app into a service and all I found online was fairly long and protracted! One to store away for future reference. I love learning things on these forums.

I modified the service file above to /path/to/node. I am unsure if this might differ from distribution to distribution…

(I was using this for a different extension on ropieee and the node binary was located at /usr/bin/node.)

Thanks - I am using DietPi and checked all the endpoints - all are under /usr/local/bin for me so seems it does vary.

Hi, does anyone know if this would work on Mac OSX for the old USB powermate? I already have Roon Extension Manager installed…?

Has anyone tested this with roopieee?