puppet-python icon indicating copy to clipboard operation
puppet-python copied to clipboard

CentOS7: Failed to start gunicorn.service: Unit not found.

Open droopy4096 opened this issue 7 years ago • 5 comments

using master:HEAD on CentOS7 having declared:

class { 'python':
   version    => 'system',
   pip        => 'present',
   dev        => 'absent',
   virtualenv => 'absent',
   gunicorn   => 'present',
   manage_gunicorn => true,
 }  

and:

python::gunicorn { 'puppet_reports':
   ensure      => present,
   mode        => 'wsgi',
   dir         => $dir,
   bind        => "0.0.0.0:${port}",
   accesslog   => "${log_dir}/access.log",
   errorlog    => "${log_dir}/error.log",
   appmodule   => 'puppet_reports:app',
   timeout     => 30,
   owner       => $owner,
   require     => Vcsrepo[$dir],
 }

I get:

Error: Could not start Service[gunicorn]: Execution of '/bin/systemctl start gunicorn' returned 5: Failed to start gunicorn.service: Unit not found.
Wrapped exception:
Execution of '/bin/systemctl start gunicorn' returned 5: Failed to start gunicorn.service: Unit not found.
Error: /Stage[main]/Python::Config/Service[gunicorn]/ensure: change from stopped to running failed: Could not start Service[gunicorn]: Execution of '/bin/systemctl start gunicorn' returned 5: Failed to start gunicorn.service: Unit not found.
Notice: /Stage[main]/Python/Anchor[python::end]: Dependency Service[gunicorn] has failures: true
Warning: /Stage[main]/Python/Anchor[python::end]: Skipping because of failed dependencies

droopy4096 avatar Mar 29 '17 14:03 droopy4096

I'm having the same problem. Has there been any work on this issue? Did you end up finding a solution @droopy4096 ?


EDIT: In case anyone finds this issue looking for a solution, I'm including some information about what I did to get it working. My solution was to replace the python::gunicorn definition with a custom systemd service. The details might be different for other projects but the basic idea should work.


I replaced the following code

python::gunicorn { 'project1-vhost':
  ensure     => present,
  virtualenv => '/var/www/project1/venv',
  dir        => '/var/www/project1'
  timeout    => 120,
  bind       => 'localhost:5000',
  appmodule  => 'app:app',
  owner      => 'www-data',
  group      => 'www-data',
}

with

file { '/etc/systemd/system/project1-vhost.service':
  source => 'puppet:///modules/site/project1/project1-vhost.service',
}

file { '/var/log/gunicorn':
  ensure => directory,
  owner  => 'apache',
}

file { '/var/run/gunicorn':
  ensure => directory,
  owner  => 'apache',
}

service { 'project1-vhost':
  ensure  => running,
  enable  => true,
  require => [
    File['/etc/systemd/system/project1-vhost.service'],
    File['/var/log/gunicorn'],
    File['/var/run/gunicorn'],
  ],
}

and added the file modules/site/files/project1/project1-vhost.service with the contents

[Unit]
Description=project1-vhost daemon
After=network.target

[Service]
User=apache
Group=apache
WorkingDirectory=/var/www/project1
ExecStart=/var/www/project1/venv/bin/python -- /var/www/project1/venv/bin/gunicorn --pid /var/run/gunicorn/project1-vhost.pid --name project1-vhost --user apache --group apache --log-file /var/log/gunicorn/project1-vhost.log --bind=localhost:5000 --workers=3 --timeout=120 --log-level=error app:app

[Install]
WantedBy=multi-user.target

zfletch avatar Sep 13 '18 21:09 zfletch

Anything new on this?

MasterMind2k avatar Mar 27 '19 17:03 MasterMind2k

not here...

droopy4096 avatar Mar 27 '19 18:03 droopy4096

Underlying problem is the current python-gunicorn rpm for CentOS/Redhat 7 doesn't deploy a systemd unit file named 'gunicorn.service,' causing declaration Service[gunicorn] to fail. Also, the /etc/gunicorn.d directory is only used in Debian/Ubuntu packaging, ignored in CentOS/Redhat.

The systemd-friendly resolution would be to modify python::gunicorn to deploy a systemd template unit file on those OSes that require systemd (like CentOS/Redhat 7) and then launch an instance of the template.

So, python::gunicorn{ 'foo_app': ...} could write a systemd unit file from ERB to /etc/systemd/system/gunicorn@foo_app.service like this:

[Unit]
Description=Gunicorn instance to serve %I
After=network.target

[Service]
User=<%= @owner] %>
Group=<%= @group] %>
WorkingDirectory=<%= @dir %>
ExecStart=<%= @virtualenv %>/bin/gunicorn --workers <%= @workers %> --bind <%= @bind %> <%= @appmodule %>
Restart=always

[Install]
WantedBy=multi-user.target

Then launch the service like this:

# systemctl start gunicorn@foo_app.service

And finally declare a service resource:

service { 'gunicorn@foo_app':
  ensure     => running,
  enable     => true,
}

The python::config class would also need updating to not declare the resource Service[gunicorn], in such cases. There still would be no service named just 'gunicorn.'

This module might be useful for farming out sysytemd unit file management: https://fedoramagazine.org/systemd-template-unit-files/

Please note I don't yet have this suggestion working for me verbatim. Just collecting what research I've gathered.

westbywest avatar Sep 04 '19 16:09 westbywest

Debian, starting from version stretch (9) does not support gunicorn.d too. This means, the /etc/gunicorn.d approach does not work since July 2020 on Debian stable. https://metadata.ftp-master.debian.org/changelogs//main/g/gunicorn/gunicorn_19.6.0-10+deb9u1_NEWS

Rocco83 avatar Oct 04 '23 05:10 Rocco83