def main(argv=sys.argv):
    p = option_parser()
    (options, args) = p.parse_args(argv[1:])

    llvl = logging.DEBUG if options.debug else logging.INFO
    logging.basicConfig(level=llvl)

    if not args:
        if options.list:
            sys.stdout.write(
                "Supported config types: " + ", ".join(A.list_types()) + "\n"
            )
            sys.exit(0)
        else:
            p.print_usage()
            sys.exit(-1)

    data = A.load(args, options.itype, options.merge)

    if options.args:
        diff = A.loads(options.args, options.atype)
        data.update(diff, options.merge)

    if options.output:
        cp = A.find_loader(options.output, options.otype)
        cp.dump(data, options.output)
    else:
        assert options.otype is not None, \
            "Please specify Output type w/ -O/--otype option"

        cp = A.find_loader(None, options.otype)
        sys.stdout.write(cp.dumps(data))
def _parse_args(argv):
    """
    Show supported config format types or usage.

    :param argv: Argument list to parse or None (sys.argv will be set).
    :return: argparse.Namespace object or None (exit before return)
    """
    parser = make_parser()
    args = parser.parse_args(argv)
    LOGGER.setLevel(to_log_level(args.loglevel))

    if not args.inputs:
        if args.list:
            tlist = ", ".join(API.list_types())
            _exit_with_output("Supported config types: " + tlist)
        elif args.env:
            cnf = os.environ.copy()
            _output_result(cnf, args.output, args.otype or "json", None, None)
            sys.exit(0)
        else:
            parser.print_usage()
            sys.exit(1)

    if args.validate and args.schema is None:
        _exit_with_output("--validate option requires --scheme option", 1)

    return args
def option_parser(defaults=DEFAULTS, usage=USAGE):
    ctypes = A.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = A.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    af_help = """Explicitly select type of argument to provide configs from %s.

If this option is not set, original parser is used: 'K:V' will become {K: V},
'K:V_0,V_1,..' will become {K: [V_0, V_1, ...]}, and 'K_0:V_0;K_1:V_1' will
become {K_0: V_0, K_1: V_1} (where the tyep of K is str, type of V is one of
Int, str, etc.""" % ctypes_s

    p = optparse.OptionParser(usage)
    p.set_defaults(**defaults)

    p.add_option("-D", "--debug", action="store_true", help="Debug mode")
    p.add_option("-L", "--list", help="List supported config types",
                 action="store_true")
    p.add_option("-o", "--output", help="Output file path")
    p.add_option("-I", "--itype", choices=ctypes, help=(type_help % "Input"))
    p.add_option("-O", "--otype", choices=ctypes, help=(type_help % "Output"))
    p.add_option("-M", "--merge", choices=mts, help=mt_help)

    p.add_option("-A", "--args", help="Argument configs to override")
    p.add_option("", "--atype", choices=ctypes, help=af_help)

    return p
Exemple #4
0
def main(argv=sys.argv):
    """
    :param argv: Argument list to parse [sys.argv]
    """
    parser = option_parser()
    (options, args) = parser.parse_args(argv[1:])

    A.set_loglevel(to_log_level(options.loglevel))

    if not args:
        if options.list:
            tlist = ", ".join(A.list_types()) + "\n"
            sys.stdout.write("Supported config types: " + tlist)
            sys.exit(0)
        else:
            parser.print_usage()
            sys.exit(-1)

    data = data = os.environ.copy() if options.env else A.container()
    diff = A.load(args, options.itype, ignore_missing=options.ignore_missing,
                  merge=options.merge, ac_template=options.template)
    data.update(diff)

    if options.args:
        diff = A.loads(options.args, options.atype,
                       ac_template=options.template, ac_context=data)
        data.update(diff, options.merge)

    if options.get:
        (data, err) = A.get(data, options.get)
        if err:
            raise RuntimeError(err)

    if options.set:
        A.set_(data, *(options.set.split('=')))

    if options.output:
        cparser = A.find_loader(options.output, options.otype)
        if cparser is None:
            raise RuntimeError("No suitable dumper was found for %s",
                               options.output)

        cparser.dump(data, options.output)
    else:
        # TODO: Reuse input type automatically detected as it's impossible to
        # detect output type w/o options.output.
        if options.otype is None:
            if options.itype is None:
                raise RuntimeError("Please specify input and/or output type "
                                   "with -I (--itype) or -O (--otype) option")
            else:
                options.otype = options.itype

        cparser = A.find_loader(None, options.otype)
        sys.stdout.write(cparser.dumps(data))
Exemple #5
0
def _show_psrs():
    """Show list of info of parsers available
    """
    sep = os.linesep

    types = "Supported types: " + ", ".join(API.list_types())
    cids = "IDs: " + ", ".join(c for c, _ps in API.list_by_cid())

    x_vs_ps = ["  %s: %s" % (x, ", ".join(p.cid() for p in ps))
               for x, ps in API.list_by_extension()]
    exts = "File extensions:" + sep + sep.join(x_vs_ps)

    _exit_with_output(sep.join([types, exts, cids]))
Exemple #6
0
def _show_psrs():
    """Show list of info of parsers available
    """
    sep = os.linesep

    types = "Supported types: " + ", ".join(API.list_types())
    cids = "IDs: " + ", ".join(c for c, _ps in API.list_by_cid())

    x_vs_ps = ["  %s: %s" % (x, ", ".join(p.cid() for p in ps))
               for x, ps in API.list_by_extension()]
    exts = "File extensions:" + sep + sep.join(x_vs_ps)

    _exit_with_output(sep.join([types, exts, cids]))
Exemple #7
0
def main(argv=sys.argv):
    """
    :param argv: Argument list to parse [sys.argv]
    """
    parser = option_parser()
    (options, args) = parser.parse_args(argv[1:])

    A.set_loglevel(to_log_level(options.loglevel))

    if not args:
        if options.list:
            tlist = ", ".join(A.list_types()) + "\n"
            sys.stdout.write("Supported config types: " + tlist)
            sys.exit(0)
        else:
            parser.print_usage()
            sys.exit(-1)

    data = A.load(args,
                  options.itype,
                  options.merge,
                  ignore_missing=options.ignore_missing)

    if options.args:
        diff = A.loads(options.args, options.atype)
        data.update(diff, options.merge)

    if options.get:
        (data, err) = A.get(data, options.get)
        if err:
            raise RuntimeError(err)

    if options.set:
        A.set_(data, *(options.set.split('=')))

    if options.output:
        cparser = A.find_loader(options.output, options.otype)
        cparser.dump(data, options.output)
    else:
        # TODO: Reuse input type automatically detected as it's impossible to
        # detect output type w/o options.output.
        if options.otype is None:
            if options.itype is None:
                raise RuntimeError("Please specify input and/or output type "
                                   "with -I (--itype) or -O (--otype) option")
            else:
                options.otype = options.itype

        cparser = A.find_loader(None, options.otype)
        sys.stdout.write(cparser.dumps(data))
Exemple #8
0
    def test_38_load_w_validation_yaml(self):
        if "yml" not in TT.list_types():
            skip_test()

        cnf_path = os.path.join(self.workdir, "cnf.yml")
        scm_path = os.path.join(self.workdir, "scm.yml")
        TT.dump(CNF_0, cnf_path)
        TT.dump(SCM_0, scm_path)

        cnf_2 = TT.load(cnf_path, ac_context={}, ac_schema=scm_path)

        self.assertEqual(cnf_2["name"], CNF_0["name"])
        self.assertEqual(cnf_2["a"], CNF_0["a"])
        self.assertEqual(cnf_2["b"]["b"], CNF_0["b"]["b"])
        self.assertEqual(cnf_2["b"]["c"], CNF_0["b"]["c"])
Exemple #9
0
def _check_options_and_args(parser, options, args):
    """
    Show supported config format types or usage.

    :param parser: Option parser object
    :param options: Options optparse.OptionParser.parse_args returns
    :param args: Arguments optparse.OptionParser.parse_args returns
    """
    if not args:
        if options.list:
            tlist = ", ".join(API.list_types())
            _exit_with_output("Supported config types: " + tlist)
        else:
            parser.print_usage()
            sys.exit(1)

    if options.validate and options.schema is None:
        _exit_with_output("--validate option requires --scheme option", 1)
Exemple #10
0
def _check_options_and_args(parser, options, args):
    """
    Show supported config format types or usage.

    :param parser: Option parser object
    :param options: Options optparse.OptionParser.parse_args returns
    :param args: Arguments optparse.OptionParser.parse_args returns
    """
    if not args:
        if options.list:
            tlist = ", ".join(API.list_types())
            _exit_with_output("Supported config types: " + tlist)
        else:
            parser.print_usage()
            sys.exit(1)

    if options.validate and options.schema is None:
        _exit_with_output("--validate option requires --scheme option", 1)
 def test_20_open_xml_file(self):
     if "xml" in TT.list_types():
         self._load_and_dump_with_opened_files("a.xml", 'rb', 'wb')
Exemple #12
0
def option_parser(defaults=None, usage=USAGE):
    """
    Make up an option and arguments parser.

    :param defaults: Default option values
    :param usage: Usage text
    """
    defaults = dict(loglevel=1, list=False, output=None, itype=None,
                    otype=None, atype=None, merge=A.MS_DICTS,
                    ignore_missing=False)

    ctypes = A.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = A.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    af_help = """Explicitly select type of argument to provide configs from %s.

If this option is not set, original parser is used: 'K:V' will become {K: V},
'K:V_0,V_1,..' will become {K: [V_0, V_1, ...]}, and 'K_0:V_0;K_1:V_1' will
become {K_0: V_0, K_1: V_1} (where the tyep of K is str, type of V is one of
Int, str, etc.""" % ctypes_s

    get_help = ("Specify key path to get part of config, for example, "
                "'--get a.b.c' to config {'a': {'b': {'c': 0, 'd': 1}}} "
                "gives 0 and '--get a.b' to the same config gives "
                "{'c': 0, 'd': 1}.")
    set_help = ("Specify key path to set (update) part of config, for "
                "example, '--set a.b.c=1' to a config {'a': {'b': {'c': 0, "
                "'d': 1}}} gives {'a': {'b': {'c': 1, 'd': 1}}}.")

    parser = optparse.OptionParser(usage, version="%%prog %s" % G.VERSION)
    parser.set_defaults(**defaults)

    parser.add_option("-L", "--list", help="List supported config types",
                      action="store_true")
    parser.add_option("-o", "--output", help="Output file path")
    parser.add_option("-I", "--itype", choices=ctypes,
                      help=(type_help % "Input"))
    parser.add_option("-O", "--otype", choices=ctypes,
                      help=(type_help % "Output"))
    parser.add_option("-M", "--merge", choices=mts, help=mt_help)

    parser.add_option("-A", "--args", help="Argument configs to override")
    parser.add_option("", "--atype", choices=ctypes, help=af_help)

    parser.add_option("", "--get", help=get_help)
    parser.add_option("", "--set", help=set_help)

    parser.add_option("-x", "--ignore-missing", action="store_true",
                      help="Ignore missing input files")

    parser.add_option("-s", "--silent", action="store_const", dest="loglevel",
                      const=0, help="Silent or quiet mode")
    parser.add_option("-q", "--quiet", action="store_const", dest="loglevel",
                      const=0, help="Same as --silent option")
    parser.add_option("-v", "--verbose", action="store_const", dest="loglevel",
                      const=2, help="Verbose mode")

    return parser
def make_parser(defaults=None):
    """
    :param defaults: Default option values
    """
    if defaults is None:
        defaults = DEFAULTS

    ctypes = API.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = API.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    parser = argparse.ArgumentParser(usage=USAGE)
    parser.set_defaults(**defaults)

    parser.add_argument("inputs", type=str, nargs='*', help="Input files")
    parser.add_argument("--version", action="version",
                        version="%%(prog)s %s" % anyconfig.globals.VERSION)

    lpog = parser.add_argument_group("List specific options")
    lpog.add_argument("-L", "--list", action="store_true",
                      help="List supported config types")

    spog = parser.add_argument_group("Schema specific options")
    spog.add_argument("--validate", action="store_true",
                      help="Only validate input files and do not output. "
                           "You must specify schema file with -S/--schema "
                           "option.")
    spog.add_argument("--gen-schema", action="store_true",
                      help="Generate JSON schema for givne config file[s] "
                           "and output it instead of (merged) configuration.")

    gspog = parser.add_argument_group("Query/Get/set options")
    gspog.add_argument("-Q", "--query", help=_QUERY_HELP)
    gspog.add_argument("--get", help=_GET_HELP)
    gspog.add_argument("--set", help=_SET_HELP)

    parser.add_argument("-o", "--output", help="Output file path")
    parser.add_argument("-I", "--itype", choices=ctypes, metavar="ITYPE",
                        help=(type_help % "Input"))
    parser.add_argument("-O", "--otype", choices=ctypes, metavar="OTYPE",
                        help=(type_help % "Output"))
    parser.add_argument("-M", "--merge", choices=mts, metavar="MERGE",
                        help=mt_help)
    parser.add_argument("-A", "--args", help="Argument configs to override")
    parser.add_argument("--atype", choices=ctypes, metavar="ATYPE",
                        help=_ATYPE_HELP_FMT % ctypes_s)

    cpog = parser.add_argument_group("Common options")
    cpog.add_argument("-x", "--ignore-missing", action="store_true",
                      help="Ignore missing input files")
    cpog.add_argument("-T", "--template", action="store_true",
                      help="Enable template config support")
    cpog.add_argument("-E", "--env", action="store_true",
                      help="Load configuration defaults from "
                           "environment values")
    cpog.add_argument("-S", "--schema", help="Specify Schema file[s] path")
    cpog.add_argument("-v", "--verbose", action="count", dest="loglevel",
                      help="Verbose mode; -v or -vv (more verbose)")
    return parser
Exemple #14
0
def parse_args(argv=None, defaults=None):
    """
    Make up an option and arguments parser.

    :param defaults: Default option values
    """
    if defaults is None:
        defaults = DEFAULTS

    ctypes = API.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = API.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    parser = optparse.OptionParser(USAGE, version="%%prog %s" %
                                   anyconfig.globals.VERSION)
    parser.set_defaults(**defaults)

    lpog = optparse.OptionGroup(parser, "List specific options")
    lpog.add_option("-L", "--list", help="List supported config types",
                    action="store_true")
    parser.add_option_group(lpog)

    spog = optparse.OptionGroup(parser, "Schema specific options")
    spog.add_option("", "--validate", action="store_true",
                    help="Only validate input files and do not output. "
                         "You must specify schema file with -S/--schema "
                         "option.")
    spog.add_option("", "--gen-schema", action="store_true",
                    help="Generate JSON schema for givne config file[s] "
                         "and output it instead of (merged) configuration.")
    parser.add_option_group(spog)

    gspog = optparse.OptionGroup(parser, "Get/set options")
    gspog.add_option("", "--get", help=_GET_HELP)
    gspog.add_option("", "--set", help=_SET_HELP)
    parser.add_option_group(gspog)

    parser.add_option("-o", "--output", help="Output file path")
    parser.add_option("-I", "--itype", choices=ctypes,
                      help=(type_help % "Input"))
    parser.add_option("-O", "--otype", choices=ctypes,
                      help=(type_help % "Output"))
    parser.add_option("-M", "--merge", choices=mts, help=mt_help)
    parser.add_option("-A", "--args", help="Argument configs to override")
    parser.add_option("", "--atype", choices=ctypes,
                      help=_ATYPE_HELP_FMT % ctypes_s)

    parser.add_option("-x", "--ignore-missing", action="store_true",
                      help="Ignore missing input files")
    parser.add_option("-T", "--template", action="store_true",
                      help="Enable template config support")
    parser.add_option("-E", "--env", action="store_true",
                      help="Load configuration defaults from "
                           "environment values")
    parser.add_option("-S", "--schema", help="Specify Schema file[s] path")
    parser.add_option("-s", "--silent", action="store_const", dest="loglevel",
                      const=0, help="Silent or quiet mode")
    parser.add_option("-q", "--quiet", action="store_const", dest="loglevel",
                      const=0, help="Same as --silent option")
    parser.add_option("-v", "--verbose", action="store_const", dest="loglevel",
                      const=2, help="Verbose mode")

    if argv is None:
        argv = sys.argv

    (options, args) = parser.parse_args(argv[1:])
    return (parser, options, args)
Exemple #15
0
 def test_30_open_bson_file(self):
     if "bson" in TT.list_types():
         self._load_and_dump_with_opened_files("a.bson", 'rb', 'wb')
Exemple #16
0
 def test_40_open_yaml_file(self):
     if "yaml" in TT.list_types():
         self._load_and_dump_with_opened_files("a.yaml")
         self._load_and_dump_with_opened_files("a.yml")
Exemple #17
0
 def test_20_open_xml_file(self):
     if "xml" in TT.list_types():
         self._load_and_dump_with_opened_files("a.xml", 'rb', 'wb')
Exemple #18
0
def option_parser(defaults=None, usage=USAGE):
    """
    Make up an option and arguments parser.

    :param defaults: Default option values
    :param usage: Usage text
    """
    defaults = dict(loglevel=1, list=False, output=None, itype=None,
                    otype=None, atype=None, merge=A.MS_DICTS,
                    ignore_missing=False, template=False, env=False,
                    schema=None, validate=False, gen_schema=False)

    ctypes = A.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = A.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    af_help = """Explicitly select type of argument to provide configs from %s.

If this option is not set, original parser is used: 'K:V' will become {K: V},
'K:V_0,V_1,..' will become {K: [V_0, V_1, ...]}, and 'K_0:V_0;K_1:V_1' will
become {K_0: V_0, K_1: V_1} (where the tyep of K is str, type of V is one of
Int, str, etc.""" % ctypes_s

    get_help = ("Specify key path to get part of config, for example, "
                "'--get a.b.c' to config {'a': {'b': {'c': 0, 'd': 1}}} "
                "gives 0 and '--get a.b' to the same config gives "
                "{'c': 0, 'd': 1}.")
    set_help = ("Specify key path to set (update) part of config, for "
                "example, '--set a.b.c=1' to a config {'a': {'b': {'c': 0, "
                "'d': 1}}} gives {'a': {'b': {'c': 1, 'd': 1}}}.")

    parser = optparse.OptionParser(usage, version="%%prog %s" %
                                   anyconfig.globals.VERSION)
    parser.set_defaults(**defaults)

    lpog = optparse.OptionGroup(parser, "List specific options")
    lpog.add_option("-L", "--list", help="List supported config types",
                    action="store_true")
    parser.add_option_group(lpog)

    spog = optparse.OptionGroup(parser, "Schema specific options")
    spog.add_option("", "--validate", action="store_true",
                    help="Only validate input files and do not output. "
                         "You must specify schema file with -S/--schema "
                         "option.")
    spog.add_option("", "--gen-schema", action="store_true",
                    help="Generate JSON schema for givne config file[s] "
                         "and output it instead of (merged) configuration.")
    parser.add_option_group(spog)

    gspog = optparse.OptionGroup(parser, "Get/set options")
    gspog.add_option("", "--get", help=get_help)
    gspog.add_option("", "--set", help=set_help)
    parser.add_option_group(gspog)

    parser.add_option("-o", "--output", help="Output file path")
    parser.add_option("-I", "--itype", choices=ctypes,
                      help=(type_help % "Input"))
    parser.add_option("-O", "--otype", choices=ctypes,
                      help=(type_help % "Output"))
    parser.add_option("-M", "--merge", choices=mts, help=mt_help)
    parser.add_option("-A", "--args", help="Argument configs to override")
    parser.add_option("", "--atype", choices=ctypes, help=af_help)

    parser.add_option("-x", "--ignore-missing", action="store_true",
                      help="Ignore missing input files")
    parser.add_option("-T", "--template", action="store_true",
                      help="Enable template config support")
    parser.add_option("-E", "--env", action="store_true",
                      help="Load configuration defaults from "
                           "environment values")
    parser.add_option("-S", "--schema", help="Specify Schema file[s] path")
    parser.add_option("-s", "--silent", action="store_const", dest="loglevel",
                      const=0, help="Silent or quiet mode")
    parser.add_option("-q", "--quiet", action="store_const", dest="loglevel",
                      const=0, help="Same as --silent option")
    parser.add_option("-v", "--verbose", action="store_const", dest="loglevel",
                      const=2, help="Verbose mode")

    return parser
Exemple #19
0
def main(argv=None):
    """
    :param argv: Argument list to parse or None (sys.argv will be set).
    """
    if argv is None:
        argv = sys.argv

    parser = option_parser()
    (options, args) = parser.parse_args(argv[1:])

    A.set_loglevel(to_log_level(options.loglevel))

    if not args:
        if options.list:
            tlist = ", ".join(A.list_types()) + "\n"
            sys.stdout.write("Supported config types: " + tlist)
            sys.exit(0)
        else:
            parser.print_usage()
            sys.exit(1)

    if options.validate and options.schema is None:
        sys.stderr.write("--validate option requires --scheme option")
        sys.exit(1)

    data = data = os.environ.copy() if options.env else A.container()
    diff = A.load(args, options.itype,
                  ignore_missing=options.ignore_missing,
                  merge=options.merge, ac_template=options.template,
                  ac_schema=options.schema)

    if diff is None:
        sys.stderr.write("Validation failed")
        sys.exit(1)

    data.update(diff)

    if options.args:
        diff = A.loads(options.args, options.atype,
                       ac_template=options.template, ac_context=data)
        data.update(diff, options.merge)

    if options.validate:
        A.LOGGER.info("Validation succeeds")
        sys.exit(0)

    if options.gen_schema:
        data = A.gen_schema(data)

    if options.get:
        (data, err) = A.get(data, options.get)
        if err:
            raise RuntimeError(err)

        # Output primitive types as it is.
        if not anyconfig.mergeabledict.is_mergeabledict_or_dict(data):
            sys.stdout.write(str(data) + '\n')
            return

    if options.set:
        (key, val) = options.set.split('=')
        A.set_(data, key, anyconfig.parser.parse(val))

    if options.output:
        cparser = A.find_loader(options.output, options.otype)
        if cparser is None:
            raise RuntimeError("No suitable dumper was found for %s",
                               options.output)

        cparser.dump(data, options.output)
    else:
        if options.otype is None:
            if options.itype is None:
                psr = A.find_loader(args[0])
                if psr is not None:
                    options.otype = psr.type()  # Reuse detected input type
                else:
                    raise RuntimeError("Please specify input and/or output "
                                       "type with -I (--itype) or -O "
                                       "(--otype) option")
            else:
                options.otype = options.itype

        cparser = A.find_loader(None, options.otype)
        sys.stdout.write(cparser.dumps(data) + '\n')
 def test_40_open_yaml_file(self):
     if "yaml" in TT.list_types():
         self._load_and_dump_with_opened_files("a.yaml")
         self._load_and_dump_with_opened_files("a.yml")
class Test_50_load_and_dump(TestBaseWithIOMultiFiles):

    def test_30_dump_and_load(self):
        TT.dump(self.dic, self.a_path)
        TT.dump(self.upd, self.b_path)

        self.assertTrue(self.a_path.exists())
        self.assertTrue(self.b_path.exists())

        res = TT.load(self.a_path)
        self.assert_dicts_equal(res, self.dic)

        res = TT.load(self.g_path)
        self.assert_dicts_equal(res, self.exp)

        res = TT.load([self.a_path, self.b_path])
        self.assert_dicts_equal(res, self.exp)

    def test_31_dump_and_load__to_from_stream(self):
        with TT.open(self.a_path, mode='w') as strm:
            TT.dump(self.dic, strm)

        self.assertTrue(self.a_path.exists())

        with TT.open(self.a_path) as strm:
            res = TT.load(strm, ac_parser="json")
            self.assert_dicts_equal(res, self.dic)

    def test_32_dump_and_load__w_options(self):
        TT.dump(self.dic, self.a_path, indent=2)
        self.assertTrue(self.a_path.exists())

        TT.dump(self.upd, self.b_path, indent=2)
        self.assertTrue(self.b_path.exists())

        res = TT.load(self.a_path, parse_int=int)
        dic = copy.deepcopy(self.dic)
        self.assert_dicts_equal(res, dic)

        res = TT.load(self.g_path, parse_int=int)
        exp = copy.deepcopy(self.exp)
        self.assert_dicts_equal(res, exp)

        res = TT.load([self.a_path, self.b_path], parse_int=int)
        exp = copy.deepcopy(self.exp)
        self.assert_dicts_equal(res, exp)

    def test_34_load__ignore_missing(self):
        cpath = pathlib.Path(os.curdir) / "conf_file_should_not_exist"
        assert not cpath.exists()

        self.assertEqual(TT.load([cpath], ac_parser="ini",
                                 ignore_missing=True),
                         NULL_CNTNR)

    def test_36_load_w_validation(self):
        cnf_path = self.workdir / "cnf.json"
        scm_path = self.workdir / "scm.json"
        TT.dump(CNF_0, cnf_path)
        TT.dump(SCM_0, scm_path)

        cnf_2 = TT.load(cnf_path, ac_context={}, ac_schema=scm_path)

        self.assertEqual(cnf_2["name"], CNF_0["name"])
        self.assertEqual(cnf_2["a"], CNF_0["a"])
        self.assertEqual(cnf_2["b"]["b"], CNF_0["b"]["b"])
        self.assertEqual(cnf_2["b"]["c"], CNF_0["b"]["c"])

    @unittest.skipIf('yml' not in TT.list_types(), "yaml lib is not available")
    def test_38_load_w_validation_yaml(self):
        cnf_path = self.workdir / "cnf.yml"
        scm_path = self.workdir / "scm.yml"
        TT.dump(CNF_0, cnf_path)
        TT.dump(SCM_0, scm_path)

        cnf_2 = TT.load(cnf_path, ac_context={}, ac_schema=scm_path)

        self.assertEqual(cnf_2["name"], CNF_0["name"])
        self.assertEqual(cnf_2["a"], CNF_0["a"])
        self.assertEqual(cnf_2["b"]["b"], CNF_0["b"]["b"])
        self.assertEqual(cnf_2["b"]["c"], CNF_0["b"]["c"])

    def test_39_single_load__w_validation(self):
        (cnf, scm) = (CNF_0, SCM_0)
        cpath = self.workdir / "cnf.json"
        spath = self.workdir / "scm.json"

        TT.dump(cnf, cpath)
        TT.dump(scm, spath)

        cnf1 = TT.single_load(cpath, ac_schema=spath)
        self.assert_dicts_equal(cnf, cnf1)

    def test_40_load_w_query(self):
        cnf_path = self.workdir / "cnf.json"
        TT.dump(CNF_0, cnf_path)

        try:
            if TT.query.jmespath:
                self.assertEqual(TT.load(cnf_path, ac_query="a"), 1)
                self.assertEqual(TT.load(cnf_path, ac_query="b.b"), [1, 2])
                self.assertEqual(TT.load(cnf_path, ac_query="b.b[1]"), 2)
                self.assertEqual(TT.load(cnf_path, ac_query="b.b[1:]"), [2])
                self.assertEqual(TT.load(cnf_path, ac_query="b.b[::-1]"),
                                 [2, 1])
                self.assertEqual(TT.load(cnf_path, ac_query="length(b.b)"), 2)
        except (NameError, AttributeError):
            pass  # jmespath is not available.
Exemple #22
0
def parse_args(argv=None, defaults=None):
    """
    Make up an option and arguments parser.

    :param defaults: Default option values
    """
    if defaults is None:
        defaults = DEFAULTS

    ctypes = API.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = API.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    parser = optparse.OptionParser(USAGE, version="%%prog %s" %
                                   anyconfig.globals.VERSION)
    parser.set_defaults(**defaults)

    lpog = optparse.OptionGroup(parser, "List specific options")
    lpog.add_option("-L", "--list", help="List supported config types",
                    action="store_true")
    parser.add_option_group(lpog)

    spog = optparse.OptionGroup(parser, "Schema specific options")
    spog.add_option("", "--validate", action="store_true",
                    help="Only validate input files and do not output. "
                         "You must specify schema file with -S/--schema "
                         "option.")
    spog.add_option("", "--gen-schema", action="store_true",
                    help="Generate JSON schema for givne config file[s] "
                         "and output it instead of (merged) configuration.")
    parser.add_option_group(spog)

    gspog = optparse.OptionGroup(parser, "Query/Get/set options")
    gspog.add_option("-Q", "--query", help=_QUERY_HELP)
    gspog.add_option("", "--get", help=_GET_HELP)
    gspog.add_option("", "--set", help=_SET_HELP)
    parser.add_option_group(gspog)

    parser.add_option("-o", "--output", help="Output file path")
    parser.add_option("-I", "--itype", choices=ctypes,
                      help=(type_help % "Input"))
    parser.add_option("-O", "--otype", choices=ctypes,
                      help=(type_help % "Output"))
    parser.add_option("-M", "--merge", choices=mts, help=mt_help)
    parser.add_option("-A", "--args", help="Argument configs to override")
    parser.add_option("", "--atype", choices=ctypes,
                      help=_ATYPE_HELP_FMT % ctypes_s)

    parser.add_option("-x", "--ignore-missing", action="store_true",
                      help="Ignore missing input files")
    parser.add_option("-T", "--template", action="store_true",
                      help="Enable template config support")
    parser.add_option("-E", "--env", action="store_true",
                      help="Load configuration defaults from "
                           "environment values")
    parser.add_option("-S", "--schema", help="Specify Schema file[s] path")
    parser.add_option("-s", "--silent", action="store_const", dest="loglevel",
                      const=0, help="Silent or quiet mode")
    parser.add_option("-q", "--quiet", action="store_const", dest="loglevel",
                      const=0, help="Same as --silent option")
    parser.add_option("-v", "--verbose", action="store_const", dest="loglevel",
                      const=2, help="Verbose mode")

    if argv is None:
        argv = sys.argv

    (options, args) = parser.parse_args(argv[1:])
    return (parser, options, args)
Exemple #23
0
def option_parser(defaults=None, usage=USAGE):
    """
    Make up an option and arguments parser.

    :param defaults: Default option values
    :param usage: Usage text
    """
    defaults = dict(loglevel=1,
                    list=False,
                    output=None,
                    itype=None,
                    otype=None,
                    atype=None,
                    merge=A.MS_DICTS,
                    ignore_missing=False)

    ctypes = A.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = A.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    af_help = """Explicitly select type of argument to provide configs from %s.

If this option is not set, original parser is used: 'K:V' will become {K: V},
'K:V_0,V_1,..' will become {K: [V_0, V_1, ...]}, and 'K_0:V_0;K_1:V_1' will
become {K_0: V_0, K_1: V_1} (where the tyep of K is str, type of V is one of
Int, str, etc.""" % ctypes_s

    get_help = ("Specify key path to get part of config, for example, "
                "'--get a.b.c' to config {'a': {'b': {'c': 0, 'd': 1}}} "
                "gives 0 and '--get a.b' to the same config gives "
                "{'c': 0, 'd': 1}.")
    set_help = ("Specify key path to set (update) part of config, for "
                "example, '--set a.b.c=1' to a config {'a': {'b': {'c': 0, "
                "'d': 1}}} gives {'a': {'b': {'c': 1, 'd': 1}}}.")

    parser = optparse.OptionParser(usage, version="%%prog %s" % G.VERSION)
    parser.set_defaults(**defaults)

    parser.add_option("-L",
                      "--list",
                      help="List supported config types",
                      action="store_true")
    parser.add_option("-o", "--output", help="Output file path")
    parser.add_option("-I",
                      "--itype",
                      choices=ctypes,
                      help=(type_help % "Input"))
    parser.add_option("-O",
                      "--otype",
                      choices=ctypes,
                      help=(type_help % "Output"))
    parser.add_option("-M", "--merge", choices=mts, help=mt_help)

    parser.add_option("-A", "--args", help="Argument configs to override")
    parser.add_option("", "--atype", choices=ctypes, help=af_help)

    parser.add_option("", "--get", help=get_help)
    parser.add_option("", "--set", help=set_help)

    parser.add_option("-x",
                      "--ignore-missing",
                      action="store_true",
                      help="Ignore missing input files")

    parser.add_option("-s",
                      "--silent",
                      action="store_const",
                      dest="loglevel",
                      const=0,
                      help="Silent or quiet mode")
    parser.add_option("-q",
                      "--quiet",
                      action="store_const",
                      dest="loglevel",
                      const=0,
                      help="Same as --silent option")
    parser.add_option("-v",
                      "--verbose",
                      action="store_const",
                      dest="loglevel",
                      const=2,
                      help="Verbose mode")

    return parser
Exemple #24
0
def make_parser(defaults=None):
    """
    :param defaults: Default option values
    """
    if defaults is None:
        defaults = DEFAULTS

    ctypes = API.list_types()
    ctypes_s = ", ".join(ctypes)
    type_help = "Select type of %s config files from " + \
        ctypes_s + " [Automatically detected by file ext]"

    mts = API.MERGE_STRATEGIES
    mts_s = ", ".join(mts)
    mt_help = "Select strategy to merge multiple configs from " + \
        mts_s + " [%(merge)s]" % defaults

    parser = argparse.ArgumentParser(usage=USAGE)
    parser.set_defaults(**defaults)

    parser.add_argument("inputs", type=str, nargs='*', help="Input files")
    parser.add_argument("--version", action="version",
                        version="%%(prog)s %s" % anyconfig.globals.VERSION)

    lpog = parser.add_argument_group("List specific options")
    lpog.add_argument("-L", "--list", action="store_true",
                      help="List supported config types")

    spog = parser.add_argument_group("Schema specific options")
    spog.add_argument("--validate", action="store_true",
                      help="Only validate input files and do not output. "
                           "You must specify schema file with -S/--schema "
                           "option.")
    spog.add_argument("--gen-schema", action="store_true",
                      help="Generate JSON schema for givne config file[s] "
                           "and output it instead of (merged) configuration.")

    gspog = parser.add_argument_group("Query/Get/set options")
    gspog.add_argument("-Q", "--query", help=_QUERY_HELP)
    gspog.add_argument("--get", help=_GET_HELP)
    gspog.add_argument("--set", help=_SET_HELP)

    parser.add_argument("-o", "--output", help="Output file path")
    parser.add_argument("-I", "--itype", choices=ctypes, metavar="ITYPE",
                        help=(type_help % "Input"))
    parser.add_argument("-O", "--otype", choices=ctypes, metavar="OTYPE",
                        help=(type_help % "Output"))
    parser.add_argument("-M", "--merge", choices=mts, metavar="MERGE",
                        help=mt_help)
    parser.add_argument("-A", "--args", help="Argument configs to override")
    parser.add_argument("--atype", choices=ctypes, metavar="ATYPE",
                        help=_ATYPE_HELP_FMT % ctypes_s)

    cpog = parser.add_argument_group("Common options")
    cpog.add_argument("-x", "--ignore-missing", action="store_true",
                      help="Ignore missing input files")
    cpog.add_argument("-T", "--template", action="store_true",
                      help="Enable template config support")
    cpog.add_argument("-E", "--env", action="store_true",
                      help="Load configuration defaults from "
                           "environment values")
    cpog.add_argument("-S", "--schema", help="Specify Schema file[s] path")
    cpog.add_argument("-e", "--extra-opts",
                      help="Extra options given to the API call, "
                           "--extra-options indent:2 (specify the "
                           "indent for pretty-printing of JSON outputs) "
                           "for example")
    cpog.add_argument("-v", "--verbose", action="count", dest="loglevel",
                      help="Verbose mode; -v or -vv (more verbose)")
    return parser