在python中有一個能夠實現批量管理服務器的工具:fabric,在本地和遠程機器上提供了一些基本的操做,而且能夠上傳/下載文件、執行sudo等功能。python
學習環境:ubuntu 12.10+python2.7web
安裝fabric:shell
1 經過apt安裝,apt-get install fabric 此版本是1.4.2ubuntu
2 經過pip安裝,pip install fabric 此版本是1.5.1,pip命令在python-pip包中api
farbic的環境變量:bash
fabric的環境變量有不少,存放在一個字典中,fabric.state.env,而它包含在fabric.api中,爲了方便,咱們通常使用env來指代環境變量。env環境變量能夠控制不少fabric的行爲,通常經過env.xxx能夠進行設置。服務器
fabric默認使用本地用戶經過ssh進行鏈接遠程機器,不過你能夠經過env.user變量進行覆蓋。當你進行ssh鏈接時,fabric會讓你交互的讓你輸入遠程機器密碼,若是你設置了env.password變量,則就不須要交互的輸入密碼。網絡
下面介紹一些經常使用的環境變量:app
abort_on_prompts 設置是否運行在交互模式下,例如會提示輸入密碼之類,默認是false
connection_attempts fabric嘗試鏈接到新服務器的次數,默認1次
cwd 目前的工做目錄,通常用來肯定cd命令的上下文環境
disable_known_hosts 默認是false,若是是true,則會跳過用戶知道的hosts文件
exclude_hosts 指定一個主機列表,在fab執行時,忽略列表中的機器
fabfile 默認值是fabfile.py在fab命令執行時,會自動搜索這個文件執行。
host_string 當fabric鏈接遠程機器執行run、put時,設置的user/host/port等
hosts 一個全局的host列表
keepalive 默認0 設置ssh的keepalive
loacl_user 一個只讀的變量,包含了本地的系統用戶,同user變量同樣,可是user能夠修改
parallel 默認false,若是是true則會並行的執行全部的task
pool_size 默認0 在使用parallel執行任務時設置的進程數
password ssh遠程鏈接時使用的密碼,也能夠是在使用sudo時使用的密碼
passwords 一個字典,能夠爲每一臺機器設置一個密碼,key是ip,value是密碼
path 在使用run/sudo/local執行命令時設置的$PATH環境變量
port 設置主機的端口
roledefs 一個字典,設置主機名到規則組的映射
roles 一個全局的role列表
shell 默認是/bin/bash -1 -c 在執行run命令時,默認的shell環境
skip_bad_hosts 默認false,爲ture時,會致使fab跳過沒法鏈接的主機
sudo_prefix 默認值"sudo -S -p '%(sudo_prompt)s' " % env 執行sudo命令時調用的sudo環境
sudo_prompt 默認值"sudo password:"
timeout 默認10 網絡鏈接的超時時間
user ssh使用哪一個用戶登陸遠程主機python2.7
fabric的執行模式:
執行策略:fabric默認是單一的,串行的執行函數,雖然有一個paralle模式可供你選擇。默認的行爲遵循如下優先級規則:
1 一個task列表被建立,經過命令行傳遞給fab
2 針對每個task,都有一個主機列表經過變量設置
3 task列表按順序執行每一個task在主機列表中的主機上執行一遍
4 若是主機列表爲空,則默認在本地執行,也是執行一次
設置主機列表的方法:
1 hosts,在上下文環境中咱們稱hosts爲「host strings」,strings指定了username、hostname、port等組合username@hostname:port。username和port能夠省略,則默認使用本地用戶和22端口。
2 roles,host strings映射單個主機,可是有時候你想把一批主機加入一個組中,roles則提供了一個定義一系列主機的方法,這個映射能夠經過env.rolesdefs來設置,它必須經過fabfile進行設置才能夠使用。env.roledefs['webservers'] = ['www1', 'www2', 'www3']。
怎樣實際構造主機列表:
1 經過全局變量env:env.hosts = ['host1', 'host2']
2 經過命令行全局設置:fab -H IP1,IP2 Task。效果和env.hosts同樣
全局設置主機列表,只有在你須要全部的task運行在相同的主機上時。若是每一個主機運行的task不同呢?
3 在命令行爲每一個task設置主機列表:fab mytask:hosts="host1;host2"
若是一個task老是運行在預先固定好的主機上面,你可能但願把這些主機在fabfile中指定到固定的task上。這個功能能夠經過hosts或者roles實現。
4 在fabfile內部爲每一個task設施主機列表。在下面的模式下即便設置了-H或者env.hosts也會被忽略掉,可是不會忽略在命令行鍼對每一個task的設置。
@hosts('host1', 'host2')
def mytask():
run('ls /var/www')
主機列表的生效順序以下:先單個task,再全局list
1 fab mytask:host=host1
2 @hosts('host1')
3 env.hosts = ['host1']
4 --hosts=host1
排除指定的主機:fab exclude_hosts="a;b" 或者 -x a,b
使用execute執行task:
目前接觸到得都是經過fab設置task來執行,咱們也能夠假裝task就像在fabfile中的元數據同樣,不用經過fab設置運行task
@roles('db')
def migrate():
pass
def deploy():
pass
execute(migrate)
fab 選項和參數:fab能夠在命令行設置一些參數來影響fabric的行爲,做用和設置fab環境變量同樣
-a, --no_agent env.no_agent=true
-A, --forward-agent env.foward_agent=true
--abort-on-prompts env.abort_on_prompts=true
-d COMMAND, --display=COMMAND
--connection-attempts=M, -n M env.connection_attempts=M
-f FABFILE, --fabfile=FABFILE 默認fabfile.py
-H HOSTS, --hosts=HOSTS env.hosts=hosts
-x HOSTS, --exclude-hosts=HOSTS env.exclude_hosts=host
--keepalive=KEEPALIVE env.keepalive=KEEPALIVE
-l, --list
-p PASSWORD, --password=PASSWORD env.password
-P, --parallel env.parallel =true
-R ROLES, --roles=ROLES env.roles
-s SHELL, --shell=SHELL env.shell
--skip-bad-hosts env.skip_bad_hosts
--timeout=N, -t N env.timeout
-u USER, --user=USER env.user
-z, --pool-size env.pool_size
Because Fabric is just Python, you can import its components any way you want. However, for the purposes of encapsulation and convenience (and to make life easier for Fabric’s packaging script) Fabric’s public API is maintained in the fabric.api module.
from fabric.api import *
core API:
1 打印帶顏色的字符串
from fabric.colors import *
print(green("This text is green!"))
2 一些基本操做
fabric.operations.get(remote_path, local_path=None)
Download one or more files from a remote host.remote能夠是目錄或者文件,cd 遠程機器 lcd本地機器
fabric.operations.local(command, capture=False, shell=None)
Run a command on the local system. 運用subprocess在shell=true的狀況下執行命令。
fabric.operations.open_shell(command=None)
Invoke a fully interactive shell on the remote end.交互式的調用遠程終端的shell
fabric.operations.prompt(text, key=None, default='', validate=None)
Prompt user with text and return the input (like raw_input).
fabric.operations.put(local_path=None, remote_path=None, use_sudo=False,mirror_local_mode=False, mode=None)
Upload one or more files to a remote host. 上傳一個或者多個文件,local_path本地文件或者目錄,
fabric.operations.reboot(wait=120)
Reboot the remote system.
fabric.operations.run(command, shell=True, pty=True, combine_stderr=None, quiet=False, warn_only=False, stdout=None, stderr=None)
Run a shell command on a remote host.
fabric.operations.sudo(command, shell=True, pty=True, combine_stderr=None, user=None, quiet=False, warn_only=False, stdout=None, stderr=None, group=None)
Run a shell command on a remote host, with superuser privileges.
3 上下文環境管理,主要使用with語句
fabric.context_managers.cd(path)
Context manager that keeps directory state when calling remote operations,能夠在run sudo get put中使用,cd只能使用在遠程服務器上,本地使用lcd。
with cd('/var/www'):
run('ls') # cd /var/www && ls
fabric.context_managers.lcd(path)
Context manager for updating local current working directory.同cd,不過是在本地改變目錄
fabric.context_managers.path(path, behavior='append')
Append the given path to the PATH used to execute any wrapped commands
fabric.context_managers.prefix(command)
Prefix all wrapped run/sudo commands with given command plus &&.在run或者sudo執行的命令前加前綴,經過&&進行鏈接
fabric.context_managers.settings(*args, **kwargs)
Nest context managers and/or override env variables.
4 有趣的工具
fabric.contrib.project.rsync_project(*args, **kwargs)
Synchronize a remote directory with the current project directory via rsync
fabric.contrib.project.upload_project(local_dir=None, remote_dir='')
Upload the current project to a remote system via tar/gzip
爲了避免誤導你們,一些英文未翻譯,參看官方文檔:http://docs.fabfile.org/en/1.5/#documentation