Şablon modülü farklı değişkenlerle nasıl kullanılır?


93

Benim kullanım durumum şudur:

Bir şablon dosyam var ve bu şablondan 2 farklı dosya oluşturmak istiyorum, değişkenler her dosya için farklı bir değişken seti ile dolduruluyor.

Örneğin, şu satırı içeren dosyayı şablonlamak istediğimi varsayalım:

mkdir -p {{myTemplateVariable}}

Bu değişkeni "Dosya1" ve "Dosya2" ile doldurmanın uygun bir yolunu bulmak istiyorum. Gibi bir şey :

- name: template test 1
  template: 
        src=myTemplateFile
        dest=result1


- name: template test 2
  template: 
        src=myTemplateFile
        dest=result2

Burada kullanılacak değişkenin a = "Dosya1" ve ikincisi için b = "Dosya2" olduğunu ilk şablonlama için belirtebilirim.


Tüm tariflerimle yaptığım tam olarak bu mu, bu yoruma bakın stackoverflow.com/a/40189525/1571310 , bu yardımı umuyoruz!
Tecnocat

Yanıtlar:


52

Ansible 2.x için:

- name: template test
  template: 
    src: myTemplateFile
    dest: result1
  vars:
    myTemplateVariable: File1

- name: template test
  template: 
    src: myTemplateFile
    dest: result2
  vars:
    myTemplateVariable: File2

Ansible 1.x için:

Maalesef templatemodül, şablonun içinde kullanılabilen değişkenlere geçişi desteklemiyor. Bir özellik isteği vardı ancak reddedildi.

İki geçici çözüm düşünebilirim:

1. Dahil et

includeİfadesi destekleri değişkenleri geçirerek. Böylece, templategörevinizi fazladan bir dosyanın içine alabilir ve uygun parametrelerle iki kez dahil edebilirsiniz:

my_include.yml:

- name: template test
  template: 
        src=myTemplateFile
        dest=destination

main.yml:

- include: my_include.yml destination=result1 myTemplateVariable=File1

- include: my_include.yml destination=result2 myTemplateVariable=File2

2. myTemplateVariable'ı yeniden tanımlayın

Diğer bir yol, her templategörevden hemen önce myTemplateVariable'ı yeniden tanımlamaktır .

- set_fact:
     myTemplateVariable: File1

- name: template test 1
  template: 
        src=myTemplateFile
        dest=result1

- set_fact:
     myTemplateVariable: File2

- name: template test 2
  template: 
        src=myTemplateFile
        dest=result2

Cevap için teşekkür ederim. Ancak, geçici çözümler olmadan yapmak gerçekten imkansız mı? Şu anda aşağıdaki gibi bir şeyi deniyorum: stackoverflow.com/questions/26020465/… , ancak yine de bazı hatalar alıyorum (belki doğrudan ilişkili olmayabilir).
Kestemont Max 01

Evet, bunu bir döngü ile de yapabilirsiniz - yine de bu bir çözümdür. :)
udondan

14
artık gerekli değil. "vars" artık desteklenmektedir. Aşağıdaki @ konstantin-suvorov cevabına bakınız.
sonjz

123

Ansible 2.x vars:ile görevler ile kullanabilirsiniz .

Şablon test.j2:

mkdir -p {{myTemplateVariable}}

Başucu Kitabı:

- template: src=test.j2 dest=/tmp/File1
  vars:
    myTemplateVariable: myDirName

- template: src=test.j2 dest=/tmp/File2
  vars:
    myTemplateVariable: myOtherDir

Bu, farklı myTemplateVariabledeğerleri test.j2'ye aktaracaktır.


9
başlangıçta bir hata yaptım ve değişkenler vardı: şablon argümanlarının geri kalanı gibi girintili (src gibi :). Sanırım girinti düzeyi vars: şablonun değil, görevin olduğu anlamına gelir. Yani bunu sadece şablonlar değil, her yerde yapabilirsiniz. Güzel.
Greg

39

Bunu çok kolay yapabilirsin, bak benim süpervizör tarifime:

- name: Setup Supervisor jobs files
  template:
    src: job.conf.j2
    dest: "/etc/supervisor/conf.d/{{ item.job }}.conf"
    owner: root
    group: root
    force: yes
    mode: 0644
  with_items:
    - { job: bender, arguments: "-m 64", instances: 3 }
    - { job: mailer, arguments: "-m 1024", instances: 2 }
  notify: Ensure Supervisor is restarted

job.conf.j2:

[program:{{ item.job }}]
user=vagrant
command=/usr/share/nginx/vhosts/parclick.com/app/console rabbitmq:consumer {{ item.arguments }} {{ item.job }} -e prod
process_name=%(program_name)s_%(process_num)02d
numprocs={{ item.instances }}
autostart=true
autorestart=true
stderr_logfile=/var/log/supervisor/{{ item.job }}.stderr.log
stdout_logfile=/var/log/supervisor/{{ item.job }}.stdout.log

Çıktı:

TASK [Supervisor : Setup Supervisor jobs files] ********************************
changed: [loc.parclick.com] => (item={u'instances': 3, u'job': u'bender', u'arguments': u'-m 64'})
changed: [loc.parclick.com] => (item={u'instances': 2, u'job': u'mailer', u'arguments': u'-m 1024'})

Zevk almak!


Bu doğru cevap olarak işaretlenmelidir. Şu an desteklendiğinden beri
PoX

23

Bu, kullandığım bir çözüm / hack:

görevler / main.yml:

- name: parametrized template - a
  template:
    src: test.j2
    dest: /tmp/templateA
  with_items: var_a

- name: parametrized template - b
  template:
    src: test.j2
    dest: /tmp/templateB
  with_items: var_b

vars / main.yml

var_a:
  - 'this is var_a'
var_b:
  - 'this is var_b'

şablonlar / test.j2:

{{ item }}

Bunu çalıştırdıktan sonra this is var_a/ tmp / templateA ve this is var_b/ tmp / templateB dizinlerine girersiniz.

Temel olarak with_items, bir öğe listesindeki her bir öğe ile şablonu oluşturmak için kötüye kullanıyorsunuz. Bu işe yarar çünkü kullanırken listenin ne olduğunu kontrol edebilirsiniz with_items.

Bunun dezavantajı, itemşablonunuzda değişken adı olarak kullanmanız gerektiğidir.

Bu şekilde birden fazla değişkeni geçirmek istiyorsanız, liste öğeleriniz olarak şu şekilde dikteler yapabilirsiniz:

var_a:
  -
    var_1: 'this is var_a1'
    var_2: 'this is var_a2'
var_b:
  -
    var_1: 'this is var_b1'
    var_2: 'this is var_b2'

ve sonra şablonunuzda bunlara şu şekilde bakın:

{{ item.var_1 }}
{{ item.var_2 }}

1
Temiz çözüm, ancak kullanılacak şapkawith_items: '{{ var_a }}'
Peter Ajtai

8

Ben bu şekilde yaptım.

Görevlerde / main.yml

- name: template test
  template: 
        src=myTemplateFile.j2
        dest={{item}}
   with_dict: some_dict

ve vars / main.yml'de

some_dict:
  /path/to/dest1:
    var1: 1
    var2: 2
  /path/to/dest2:
    var1: 3
    var2: 4

ve şablonlarda / myTemplateFile.j2

some_var = {{ item.value.var1 }}
some_other_var = {{ item.value.var2 }}

Umarız bu sorununuzu çözer.


with_dictdaha iyi bir çözüm.
zx1986

1
- name: copy vhosts
  template: src=site-vhost.conf dest=/etc/apache2/sites-enabled/{{ item }}.conf
  with_items:
    - somehost.local
    - otherhost.local
  notify: restart apache

ÖNEMLİ: Bir öğenin yalnızca bir dizge olması gerekmediğini, istediğiniz kadar çok özelliğe sahip bir nesne olabileceğini unutmayın, böylece istediğiniz sayıda değişkeni aktarabilirsiniz.

Şablonda var:

<VirtualHost *:80>
    ServerAdmin me@example.org
    ServerName {{ item }}
    DocumentRoot /vagrant/public


    ErrorLog ${APACHE_LOG_DIR}/error-{{ item }}.log
    CustomLog ${APACHE_LOG_DIR}/access.log combined

</VirtualHost>

1
Onu nasıl nesne yapabilirim?
camdixon

1

Çözmem gereken benzer bir problem vardı, işte değişkenlerin şablon dosyalarına nasıl aktarılacağına dair basit bir çözüm, işin püf noktası değişkenden yararlanarak şablon dosyasını yazmak. Dosyanın her birine karşılık gelen değişkenler kümesini tutan bir sözlük oluşturmanız gerekir (liste de mümkündür). Daha sonra şablon dosyası içinden bunlara erişin.

aşağıya bakınız:

the template file: test_file.j2
# {{ ansible_managed }} created by xbalaji@gmail.com

{% set dkey  = (item | splitext)[0]  %}
{% set fname = test_vars[dkey].name  %}
{% set fip   = test_vars[dkey].ip    %}
{% set fport = test_vars[dkey].port  %}
filename: {{ fname }}
ip address: {{ fip }}
port: {{ fport }}

oyun kitabı

---
#
# file: template_test.yml
# author: xbalaji@gmail.com
#
# description: playbook to demonstrate passing variables to template files
#
# this playbook will create 3 files from a single template, with different
# variables passed for each of the invocation
#
# usage:
# ansible-playbook -i "localhost," template_test.yml

- name: template variables testing
  hosts: all
  gather_facts: false

  vars:
    ansible_connection: local
    dest_dir: "/tmp/ansible_template_test/"
    test_files:
      - file_01.txt
      - file_02.txt
      - file_03.txt
    test_vars:
      file_01:
        name: file_01.txt
        ip: 10.0.0.1
        port: 8001
      file_02:
        name: file_02.txt
        ip: 10.0.0.2
        port: 8002
      file_03:
        name: file_03.txt
        ip: 10.0.0.3
        port: 8003

  tasks:
    - name: copy the files
      template:
        src: test_file.j2
        dest: "{{ dest_dir }}/{{ item }}"
      with_items:
        - "{{ test_files }}"

0

Liste kullanan başka bir gerçek dünya örneği

php.ini için bir şablon özü

{% if 'cli/php.ini' in item.d %}
max_execution_time = 0
memory_limit = 1024M
{% else %}
max_execution_time = 300
memory_limit = 512M
{% endif %}

Bu var

php_templates:
  - { s: 'php.ini.j2', d: "/etc/php/{{php_version}}/apache2/php.ini" }
  - { s: 'php.ini.j2', d: "/etc/php/{{php_version}}/cli/php.ini" }

Sonra bununla dağıtıyorum

- name: push templated files
  template:
    src: "{{item.s}}"
    dest: "{{item.d}}"
    mode: "{{item.m | default(0644) }}"
    owner: "{{item.o | default('root') }}"
    group: "{{item.g | default('root') }}"
    backup: yes
  with_items: "{{php_templates}}"
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.