Search code examples
playframework-2.0debiansbtsbt-native-packager

.deb for SystemD created from debian:packageBin for Play 2.4.2 App Does Not Have Permisison to Create Log


How can a SystemD install script created by sbt debian:packageBin set up permissions for the webapp to write to the PID /var/run or a subdirectory?

Only root has permission to create a pid file in /var/run or to create a directory like /var/run/myWebApp/ that holds a pid file. The debian:packageBin task causes the webapp to run as a special user:group created from the name of the webapp. If a directory is created like /var/run/myWebApp, the myWebApp group needs write permission, but I don't see any way to make this happen automatically. Am I missing something?

Here are some of my config files:

dist/conf/application.ini:

-Dpidfile.path=/var/run/webapp2/webapp2.pid

conf/application.conf:

# This seems redundant ... should it be removed?
pidfile.path = /var/run/webapp2/pid
pidfile.path = ${?pidfile.path}

debian.sbt:

import com.typesafe.sbt.packager.archetypes.ServerLoader.{Systemd, SystemV, Upstart}
import com.typesafe.sbt.SbtNativePackager.autoImport._

lazy val root = (project in file(".")).enablePlugins(PlayScala, DebianPlugin)

enablePlugins(JavaAppPackaging)
enablePlugins(JDebPackaging)
enablePlugins(JavaServerAppPackaging)

serverLoading in Debian := Systemd

maintainer in Linux      := "Mike Slinn <mslinn@mslinn.com>"
packageSummary in Linux  := "myWebApp blah blah"
packageDescription       := "myWebApp blah blah"
daemonUser in Linux      := normalizedName.value        // user which will execute the application, resolves to "myWebApp"
daemonGroup in Linux     := (daemonUser in Linux).value // group which will execute the application, resolves to "myWebApp"

Update:

Play manages its own pid.. I was not able to get ${{app_name}} to expand, so I hardcoded myWebApp instead.

The sbt-native-packager docs say that the pid should be placed in /var/run/myWebApp and the logs in /var/log/myWebApp.

/var/run has permission 777 is symlinked to /run with permission 775; both are owned by root:root. Thus the only way for a non-root process can write to /var/run is for a directory to be created under /var/run with the appropriate permissions. For example, postgres:postgres has permission to write to /var/run/postgres:

$ ls -adlF /var/run/postgresql
drwxrwsr-x 3 postgres postgres 120 Aug 28 01:17 /var/run/postgresql/

This is how the Play docs show placing the pid in /var/run should work, however this does not work for me.


Solution

  • Here is the solution, placed in debian.sbt:

    linuxPackageMappings += packageTemplateMapping(s"/var/run/${name.value}/")() withUser name.value withGroup name.value
    

    There was no need for the extra entries in conf/application.conf.