# HG changeset patch # User Tero Marttila # Date 1425376690 -7200 # Node ID d5e2d1d9716a73a084f3e82f093db98d68711289 # Parent 97fa1b086b36bf0f846a77e3b76e007002fb53d2 pvl.hosts.config: --hosts-include-trace to write out all included files diff -r 97fa1b086b36 -r d5e2d1d9716a pvl/hosts/__init__.py --- a/pvl/hosts/__init__.py Tue Mar 03 11:41:32 2015 +0200 +++ b/pvl/hosts/__init__.py Tue Mar 03 11:58:10 2015 +0200 @@ -1,4 +1,4 @@ -__version__ = '0.8.0a6' +__version__ = '0.8.0a7' from pvl.hosts.config import ( optparser, diff -r 97fa1b086b36 -r d5e2d1d9716a pvl/hosts/config.py --- a/pvl/hosts/config.py Tue Mar 03 11:41:32 2015 +0200 +++ b/pvl/hosts/config.py Tue Mar 03 11:58:10 2015 +0200 @@ -22,6 +22,9 @@ hosts.add_option('--hosts-include', metavar='PATH', help="Optional path for hosts includes, in addition to the host config dir") + + hosts.add_option('--hosts-include-trace', metavar='FILE', + help="Write out all included file paths") return hosts @@ -207,7 +210,7 @@ log.info("%s: include: %s", config_path, path) yield path -def apply_hosts_configs (options, path, name, config, parent=None, defaults={}): +def apply_hosts_configs (options, path, name, config, parent=None, defaults={}, include_trace=None): """ Load hosts from a configobj.Section (which can be the top-level ConfigObj). @@ -217,6 +220,7 @@ config configobj.Section parent parent section from included files or --hosts-domain defaults hierarchial section defaults + include_trace - optional list to append loaded files to """ # items in this section @@ -226,12 +230,15 @@ # process includes? if 'include' in section: - includes = section.pop('include').split() + # convert from unicode + includes = [str(include) for include in section.pop('include').split()] includes = list(parse_config_includes(options, path, includes)) # within our domain context - for host in apply_hosts_files(options, includes, parent=name, defaults=section): + for host in apply_hosts_files(options, includes, include_trace=include_trace, + parent=name, defaults=section + ): yield host else: includes = None @@ -304,26 +311,38 @@ return apply_hosts_configs(options, path, name, config, **opts) -def apply_hosts_file (options, path, **opts): +def apply_hosts_file (options, path, include_trace=None, **opts): """ Load Hosts from a file path. + + include_trace - optional list to append loaded files to """ + + if include_trace is not None: + log.debug("%s: include trace", path) + include_trace.append(path) try: file = open(path) except IOError as ex: raise HostConfigError(path, ex.strerror) - for host in apply_hosts_config(options, file, **opts): + for host in apply_hosts_config(options, file, include_trace=include_trace, **opts): yield host -def apply_hosts_directory (options, root, **opts): +def apply_hosts_directory (options, root, include_trace=None, **opts): """ Load Hosts from a directory, loading each file within the directory. + include_trace - optional list to append loaded files to + Skips .dotfiles. """ + if include_trace is not None: + log.debug("%s: include trace", root) + include_trace.append(root) + for name in sorted(os.listdir(root)): path = os.path.join(root, name) @@ -335,7 +354,7 @@ log.debug("%s: skip directory: %s", root, name) continue - for host in apply_hosts_file(options, path, **opts): + for host in apply_hosts_file(options, path, include_trace=include_trace, **opts): yield host def apply_hosts_files (options, files, **opts): @@ -359,10 +378,16 @@ Exits with status=2 if loading the confs fails. """ + + if options.hosts_include_trace: + log.debug("include trace") + include_trace = [ ] + else: + include_trace = None try: # load hosts from configs - hosts = list(apply_hosts_files(options, args)) + hosts = list(apply_hosts_files(options, args, include_trace=include_trace)) except HostConfigObjError as error: log.error("%s", error) log.error("\t%s", error.line_contents) @@ -371,6 +396,11 @@ except HostConfigError as error: log.error("%s", error) sys.exit(2) + + if options.hosts_include_trace: + with pvl.args.apply_file(options.hosts_include_trace, 'w') as file: + for include in include_trace: + print >>file, include # stable ordering return sorted(hosts, key=Host.sort_key) diff -r 97fa1b086b36 -r d5e2d1d9716a pvl/hosts/tests.py --- a/pvl/hosts/tests.py Tue Mar 03 11:41:32 2015 +0200 +++ b/pvl/hosts/tests.py Tue Mar 03 11:58:10 2015 +0200 @@ -18,6 +18,7 @@ hosts_charset = 'utf-8', hosts_domain = None, hosts_include = None, + hosts_include_trace = None, ) def assertHostEqual(self, host, host_str, attrs): @@ -185,7 +186,13 @@ def testApplyIncludePath(self): self.options.hosts_include = 'etc/hosts' - self.assertHostsEqual(config.apply_hosts_files(self.options, ['etc/zones/forward/test']), [ + include_trace = [ ] + + hosts = list(config.apply_hosts_files(self.options, ['etc/zones/forward/test'], + include_trace = include_trace, + )) + + self.assertHostsEqual(hosts, [ ('quux@asdf.test', dict( ip = ipaddr.IPAddress('192.0.2.5'), )), @@ -197,6 +204,15 @@ )), ]) + self.assertEqual(include_trace, [ + 'etc/zones/forward/test', + 'etc/zones/forward/test/asdf.test', + 'etc/zones/forward/test/test', + 'etc/hosts/test.d/', + 'etc/hosts/test.d/bar', + 'etc/hosts/test.d/foo', + ]) + def testApply(self): self.assertHostsEqual(config.apply(self.options, ['etc/hosts/example.com']), [ ('foo@example.com', dict(