2015-10-14 141 views
26

我有一個很大的Ansible playbook,在運行Docker時會創建Docker鏡像。我正在使用越來越多的數字作爲標籤來對它們進行版本化。目前,我必須在每個hosts:部分中指定。是否可以在Ansible中定義劇本全局變量?

我知道存在全局變量,但是通過搜索「可靠的」「全局變量」,我發現它們必須在劇本之外進行定義。是否有可能爲劇本定義全局變量?

回答

11

如果您使用的標籤/版本適用於所有主機,則使用group_vars/all是一個可行的選項。

如果修訂版本號特定於host_vars/host_name文件中的每個主機條目可能會更好。

如果您想讀取並初始化var,然後在每次播放後增加該值,在劇本中跨越播放(或您所說的每個主機)變得更難以持續保存該信息。例如,如果您正在尋找部署ň泊塢窗情況下,你可能會做一些動態庫存魔術這樣的:

- hosts: localhost 
    tasks: 
    - add_host: name=docker_{{item}} groups="dockers,other" tag={{item}} 
    with_sequence: start={{ext_def_start}} count={{ext_def_num}} 


- hosts: dockers 
    tasks: 
    - debug: var=tag 
+0

我希望在劇本中有變量,因爲我在Git中擁有它。然後我採取與變量共享庫存文件,並且必須適應它。我希望劇本中的變量,因爲一旦所有東西都設置好了,它們不會改變,但是庫存中的主機可能會改變。 – rabejens

+0

ansible處理變量的方法有點笨拙,但由於它嚴重依賴隱式包含(基於庫存)以及無法在整個劇本中輕鬆共享變量,所以這是可以理解的。正如我的例子所示,我已經使用庫存模塊將數據推送到庫存變量。事實上(參見set_fact模塊)在整個遊戲中保持不變,但它們是基於主機的。請記住,您始終可以編寫一個快速腳本(例如python)來生成動態庫存,包括變量和分組,這些庫存看起來完全符合您的需要。 – Petro026

+0

我一直在想這樣的事情(編寫一個腳本來生成庫存),我想我會這樣做。該劇本用於設置具有Spark/YARN支持,Cassandra數據庫和Zeppelin的基本Hadoop集羣,我可能會編寫一個腳本,首先要求用戶枚舉所有主機,然後設置哪些主機應該安裝哪個服務。 – rabejens

10

Ansible有一個默認all組,它足夠有趣地包含庫存文件中的所有主機。

因此,您可以使用任何主機組併爲主機組提供group_vars

如上一個鏈接所示,這些可以直接在庫存文件中定義,也可以包含在與庫存文件相同目錄級別的group_vars目錄中的組之後命名的單獨文件中。然後

一個例子的目錄結構可能看起來像:

-ansible 
|--inventory 
| |--group_vars 
| | |--all 
| | |--dev 
| | |--test 
| | |--prod 
| | |--webservers 
| | |--databases 
| |--dev 
| |--test 
| |--prod 
|--roles 
    ... 

dev的庫存文件,那麼可能看起來像:

​​

所有這些主機現在拿起任何主機特定的配置(可以在行中定義,或者像group_vars一樣可以放入host_vars文件夾中),還可以配置它們所在的特定組,例如,然後還可以繼承它們繼承的組,如dev b另外,默認情況下,all

然後,這可以用來以比每臺主機更粗糙的方式來配置事物。

諸如NTP服務器之類的事情可能需要全部定義,而DNS服務器可能希望在環境級別定義(如果您的網絡被分割爲dev,測試和生產他們可能需要不同的DNS服務器設置/etc/resolv.conf ),而不同類型的服務器可能具有不同的配置,如要安裝的軟件包列表等。最後,有些事情可能需要特定於主機,例如在複製組中設置MySQL服務器標識。

相反,如果你只是想確定劇本全局設置,而不是在廣告資源(並因此可能被其他劇本進行訪問),那麼你只需要一個vars塊在play定義,就像這樣:

- hosts: webservers 
    vars: 
    http_port: 80 
    tasks: 
    - name: Task1 to be ran against all the webservers 
     ... 

正如前面提到的,你可以隨時在這裏使用的all組太:

- hosts: all 
    vars: 
    ntp_pool: 
     - ntp1.domain 
     - ntp2.domain 
    tasks: 
    - name: Task1 to be ran against all the servers 
     ... 

雖然在一般,我會強烈建議使用角色構建什麼東西對某些^ h跑然後使用清單解釋哪些服務器是什麼類型,然後在清單級別使用group_vars目錄來包含這些主機組的所有變量。以這種方式做事可以幫助您將事情保持在合理的位置,並讓您輕鬆地重用您的代碼庫。

+0

嗯,把一個'[{主機: '所有',乏:{測試: 'hello'}},{hosts:'web':roles:[...]}'當我在'all'的設置階段後進入角色時,我仍然得到一個'未定義的變量'錯誤: ( – ThorSummoner

+0

@ThorSummoner我也收到了。我認爲這些變量只對在該主機組內部調用的任務有效。 –

+0

如果您有興趣,我會寫出我的解決方案。 –

0

是,全局變量有可能這樣,

樣品的Splunk安裝劇本

splunk/ 
    setup_splunk_playbook.yaml 
    roles/base 
      /tasks/main.yaml 
      /tasks/install.yaml 
     search_head 
      /tasks/configure.yaml 
     indexer 
      /tasks/configure.yaml 
     some_other_role 
      /tasks/some_task.yaml 
    hosts 
    config.yaml 

將您瓦爾成config.yaml

貓的Splunk/config.yaml

--- 
# global Splunk variables 
splunk_version: 7.0.0 
在你的劇本

,包括角色

貓setup_splunk_playbook.yaml

- hosts: "search_heads" 
    become_user: root 
    become: true 
    gather_facts: true 

    roles: 
    - base 
    - search_head 
在你的角色

,包括任務

貓的角色裏面的全局變量/ base/tasks/main.yaml

--- 
# install Splunk Base 

- name: include vars 
    include_vars: "{{ playbook_dir }}/config.yaml" 

- include: install.yaml 

瓦爾在現在的任務訪問,

貓的角色/基/任務/ install.yaml

- name: echo version 
    debug: splunk version is {{ splunk_version }} 
+0

在「hosts:」屬性中使用變量不起作用。 – hakre