File: argutil.py

package info (click to toggle)
libreswan 5.2-2.3
  • links: PTS, VCS
  • area: main
  • in suites: sid
  • size: 81,644 kB
  • sloc: ansic: 129,988; sh: 32,018; xml: 20,646; python: 10,303; makefile: 3,022; javascript: 1,506; sed: 574; yacc: 511; perl: 264; awk: 52
file content (123 lines) | stat: -rw-r--r-- 4,172 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
# Some argument parsing functions.
#
# Copyright (C) 2015-2016 Andrew Cagney <cagney@gnu.org>
#
# This program is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by the
# Free Software Foundation; either version 2 of the License, or (at your
# option) any later version.  See <https://www.gnu.org/licenses/gpl2.txt>.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
# or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
# for more details.

import sys
import os

from fab import tee

class MetaList(type):
    def __new__(cls, name, bases, namespace, **kwds):
        result = type.__new__(cls, name, bases, namespace, **kwds)

        # The string names are mapped onto the canonical member names
        # so that that the construct:
        #
        #    for p in List(List.member): p is List.member"
        #
        # works.
        members = {}
        for name, value in namespace.items():
            # good enough for now
            if name.startswith("__"):
                continue
            if not isinstance(value, str):
                continue
            members[value] = value
        result._members_ = members
        result._metavar_ = "{" + ",".join(sorted(members)) + "},..."
        return result
    def __str__(cls):
        return cls._metavar_

class List(metaclass=MetaList):
    def __init__(self, *args):
        self.args = []
        for arg in args:
            for member in arg.split(","):
                if not member:
                    # ignore ''
                    continue
                if member in self._members_:
                    # Form the list using the member values, not some
                    # equivalent string.  Ignore ''.
                    self.args.append(self._members_[member])
                else:
                    raise ValueError()
    def __iter__(self):
        return self.args.__iter__()
    def __str__(self):
        return ",".join(self.args)
    def __contains__(self, member):
        return member in self.args
    def __bool__(self):
        return bool(self.args)


def boolean(arg):
    a = arg.lower()
    for t in [ "1", "yes", "true", "enable" ]:
        if t.startswith(a):
            return True
    for f in [ "0", "no", "false", "disable" ]:
        if f.startswith(a):
            return False
    raise Exception("Unrecognized boolean argument '%s'" % arg)

def timeout(arg):
    arg = arg.lower()
    if arg == "none" or arg == "infinite":
        return None
    v = float(arg)
    if v < 0:
        return None
    else:
        return v

def directory(arg):
    if os.path.isdir(arg):
        return arg
    raise Exception("directory '%s' not found" % arg)

def directory_file(arg):
    d,b = os.path.split(arg)
    if os.path.isdir(d):
        return arg
    raise Exception("directory '%d' for file '%s' not found" % (d, b))

def add_redirect_argument(parser, what, *args, **kwargs):
    # Can't use '-FILE' as the argument as the parser doesn't like it.
    # The prefix syntax is hacky.
    parser.add_argument(*args, type=stdout_or_open_file,
                        help=(what +
                              "; '-' is an alias for /dev/stdout"
                              "; '+%(metavar)s': append to %(metavar)s"
                              "; '=%(metavar)s': overwrite %(metavar)s (default behaviour)"
                              "; '++%(metavar)s': copy to stdout, append to %(metavar)s"
                              "; '+=%(metavar)s': copy to stdout, overwrite %(metavar)s"),
                        **kwargs)

def stdout_or_open_file(arg):
    if arg == "-":
        return sys.stdout.buffer
    elif arg.startswith("++"):
        return tee.open(sys.stdout, files=[open(arg[2:], "a")])
    elif arg.startswith("+="):
        return tee.open(sys.stdout, files=[open(arg[2:], "w")])
    elif arg.startswith("+"):
        return open(arg[1:], "a")
    elif arg.startswith("="):
        return open(arg[1:], "w")
    else:
        return open(arg, "w")