I want to use ansible to generate zone configuration files separately for bind9 dns server with 3 zones by reading data from a csv file
for example, in csv file we have:
hostname ,network1 ,network2 ,network3
server1 ,192.168.101.1 ,172.16.101.1 ,10.185.101.1
server2 ,192.168.101.2 ,172.16.101.2 ,10.185.101.2
<etc...>
I want at the end ansible to generate 3 files named like network1.zone.conf
, network2.zone.conf
, network3.zone.conf
.
I have no idea how to do that.
I tried:
- name: read from csv file
read_csv:
unique: false
path: "{{ CSV_File_Path }}"
delegate_to: localhost
register: OUTPUT_CSV
- name: print output
template:
src: zones.rfc.j2 # template path
dest: "/path/to/create/files/{{item}}.txt"
delegate to: dns_server
loop: "{{ OUTPUT_CSV.list }}"
loop_control:
extended: true
label: "{{ ansible_loop.index0 }}"
This made a bunch of files with whole list in the name of the files.
Demo file structure:
I made a fake
inventory.yml
for the occasion which will play everything on localhost:I fixed your
zones.csv
so that it does not contain parasite space we later have to trim:Since it is not part of your question, I created what should more or less look like your template in
templates/zones.rfc.j2
We can now put all this together with a playbook. The difficulty here is that reading the csv gives a list element for each line in your csv while we want to create a file for each networks given as columns.
If we read the csv into
output.csv
then we can getoutput_csv.list[0]
which is a dictionary:If we extract the key names and remove the
hostname
key, we have our list of networks. Henceoutput_csv.list[0].keys() | difference(['hosname'])
gives:The below playbook uses that technique with an alias in the task (i.e.
output_csv.list
=>server_list
) to match the variables used to make the template more readable.Running the playbook gives:
We can check all files have been created in the target dir:
I'll only show result from the first one here as a proof, you can check the others testing on your own environment: