添加链接
link管理
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接

I did not intend to create a new blog on Ansible so fast, but here it comes.
My previous blog on that topic was a first step in Ansible world. Now, it is time to use some of the advanced features.

Context

We recently had an issue at a customer site, where some of the servers were having time synchronization issues. I discovered that ntp configuration was not the same across all servers which, from my experience. can lead to time drifts. For most of the web application, time is not so important constraint, unless your application used SAML2 Single Sign On mechanism.

My goal, here, is to check ntp status on all servers in one shot.

First playbook

My first attempt was a very basic playbook:

- name: NTP Check hosts: all gather_facts: no tasks: - name: Run ntpdc -p shell: /usr/sbin/ntpdc -p register: output - name: Display output debug: var: output.stdout_lines

I use a variable named output (which is created with register option) and display content for each servers of the inventory ( output.stdout_lines ).

I faced an issue on two hosts of my list:

ok: [server-123456] => {
"output.stdout_lines": "VARIABLE IS NOT DEFINED!"

This was due a difference in ntp client. These two hosts run chrony instead of ntpd, which means I have to run different commands depending on the time synchronization client.

Second attempt

I took the easiest way: If /etc/ntp.conf exists, I run ntpdc command. If not, I used the chronyc command. And, finally, display merged result whatever the ntp client.

Playbook becomes:

- name: NTP Check hosts: all gather_facts: no tasks: - name: Determine ntp client stat: path: /etc/ntp.conf register: ntpd - name: Run ntpdc -p shell: /usr/sbin/ntpdc -p register: output when: ntpd.stat.exists - name: Run chronyc shell: /usr/bin/chronyc sources register: output when: not ntpd.stat.exists - name: Display output debug: var: output.stdout_lines

From this playbook, I learn that even if “when” condition is not met, and task will be skipped, output register will be erased for these hosts (and “VARIABLE IS NOT DEFINED!” will be displayed). Which means that output will be populated for my two hosts that use chrony client. Unfortunately, as per Ansible documentation , this is the expected behavior:

“If a task fails or is skipped, Ansible still registers a variable with a failure or skipped status, unless the task is skipped based on tags. See Tags for information on adding and using tags.”

tags will not help me here as I want to have all results in same output and in one command.

Third try

As Ansible can manage errors via exception, I wondered if it would be possible to simply run chrony command if ntpdc command fails.

- name: NTP Check hosts: all gather_facts: no tasks: - name: Run ntpdc -p (block) block: - name: Run ntpdc -p command: /usr/sbin/ntpdc -p register: output rescue: - name: Run chronyc (block) block: - name: Run chronyc command: /usr/bin/chronyc sources register: output always: - name: Display output debug: var: output.stdout_lines

If first task block “Run ntpdc” fails, it will jump to rescue block and run chronyc block. Then, whatever ntpdc or chronyc block was run, always will be run with output always defined.
All servers will have similar output as below:

  • For a ntp client:
  • ok: [server-123456] => {
        "output.stdout_lines": [
            " remote local st poll reach delay offset disp",
            "=======================================================================",
            "*ntp01 10.10.10.10 1 512 377 0.00047 -0.730333 0.11720",
            "=ntp02 10.10.10.11 1 512 377 0.00087 -0.733377 0.11292"
    
  • For a chrony client:
  • ok: [server-456789] => {
        "output.stdout_lines": [
        "210 Number of sources = 5",
        "MS Name/IP address Stratum Poll Reach LastRx Last sample ",
        "===============================================================================",
        "^* ntp04 1 6 377 38 -14us[ -46us] +/- 233us",
        "^- ntp05 3 10 377 388 +7566us[+7585us] +/- 116ms",
        "^? ntp06 2 6 377 43 +2947ms[+2947ms] +/- 11.0s",
        "^- ntp07 3 10 377 191 -8696us[-8716us] +/- 120ms",
        "^? ntp08 2 10 377 999 +2953ms[+2953ms] +/- 11.0s"
    

    Note that for these examples, servers were using different ntp client but also different ntp sources which is what I wanted to check.

    What next ?

    These are still basic playbooks, but I wrote them in few minutes and they fill a need. It is from needs that come ideas.

    Post Views: 2,242 DevOps, Kubernetes Investigative look into cloud-native hyper-converged infrastructure with Harvester
    19.04.2024 by Jean-Philippe Clapot

    dbi services is a company specialized in IT consulting and services. We are experts in innovative and efficient data infrastructures and platforms. Tailor-made solutions is what we offer to our customers thanks to our consultants, whose skills and knowledge are constantly evolving thanks to continuous training.