Not able to insert ansible register output in csv - ansible

Here is my code:
- name: Check last usage history
shell: |
mysql -N --host={{ host }} \
--user={{ user }} \
--password={{ pass }} \
-D db \
-e "SELECT LEFT(CreationTime,LOCATE(' ',CreationTime) - 1) from table;"
register: last_usage
when: products != "1" and products != "2" and products != "3"
- name: Check last modified
shell: |
mysql -N --host={{ host }} \
--user={{ user }} \
--password={{ password }} \
-D db \
-e "SELECT LEFT(ModificationTime,LOCATE(' ',ModificationTime) - 1) FROM table2"
register: last_modi
when: products == "1 or products == "3" or products == "2"
- name: insert data in csv
shell: |
echo "{{ name }}{{ last_usage.stdout }} {{ last_modi.stdout }}" >> /home/test/test.csv
I want to print output in csv file NULL for a variable if task is skipped.
For now, it is showing
One or more undefined variables: 'dict object' has no attribute 'stdout'

- name: insert data in csv
shell: |
echo "{{ name }}{{ last_usage.stdout | default('NULL') }} {{ last_modi.stdout | default('NULL') }}" >> /home/test/test.csv

Related

Error with splitting Arguments due to bad quotes Ansible

I am writing a script, which should alter the Users of all Tenants of the Database. When i print the Command and execute it from hand on the Server, it works fine. With the Command Module i get this weird Error:
ERROR! failed at splitting arguments, either an unbalanced jinja2 block or quotes: {{ _hdbclient }} -U BASIS_{{ SID }}_{{ item.item }} -x -a "{{ item.stdout | replace('"', '')}}"
The error appears to be in '/tmp/awx_313202_z7e4l568/project/ansible_labor/scripts/update_users.yml': line 37, column 5, but may
be elsewhere in the file depending on the exact syntax problem.
The offending line appears to be:
- name: Execute Querys on Tenants
^ here
I think it has something to do with the Quotes in the Command Module.
This is the Script:
---
- name: Update all Users in DB
hosts: '*'
become: true
vars:
_User: "{{ lookup('env', 'USER') | upper }}_M"
_pattern: ^\"[a-zA-Z0-9]*\"
_tenants: []
_query: select 'alter user ' || user_name || ' IDENTIFIED EXTERNALLY AS ''' || user_name ||'#INTERN'';' as todo from users where EXTERNAL_IDENTITY LIKE '%COMPANY.DE';
_hdbclient: "/hana/shared/{{ SID }}/hdbclient/hdbsql -i {{ Instanz }} -n {{ inventory_hostname }}"
tasks:
- name: "Tenants der DB auslesen"
command: "{{ _hdbclient }} -U BASIS_{{ SID }}_SYSTEMDB -x -a 'SELECT * FROM M_DATABASES'"
register: tenants
- debug:
msg: "{{ tenants }}"
- set_fact:
_tenants: "{{ _tenants + [ item | regex_search(_pattern) | replace('\"', '') ] }}"
with_items: "{{ tenants.stdout_lines }}"
- name: Print extracted Tenants
debug:
msg: "{{ _tenants }}"
- name: Create Query on Tenant
command: '{{ _hdbclient }} -U BASIS_{{ SID }}_{{ item }} -x -a "{{ _query }}"'
register: query_tenants
with_items: "{{ _tenants }}"
- name: Print All Queries
debug:
msg: "{{ query_tenants.results[1] }}"
- name: Execute Querys on Tenants
command: "{{ _hdbclient }} -U BASIS_{{ SID }}_{{ item.item }} -x -a \"{{ item.stdout | replace('\"', '')}}\" "
with_items: "{{ query_tenants.results }}"
This is an escape issue inside your replace filter. You need to replace double quotes which translates as a string to \". Since that string is itself inside a double quoted string you have to escape the escape => \\\n
So keeping your initial quoting this gives:
command: "{{ _hdbclient }} -U BASIS_{{ SID }}_{{ item.item }} -x -a \"{{ item.stdout | replace('\\\"', '') }}\""
Meanwhile there are a few (non exhaustive list) alternatives you might want to consider:
command: '{{ _hdbclient }} -U BASIS_{{ SID }}_{{ item.item }} -x -a "{{ item.stdout | replace("\"", "") }}"'
command: >-
{{ _hdbclient }} -U BASIS_{{ SID }}_{{ item.item }} -x -a "{{ item.stdout | replace("\"", "") }}"

Ansible SHA1 encrypt variable

how can I encode a given string using ansible?
I'm trying to do this:
echo -n "mypassword" | sha1sum
Q: "Encode a given string."
A: Use hash filter. For example, the command and the filter
- shell: echo -n "mypassword" | sha1sum
register: result
- debug:
var: result.stdout
- set_fact:
pswd: "{{ 'mypassword' | hash('sha1') }}"
- debug:
var: pswd
give the same results
"result.stdout": "91dfd9ddb4198affc5c194cd8ce6d338fde470e2 -"
"pswd": "91dfd9ddb4198affc5c194cd8ce6d338fde470e2"
Q: "Insert the output string into a file."
A: For example, use the template
shell> cat templates/pswd.j2.txt
pswd: {{ pswd }}
- template:
src: pswd.j2.txt
dest: pswd.txt
give
shell> cat pswd.txt
pswd: 91dfd9ddb4198affc5c194cd8ce6d338fde470e2

Comparing the Mounts in ansible

I have a requirement in ansible to compare the mount counts before and after the maintenance, for this i am using the below tasks. We need to compare the premounts and postmounts and if there is difference in the value, it should throw a message to check the host. Please advise.
- name: Take premount counts
shell: df -h |awk ' NR>1{print $1}'|grep -v "tmpfs"|wc -l
register: premounts
- name: Take postmount counts
shell: df -h |awk ' NR>1{print $1}'|grep -v "tmpfs"|wc -l
register: postmounts
I think you are looking for the assert module. You can use this to print a message or fail as per condition.
Example:
- name: Take premount counts
shell: df -h |awk ' NR>1{print $1}'|grep -v "tmpfs"|wc -l
register: premounts
- name: Take postmount counts
shell: df -h |awk ' NR>1{print $1}'|grep -v "tmpfs"|wc -l
register: postmounts
- assert:
that:
- premounts == postmounts
fail_msg: "Premounts: {{ premounts }} and postmounts: {{ postmounts }} do not match!"
success_msg: "Mounts match."
Instead of running the df command and getting number of mounts, you can use the Ansible fact ansible_mounts to get this count also.
Example:
- set_fact:
premounts: "{{ ansible_mounts|count }}"
# some tasks in between
# Gather facts again
- setup:
- set_fact:
postmounts: "{{ ansible_mounts|count }}"
- assert:
that:
- premounts == postmounts
fail_msg: "Premounts: {{ premounts }} and postmounts: {{ postmounts }} do not match!"
success_msg: "Mounts match."
Try as below:
- name: Take premount counts
shell: df -h |awk ' NR>1{print $1}'|grep -v "tmpfs"|wc -l
register: premounts
- name: Take postmount counts
shell: df -h |awk ' NR>1{print $1}'|grep -v "tmpfs"|wc -l
register: postmounts
- debug:
msg: 'There are difference in the mount count, check it'
when: premounts.stdout_lines[0] | int != postmounts.stdout_lines[0] | int

Ansible multiple variable contains multiple values

i have some ansible task below :
- name: counting object from json
shell: >
jq '.results[].stdout_lines | length' backup/{{ inventory_hostname }}_rsl.json | wc -l
register: jsondata
- name: counting object converting
shell: >
seq 0 {{ jsondata.stdout|int - 1 }} | tr '\n' ' ' | xargs | sed 's/[[:space:]]/,/g'
register: seq
- name: get interface
shell: >
cat backup/{{ inventory_hostname }}_{{ item }}_rsl_result_nows.json | cut -d, -f1
register: interface
with_items:
- "{{ seq.stdout.split(',') | list }}"
- name: get rsl value
shell: >
cat backup/{{ inventory_hostname }}_{{ item }}_rsl_result_nows.json | cut -d, -f2-
register: rslvalue
with_items:
- "{{ seq.stdout.split(',') | list }}"
- name: post to DB via curl
shell: >
curl -d "ip_address={{ inventory_hostname }}&hostname={{ varhostname.stdout }}&interface={{ interface }}&rslvalue={{ rslvalue }}" -X POST http://dev.trm.net:8088/ip_planning/rsl/postrsl -v
i want to post data with the same hostname but different interface and some other attributes.
This my curl command that i want :
curl -d "ip_address=IP_A&hostname=HOST_A&interface=IFACE_1&rslvalue=1,2,3,4,5" -X POST http://dev.trm.net:8088/ip_planning/rsl/postrsl -v
curl -d "ip_address=IP_A&hostname=HOST_A&interface=IFACE_2&rslvalue=5,4,3,2,1" -X POST http://dev.trm.net:8088/ip_planning/rsl/postrsl -v
curl -d "ip_address=IP_B&hostname=HOST_B&interface=IFACE_1&rslvalue=11,21,31,41,51" -X POST http://dev.trm.net:8088/ip_planning/rsl/postrsl -v
i'm tired a full-day, please help me. i've tried from my ansible script above but error
"msg": "The task includes an option with an undefined variable. The error was: 'item' is undefined
You have {{ item.interface.stdout }} in the last task, but with_items is not present.
Also when you use item in the shell command, use as "{{item}}"
a little improvement make me small fun...
- name: post to DB via curl
shell: >
curl -d "ip_address={{ inventory_hostname }}&hostname={{ varhostname.stdout }}&interface={{ item }}&rslvalue={{ item }}" -X POST http://dev.tr$
with_items:
- "{{ rslvalue.results | map(attribute='stdout') | list }}"
- "{{ interface.results | map(attribute='stdout') | list }}"
but "item" variable always print "rslvalue" result. how to declare "item" with multiple with_items ??

complex loop in ansible with_together

How do I skip empty item in list if I use with_together?
see the code below:
- name: get data_files list
shell: ls -l data_files | awk -F " " {'print $9'}
register: csv_file_list
- debug: var=csv_file_list
- name: get table name list
shell: ls -l data_files/ | awk -F " " {'print $9'} | sed -e "s/.csv//g" | sed -e "s/-/./g"
register: table_list
- debug: var=table_list
- name: copy table from csv to demo db
shell: psql -U postgres -d demo -c "\copy {{ item.1 }} from /home/ubuntu/data_files/{{ item.0 }} DELIMITER ',' CSV HEADER"
with_together:
- csv_file_list.stdout_lines
- table_list.stdout_lines
when: {{ item.1 }} != ''
Test if item.1 is not none.
when: item.1 != None

Resources