ansible – restart a (nginx) service only if it is running and the configuration is ok

Author:

Another ansible quick tip showing how to restart a program properly. We want to restart the program or the service only if it is running (because some system on executing restart may start the service even it is in the stopped state).
Here is what the ansible playbook do:

  1. Check if the program is running.
  2. Check the configuration of the program. Do not restart a program or service if it cannot start after a stop command because of bad configuration file(s).
  3. Restart the service (the program) only if the above two are true.

If you are a newbie in ansible you can check this article – First ansible use – install and execute a single command or multiple tasks in a playbook There you can see how to create your inventory file (and configure sudo if you remotely log in with unprivileged user) used herein the example.

Ansible YAML file

For our example we use the nginx webserver in the ansible playbook. Put the following code in a file and then execute ansible-playbook:

---
- hosts: all
  tasks:
            
    - name: Test for running nginx
      shell: ps axuf|grep 'nginx'|grep -v "grep" | tr -d "\n" | cat
      register: test_running_nginx
      changed_when: False
      tags: restart-nginx
      
    - name: First check the configuration
      shell: /usr/sbin/nginx -t
      register: test_nginx_config
      when: test_running_nginx.stdout != ""
      changed_when: False
      ignore_errors: True
      tags: restart-nginx
          
    - name: Restart nginx
      service: name=nginx state=restarted
      when: test_running_nginx.stdout != "" and test_nginx_config.rc == 0
      tags: restart-nginx

Here is how to run the above ansible playbook

myuser@srv ~ $ ansible-playbook -l srv2 -i ./inventory.ini ./playbook-example.yml -b

PLAY [all] *****************************************************************************************************************************************************************

TASK [Gathering Facts] *****************************************************************************************************************************************************
ok: [srv2]

TASK [Test for running nginx] **********************************************************************************************************************************************
ok: [srv2]

TASK [First check the configuration] ***************************************************************************************************************************************
ok: [srv2]

TASK [Restart nginx] *******************************************************************************************************************************************************
changed: [srv2]

PLAY RECAP *****************************************************************************************************************************************************************
srv2                       : ok=4    changed=1    unreachable=0    failed=0   

Here we add to the command line “-b”, which will escalate to root if it is needed (using sudo) because the remote connection is done with unprivileged user “myuser”. You can skip this option if you described the remote connection with the root user in the inventory file (or a system user, which has permissions to restart services).

If there are no running nginx the rest tasks are skipped:

myuser@srv ~ $ ansible-playbook -l srv3 -i ./inventory.ini ./playbook-example.yml -b

PLAY [all] *****************************************************************************************************************************************************************

TASK [Gathering Facts] *****************************************************************************************************************************************************
ok: [srv3]

TASK [Test for running nginx] **********************************************************************************************************************************************
ok: [srv3]

TASK [First check the configuration] ***************************************************************************************************************************************
skipping: [srv3]

TASK [Restart nginx] *******************************************************************************************************************************************************
skipping: [srv3]

PLAY RECAP *****************************************************************************************************************************************************************
srv3                       : ok=2    changed=0    unreachable=0    failed=0

One thought on “ansible – restart a (nginx) service only if it is running and the configuration is ok”

  1. > ps axuf|grep ‘nginx’|grep -v “grep” | tr -d “n” | cat

    This looks… well, scary a bit. ‘ps -C procname’ does pretty much the same thing. Also, it returns exit code of 1 if the matching process was not found. The process must be named by the full filename with or without path. Ex.

    “`
    $ ps -C dbus-daemon; echo $?
    PID TTY TIME CMD
    381 ? 00:00:06 dbus-daemon
    472 ? 00:00:03 dbus-daemon
    0
    $ ps -C dbus-daemon -opid=,user=; echo $?
    381 messagebus
    472 kkm
    0
    $ ps -C dbus-daemon –no-header -opid,user; echo $?
    381 messagebus
    472 kkm
    0
    $ ps -C dbus –no-header -opid,user; echo $?
    1
    $
    “`
    Unless you’re on BSD, where -C does not exist, AFAIK.

    Cheers!

Leave a Reply

Your email address will not be published. Required fields are marked *