Take the 2-minute tour ×
Server Fault is a question and answer site for system and network administrators. It's 100% free, no registration required.

i am working on Fabric for my deploying tools and also distribute the command on multiple hosts. but i don't know how can define a complex hosts in my fabfile.py

for example: i have 4 servers. serverA, serverB, serverC, serverD

def prod():
    env.hosts = ["serverA', "serverB" ]

def dev():
    env.hosts = ["serverC' "serverD"]

def all():
    prod()
    dev()

is it possible for me to run a command on all hosts without define again?

EX: fab all {command}
share|improve this question

2 Answers 2

up vote 1 down vote accepted

You could take a look at defining roles for your environment.

from fabric.api import env, run
from fabric.decorators import task

env.roledefs = {
    'prod': ['ServerA', 'ServerB'],
    'dev': ['ServerC', 'ServerD'],
    'envC': ['ServerE', 'ServerF']
}

env.roledefs['all'] = [h for r in env.roledefs.values() for h in r]


@task
def hostname():
    run('hostname -f')

This would mean that your will now have to issue your fabric calls like this:

fab -R prod hostname
fab -R dev hostname
fab -R all hostname
fab -R dev,envC hostname
share|improve this answer
    
It does not work on my side. here is my fabric version: > $ fab -V > Fabric 1.8.0 > Paramiko 1.12.0 > $ fabb -R all cmd:"ls" > Fatal error: The following specified roles do not exist: all > Aborting. –  Calvin Pham Jan 15 at 6:22
    
I edited the answer and added the full contents of the fabfile. I tested it with Fabric 1.8.1 and Paramiko 1.12.1. –  user76776 Jan 15 at 16:17
    
it works. Thank you so much. –  Calvin Pham Jan 19 at 4:17
    
Thank you so much because of your kind. i wish can vote you more :) –  Calvin Pham Jan 20 at 16:56

Thanks user76776 a lot for your help.

Actually my config for host is more complicated a bit.

env.roledefs = {
    'webA': ['ServerA', 'ServerB'],
    'dbA': ['ServerC', 'ServerD'],
    'webB': ['serverF', 'ServerK'],
    'dbB': ['serverX', 'ServerV']  }

env.roledefs['all'] = [h for r in env.roledefs.values() for h in r]

webA and dbA are the servers for Thailand (system for Thailand) webB and dbB are the servers for Vietnam (system for Vietnam)

case 1: execute a command on all servers (it works as your recommendation)

case 2: how can i execute a command on all WEB servers (include 2 countries - webA and webB)? case 3: how can i execute a command on only Thailand's servers (included webA and dbA)?

sorry if my question is bad as i am new with fabric.

Thanks so much for your help.

share|improve this answer
    
I added an example for case2 on the original answer. You basically just have to pass all the roles to the -R flag. For case3, I'm afraid that you will need to either pass all the hostnames to the -H flag, or rethink how you want to structure your role definitions. –  user76776 Jan 20 at 8:58

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.