mirror of
https://github.com/ansible-collections/community.general.git
synced 2024-09-14 20:13:21 +02:00
Allow the /etc/ansible/hosts file to contain groups and those group names to be used in place
of pattern names.
This commit is contained in:
parent
24d854e0bc
commit
bed29b7e11
3 changed files with 44 additions and 18 deletions
|
@ -23,7 +23,7 @@ DEFAULT_MODULE_NAME = 'ping'
|
||||||
DEFAULT_PATTERN = '*'
|
DEFAULT_PATTERN = '*'
|
||||||
DEFAULT_FORKS = 3
|
DEFAULT_FORKS = 3
|
||||||
DEFAULT_MODULE_ARGS = ''
|
DEFAULT_MODULE_ARGS = ''
|
||||||
DEFAULT_TIMEOUT = 60
|
DEFAULT_TIMEOUT = 10
|
||||||
DEFAULT_REMOTE_USER = 'root'
|
DEFAULT_REMOTE_USER = 'root'
|
||||||
DEFAULT_REMOTE_PASS = None
|
DEFAULT_REMOTE_PASS = None
|
||||||
|
|
||||||
|
|
|
@ -106,7 +106,7 @@ class PlayBook(object):
|
||||||
# actions where not all hosts have changed
|
# actions where not all hosts have changed
|
||||||
# though top-level tasks will pass in "None" here
|
# though top-level tasks will pass in "None" here
|
||||||
host_list = self.host_list
|
host_list = self.host_list
|
||||||
host_list = ansible.runner.Runner.parse_hosts(host_list)
|
(host_list, groups) = ansible.runner.Runner.parse_hosts(host_list)
|
||||||
|
|
||||||
# do not continue to run tasks on hosts that have had failures
|
# do not continue to run tasks on hosts that have had failures
|
||||||
new_hosts = []
|
new_hosts = []
|
||||||
|
@ -132,9 +132,9 @@ class PlayBook(object):
|
||||||
|
|
||||||
if self.verbose:
|
if self.verbose:
|
||||||
if not conditional:
|
if not conditional:
|
||||||
print "\nTASK [%s]" % (name)
|
print "\nTASK: %s" % (name)
|
||||||
else:
|
else:
|
||||||
print "\nNOTIFIED [%s]" % (name)
|
print "\nNOTIFIED: %s" % (name)
|
||||||
|
|
||||||
# load up an appropriate ansible runner to
|
# load up an appropriate ansible runner to
|
||||||
# run the task in parallel
|
# run the task in parallel
|
||||||
|
@ -240,10 +240,12 @@ class PlayBook(object):
|
||||||
tasks = pg['tasks']
|
tasks = pg['tasks']
|
||||||
handlers = pg['handlers']
|
handlers = pg['handlers']
|
||||||
user = pg.get('user', C.DEFAULT_REMOTE_USER)
|
user = pg.get('user', C.DEFAULT_REMOTE_USER)
|
||||||
self.host_list = pg.get('hosts', '/etc/ansible/hosts')
|
|
||||||
|
host_file = pg.get('hosts', '/etc/ansible/hosts')
|
||||||
|
self.host_list, groups = ansible.runner.Runner.parse_hosts(host_file)
|
||||||
|
|
||||||
if self.verbose:
|
if self.verbose:
|
||||||
print "PLAY: [%s] from [%s] ********** " % (pattern, self.host_list)
|
print "PLAY: [%s] ********** " % (pattern)
|
||||||
|
|
||||||
# run all the top level tasks, these get run on every node
|
# run all the top level tasks, these get run on every node
|
||||||
|
|
||||||
|
@ -252,7 +254,8 @@ class PlayBook(object):
|
||||||
pattern=pattern,
|
pattern=pattern,
|
||||||
task=task,
|
task=task,
|
||||||
handlers=handlers,
|
handlers=handlers,
|
||||||
remote_user=user)
|
remote_user=user
|
||||||
|
)
|
||||||
|
|
||||||
# handlers only run on certain nodes, they are flagged by _flag_handlers
|
# handlers only run on certain nodes, they are flagged by _flag_handlers
|
||||||
# above. They only run on nodes when things mark them as changed, and
|
# above. They only run on nodes when things mark them as changed, and
|
||||||
|
|
|
@ -68,7 +68,8 @@ class Runner(object):
|
||||||
'''
|
'''
|
||||||
|
|
||||||
# save input values
|
# save input values
|
||||||
self.host_list = self.parse_hosts(host_list)
|
|
||||||
|
self.host_list, self.groups = self.parse_hosts(host_list)
|
||||||
self.module_path = module_path
|
self.module_path = module_path
|
||||||
self.module_name = module_name
|
self.module_name = module_name
|
||||||
self.forks = forks
|
self.forks = forks
|
||||||
|
@ -78,19 +79,35 @@ class Runner(object):
|
||||||
self.verbose = verbose
|
self.verbose = verbose
|
||||||
self.remote_user = remote_user
|
self.remote_user = remote_user
|
||||||
self.remote_pass = remote_pass
|
self.remote_pass = remote_pass
|
||||||
self._tmp_paths = {}
|
# hosts in each group name in the inventory file
|
||||||
|
self._tmp_paths = {}
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def parse_hosts(cls, host_list):
|
def parse_hosts(cls, host_list):
|
||||||
''' parse the host inventory file if not sent as an array '''
|
'''
|
||||||
|
parse the host inventory file, returns (hosts, groups)
|
||||||
|
[groupname]
|
||||||
|
host1
|
||||||
|
host2
|
||||||
|
'''
|
||||||
|
|
||||||
# if the host list is given as a string load the host list
|
if type(host_list) == list:
|
||||||
# from a file, one host per line
|
return (host_list, {})
|
||||||
if type(host_list) != list:
|
|
||||||
host_list = os.path.expanduser(host_list)
|
|
||||||
return file(host_list).read().split("\n")
|
|
||||||
|
|
||||||
return host_list
|
host_list = os.path.expanduser(host_list)
|
||||||
|
lines = file(host_list).read().split("\n")
|
||||||
|
groups = {}
|
||||||
|
group_name = 'ungrouped'
|
||||||
|
results = []
|
||||||
|
for item in lines:
|
||||||
|
if item.startswith("["):
|
||||||
|
group_name = item.replace("[","").replace("]","").lstrip().rstrip()
|
||||||
|
groups[group_name] = []
|
||||||
|
else:
|
||||||
|
groups[group_name].append(item)
|
||||||
|
results.append(item)
|
||||||
|
|
||||||
|
return (results, groups)
|
||||||
|
|
||||||
|
|
||||||
def _matches(self, host_name, pattern=None):
|
def _matches(self, host_name, pattern=None):
|
||||||
|
@ -98,12 +115,18 @@ class Runner(object):
|
||||||
# a pattern is in fnmatch format but more than one pattern
|
# a pattern is in fnmatch format but more than one pattern
|
||||||
# can be strung together with semicolons. ex:
|
# can be strung together with semicolons. ex:
|
||||||
# atlanta-web*.example.com;dc-web*.example.com
|
# atlanta-web*.example.com;dc-web*.example.com
|
||||||
|
|
||||||
if host_name == '':
|
if host_name == '':
|
||||||
return False
|
return False
|
||||||
subpatterns = pattern.split(";")
|
subpatterns = pattern.split(";")
|
||||||
for subpattern in subpatterns:
|
for subpattern in subpatterns:
|
||||||
|
# the pattern could be a real glob
|
||||||
if fnmatch.fnmatch(host_name, subpattern):
|
if fnmatch.fnmatch(host_name, subpattern):
|
||||||
return True
|
return True
|
||||||
|
# or it could be a literal group name instead
|
||||||
|
if self.groups.has_key(subpattern):
|
||||||
|
if host_name in self.groups[subpattern]:
|
||||||
|
return True
|
||||||
return False
|
return False
|
||||||
|
|
||||||
def _connect(self, host):
|
def _connect(self, host):
|
||||||
|
@ -117,7 +140,7 @@ class Runner(object):
|
||||||
try:
|
try:
|
||||||
# try paramiko
|
# try paramiko
|
||||||
ssh.connect(host, username=self.remote_user, allow_agent=True,
|
ssh.connect(host, username=self.remote_user, allow_agent=True,
|
||||||
look_for_keys=True, password=self.remote_pass timeout=self.timeout)
|
look_for_keys=True, password=self.remote_pass, timeout=self.timeout)
|
||||||
return [ True, ssh ]
|
return [ True, ssh ]
|
||||||
except Exception, e:
|
except Exception, e:
|
||||||
# it failed somehow, return the failure string
|
# it failed somehow, return the failure string
|
||||||
|
@ -303,7 +326,7 @@ class Runner(object):
|
||||||
|
|
||||||
# find hosts that match the pattern
|
# find hosts that match the pattern
|
||||||
hosts = self.match_hosts(self.pattern)
|
hosts = self.match_hosts(self.pattern)
|
||||||
|
|
||||||
# attack pool of hosts in N forks
|
# attack pool of hosts in N forks
|
||||||
# _executor_hook does all of the work
|
# _executor_hook does all of the work
|
||||||
hosts = [ (self,x) for x in hosts ]
|
hosts = [ (self,x) for x in hosts ]
|
||||||
|
|
Loading…
Reference in a new issue