[systemd-devel] Services with Access to User Sessions

Mantas Mikulėnas grawity at gmail.com
Mon May 19 12:14:58 PDT 2014


On Mon, May 19, 2014 at 9:55 PM, Justin Brown <justin.brown at fandingo.org> wrote:
>
> I'm having some difficulty setting up a systemd service that needs
> access to a "user session" (probably not the correct term). I want to
> configure shairport as a systemd service. Shairport is an open source
> implementation of Apple's AirPlay and is used to play audio from an
> iOS device on a Linux computer. As such, it needs access to
> PulseAudio. This is where I'm having trouble.
>
> I have a basic shairport.service file setup, and it correctly starts,
> but it does not seem to connect to PulseAudio because there is no
> audio output, even though the iOS device shows that audio is being
> transmitted.
>
> [Unit]
> Description=Shairport AirTunes receiver
> After=sound.target
> Requires=avahi-daemon.service
> After=avahi-daemon.service
>
> [Service]
> ExecStart=/usr/local/bin/shairport -v
> Restart=always
>
> [Install]
> WantedBy=multi-user.target
>
> I need some help addressing two points.
>
> 1) What do I need to change to allow this service to connect to
> PulseAudio in my desktop session?
> 2) Following on #1, how can I start this application only once a user
> logs in (i.e. PulseAudio can play audio)?

To both questions – it cannot easily be done from a system service, as
there can be zero or multiple desktop sessions at any moment. On the
other hand, if your systemd version is recent enough (v205+, I
think?), then you can run this as a _user_ service. [1]

When a user logs in, logind starts an instance of user@<uid>.service
for them, which starts "default.target" according to what's in
{~/.config,/etc,/usr/lib}/systemd/user/. It is not _completely_
connected to the desktop session right now – e.g. it won't know the
right $DISPLAY or $XAUTHORITY unless the X11 startup scripts call
`systemctl --user {set,import}-environment`. However, it should work
just fine for PulseAudio, which uses static paths for its socket &
cookie. I have been running mpd & pulseaudio as user services for the
past few months without any problems.

One minor downside is that right now a user service cannot depend on,
or be ordered against, a system service – so
"After=avahi-daemon.service" will be a no-op and
"Requires=avahi-daemon.service" will never succeed. (Though I think
one could work around this with a fake .service and a short perl
script that just watches bus names...)

You can use `systemctl --user` to control your user services.

[1] It's possible to use user at .service in some older systemd versions
as well, but it's not auto-started until v205, and there are other
small differences.

-- 
Mantas Mikulėnas <grawity at gmail.com>


More information about the systemd-devel mailing list