diff --git a/Makefile.am b/Makefile.am index 29080d96..7040bce6 100644 --- a/Makefile.am +++ b/Makefile.am @@ -7,13 +7,14 @@ ACLOCAL_AMFLAGS = -I m4 RPM_SPEC_FILE = owntone.spec CONF_FILE = owntone.conf SYSTEMD_SERVICE_FILE = owntone.service +SYSTEMD_TSERVICE_FILE = owntone@.service if COND_INSTALL_SYSTEMD systemddir = $(SYSTEMD_DIR) -systemd_DATA = $(SYSTEMD_SERVICE_FILE) +systemd_DATA = $(SYSTEMD_SERVICE_FILE) $(SYSTEMD_TSERVICE_FILE) endif -BUILT_SOURCES = $(CONF_FILE) $(SYSTEMD_SERVICE_FILE) +BUILT_SOURCES = $(CONF_FILE) $(SYSTEMD_SERVICE_FILE) $(SYSTEMD_TSERVICE_FILE) SUBDIRS = $(LIBRESPOTC_SUBDIR) sqlext src htdocs @@ -33,6 +34,7 @@ nobase_dist_doc_DATA = \ EXTRA_DIST = \ $(CONF_FILE).in \ $(SYSTEMD_SERVICE_FILE).in \ + $(SYSTEMD_TSERVICE_FILE).in \ $(RPM_SPEC_FILE) install-data-hook: @@ -73,7 +75,7 @@ do_subst = $(SED) -e 's|@sbindir[@]|$(sbindir)|g' \ -e 's|@OWNTONE_USER[@]|$(OWNTONE_USER)|g' # these files use $prefix, which is determined at build (not configure) time -$(CONF_FILE) $(SYSTEMD_SERVICE_FILE): Makefile +$(CONF_FILE) $(SYSTEMD_SERVICE_FILE) $(SYSTEMD_TSERVICE_FILE): Makefile $(AM_V_at)rm -f $@ $@-t $(AM_V_GEN)$(do_subst) "$(srcdir)/$@.in" > $@-t $(AM_V_at)mv $@-t $@ @@ -81,3 +83,5 @@ $(CONF_FILE) $(SYSTEMD_SERVICE_FILE): Makefile $(CONF_FILE): $(srcdir)/$(CONF_FILE).in $(SYSTEMD_SERVICE_FILE): $(srcdir)/$(SYSTEMD_SERVICE_FILE).in + +$(SYSTEMD_TSERVICE_FILE): $(srcdir)/$(SYSTEMD_TSERVICE_FILE).in diff --git a/README.md b/README.md index 3dd581e3..643d3332 100644 --- a/README.md +++ b/README.md @@ -52,6 +52,7 @@ please see the [INSTALL.md](INSTALL.md) file. - [Spotify](#spotify) - [LastFM](#lastfm) - [MPD clients](#mpd-clients) +- [Running Multiple Instances](#running-multiple-instances) - [References](#references) @@ -569,6 +570,30 @@ The following table shows what is working for a selection of MPD clients: | [mpc](http://www.musicpd.org/clients/mpc/) | CLI | Working commands: mpc, add, crop, current, del (ranges are not yet supported), play, next, prev (behaves like cdprev), pause, toggle, cdprev, seek, clear, outputs, enable, disable, playlist, ls, load, volume, repeat, random, single, search, find, list, update (initiates an init-rescan, the path argument is not supported) | | [ympd](http://www.ympd.org/) | Web | Everything except "add stream" should work | +## Running Multiple Instances + +To run multiple instances of owntone on a server, you should copy +`/etc/owntone.conf` to `/etc/owntone-zone.conf` (for each `zone`) and +modify the following to be unique across all instances: + +* the three port settings (`general` -> `websocket_port`, + `library` -> `port`, and `mpd` -> `port`) + +* the database paths (`general` -> `db_path`, `db_backup_path`, and `db_cache_path`) + +* the service name (`library` -> `name`). + +* you probably also want to disable local output (set `audio` -> `type = + "disabled"`). + +Then run `owntone -c /etc/owntone-zone.conf` to run owntone with the new +zone configuration. + +Owntone has a `systemd` template which lets you run this automatically +on systems that use systemd. You can start or enable the service for +a `zone` by `sudo systemctl start owntone@zone` and check that it is +running with `sudo systemctl status owntone@zone`. Use `sudo +systemctl enable ownton@zone` to get the service to start on reboot. ## References diff --git a/owntone.service.in b/owntone.service.in index ad5a9b49..f56b7b93 100644 --- a/owntone.service.in +++ b/owntone.service.in @@ -1,3 +1,5 @@ +# Note: Please keep this file in sync with owntone@.service.in + [Unit] Description=DAAP/DACP (iTunes), RSP and MPD server, supports AirPlay and Remote Documentation=man:owntone(8) diff --git a/owntone.spec.in b/owntone.spec.in index cc75f730..02910919 100644 --- a/owntone.spec.in +++ b/owntone.spec.in @@ -102,6 +102,7 @@ exit 0 %{_libdir}/%{name}/ %{_datarootdir}/%{name}/ %{_unitdir}/%{name}.service +%{_unitdir}/%{name}@.service %attr(0750,%{username},%{groupname}) %{_localstatedir}/cache/%{name} %attr(0750,%{username},%{groupname}) %{homedir} %ghost %{_localstatedir}/log/%{name}.log diff --git a/owntone@.service.in b/owntone@.service.in new file mode 100644 index 00000000..fdc4ae86 --- /dev/null +++ b/owntone@.service.in @@ -0,0 +1,37 @@ +# Note: Please keep this file in sync with owntone.service.in + +[Unit] +Description=DAAP/DACP (iTunes), RSP, MPD server, with AirPlay and Remote - %I +Documentation=man:owntone(8) +Requires=network.target local-fs.target avahi-daemon.socket +After=network.target sound.target remote-fs.target pulseaudio.service + +[Service] +ExecStart=@sbindir@/owntone -f -c /etc/owntone-%I.conf +SyslogIdentifier=owntone-%I + +# Constrain the upper limit of memory/swap that can be used; this prevents +# the server from consuming all system memory (in event of bug/malformed user +# curl/SMARTPL query etc) that would hang/freeze low resource and headless (ie +# RPi) machines +# +# systemd will kill the process in such an event but would be auto-restarted as +# per 'Restart' directive below +# +# Values derived from obersvations on rpi3 under load - limits are >50% above +# seen high watermarks +# +# https://www.freedesktop.org/software/systemd/man/systemd.resource-control.html +MemoryMax=256M +MemorySwapMax=32M + +# Restart, but set a limit so we don't restart indefinitely. Unfortunately, +# systemd also applies the start limits to manual restarts, so that's why the +# burst value allows for 10 restarts. +Restart=on-failure +RestartSec=5 +StartLimitBurst=10 +StartLimitInterval=600 + +[Install] +WantedBy=multi-user.target