Statistics
| Branch: | Tag: | Revision:

root / kamaki / cli / commands / __init__.py @ 534e7bbb

History | View | Annotate | Download (12.4 kB)

1 e3f01d64 Stavros Sachtouris
# Copyright 2011-2013 GRNET S.A. All rights reserved.
2 5eae854d Stavros Sachtouris
#
3 5eae854d Stavros Sachtouris
# Redistribution and use in source and binary forms, with or
4 5eae854d Stavros Sachtouris
# without modification, are permitted provided that the following
5 5eae854d Stavros Sachtouris
# conditions are met:
6 5eae854d Stavros Sachtouris
#
7 5eae854d Stavros Sachtouris
#   1. Redistributions of source code must retain the above
8 5eae854d Stavros Sachtouris
#      copyright notice, this list of conditions and the following
9 5eae854d Stavros Sachtouris
#      disclaimer.
10 5eae854d Stavros Sachtouris
#
11 5eae854d Stavros Sachtouris
#   2. Redistributions in binary form must reproduce the above
12 5eae854d Stavros Sachtouris
#      copyright notice, this list of conditions and the following
13 5eae854d Stavros Sachtouris
#      disclaimer in the documentation and/or other materials
14 5eae854d Stavros Sachtouris
#      provided with the distribution.
15 5eae854d Stavros Sachtouris
#
16 5eae854d Stavros Sachtouris
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17 5eae854d Stavros Sachtouris
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 5eae854d Stavros Sachtouris
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19 5eae854d Stavros Sachtouris
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20 5eae854d Stavros Sachtouris
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 5eae854d Stavros Sachtouris
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 5eae854d Stavros Sachtouris
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23 5eae854d Stavros Sachtouris
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24 5eae854d Stavros Sachtouris
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 5eae854d Stavros Sachtouris
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26 5eae854d Stavros Sachtouris
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27 5eae854d Stavros Sachtouris
# POSSIBILITY OF SUCH DAMAGE.
28 5eae854d Stavros Sachtouris
#
29 5eae854d Stavros Sachtouris
# The views and conclusions contained in the software and
30 5eae854d Stavros Sachtouris
# documentation are those of the authors and should not be
31 5eae854d Stavros Sachtouris
# interpreted as representing official policies, either expressed
32 5eae854d Stavros Sachtouris
# or implied, of GRNET S.A.command
33 5eae854d Stavros Sachtouris
34 137c51f5 Stavros Sachtouris
from kamaki.cli.logger import get_logger
35 ddcb2e09 Stavros Sachtouris
from kamaki.cli.utils import (
36 ddcb2e09 Stavros Sachtouris
    print_list, print_dict, print_json, print_items, ask_user,
37 ddcb2e09 Stavros Sachtouris
    filter_dicts_by_dict)
38 6d190dd1 Stavros Sachtouris
from kamaki.cli.argument import FlagArgument, ValueArgument
39 f76c6bbc Stavros Sachtouris
from kamaki.cli.errors import CLIInvalidArgument
40 ff1c0296 Stavros Sachtouris
from sys import stdin, stdout, stderr
41 6069b53b Stavros Sachtouris
42 0d4a6d0a Stavros Sachtouris
log = get_logger(__name__)
43 6069b53b Stavros Sachtouris
44 234954d1 Stavros Sachtouris
45 b4f69041 Stavros Sachtouris
def DontRaiseKeyError(foo):
46 b4f69041 Stavros Sachtouris
    def wrap(*args, **kwargs):
47 b4f69041 Stavros Sachtouris
        try:
48 b4f69041 Stavros Sachtouris
            return foo(*args, **kwargs)
49 b4f69041 Stavros Sachtouris
        except KeyError:
50 b4f69041 Stavros Sachtouris
            return None
51 b4f69041 Stavros Sachtouris
    return wrap
52 b4f69041 Stavros Sachtouris
53 b4f69041 Stavros Sachtouris
54 b4f69041 Stavros Sachtouris
def addLogSettings(foo):
55 b4f69041 Stavros Sachtouris
    def wrap(self, *args, **kwargs):
56 b4f69041 Stavros Sachtouris
        try:
57 b4f69041 Stavros Sachtouris
            return foo(self, *args, **kwargs)
58 b4f69041 Stavros Sachtouris
        finally:
59 b4f69041 Stavros Sachtouris
            self._set_log_params()
60 b4f69041 Stavros Sachtouris
            self._update_max_threads
61 b4f69041 Stavros Sachtouris
    return wrap
62 b4f69041 Stavros Sachtouris
63 b4f69041 Stavros Sachtouris
64 5eae854d Stavros Sachtouris
class _command_init(object):
65 36526b3c Stavros Sachtouris
66 1757c616 Stavros Sachtouris
    def __init__(
67 1757c616 Stavros Sachtouris
            self,
68 ff1c0296 Stavros Sachtouris
            arguments={}, auth_base=None, cloud=None,
69 ff1c0296 Stavros Sachtouris
            _in=None, _out=None, _err=None):
70 ff1c0296 Stavros Sachtouris
        self._in, self._out, self._err = (
71 ff1c0296 Stavros Sachtouris
            _in or stdin, _out or stdout, _err or stderr)
72 e15d78e2 Stavros Sachtouris
        if hasattr(self, 'arguments'):
73 e15d78e2 Stavros Sachtouris
            arguments.update(self.arguments)
74 915b99b5 Stavros Sachtouris
        if isinstance(self, _optional_output_cmd):
75 915b99b5 Stavros Sachtouris
            arguments.update(self.oo_arguments)
76 545c6c29 Stavros Sachtouris
        if isinstance(self, _optional_json):
77 545c6c29 Stavros Sachtouris
            arguments.update(self.oj_arguments)
78 6d190dd1 Stavros Sachtouris
        if isinstance(self, _name_filter):
79 6d190dd1 Stavros Sachtouris
            arguments.update(self.nf_arguments)
80 6d190dd1 Stavros Sachtouris
        if isinstance(self, _id_filter):
81 6d190dd1 Stavros Sachtouris
            arguments.update(self.if_arguments)
82 60c42f9f Stavros Sachtouris
        try:
83 60c42f9f Stavros Sachtouris
            arguments.update(self.wait_arguments)
84 60c42f9f Stavros Sachtouris
        except AttributeError:
85 60c42f9f Stavros Sachtouris
            pass
86 e15d78e2 Stavros Sachtouris
        self.arguments = dict(arguments)
87 5eae854d Stavros Sachtouris
        try:
88 e15d78e2 Stavros Sachtouris
            self.config = self['config']
89 5eae854d Stavros Sachtouris
        except KeyError:
90 5eae854d Stavros Sachtouris
            pass
91 844a6bdb Stavros Sachtouris
        self.auth_base = auth_base or getattr(self, 'auth_base', None)
92 844a6bdb Stavros Sachtouris
        self.cloud = cloud or getattr(self, 'cloud', None)
93 5eae854d Stavros Sachtouris
94 ff1c0296 Stavros Sachtouris
    def write(self, s):
95 ff1c0296 Stavros Sachtouris
        self._out.write(u'%s' % s)
96 ff1c0296 Stavros Sachtouris
        self._out.flush()
97 ff1c0296 Stavros Sachtouris
98 ff1c0296 Stavros Sachtouris
    def writeln(self, s=''):
99 ff1c0296 Stavros Sachtouris
        self.write(u'%s\n' % s)
100 ff1c0296 Stavros Sachtouris
101 ff1c0296 Stavros Sachtouris
    def error(self, s=''):
102 ff1c0296 Stavros Sachtouris
        self._err.write(u'%s\n' % s)
103 ff1c0296 Stavros Sachtouris
        self._err.flush()
104 ff1c0296 Stavros Sachtouris
105 ddcb2e09 Stavros Sachtouris
    def print_list(self, *args, **kwargs):
106 ddcb2e09 Stavros Sachtouris
        kwargs.setdefault('out', self._out)
107 76f58e2e Stavros Sachtouris
        return print_list(*args, **kwargs)
108 ddcb2e09 Stavros Sachtouris
109 ddcb2e09 Stavros Sachtouris
    def print_dict(self, *args, **kwargs):
110 ddcb2e09 Stavros Sachtouris
        kwargs.setdefault('out', self._out)
111 76f58e2e Stavros Sachtouris
        return print_dict(*args, **kwargs)
112 ddcb2e09 Stavros Sachtouris
113 ddcb2e09 Stavros Sachtouris
    def print_json(self, *args, **kwargs):
114 ddcb2e09 Stavros Sachtouris
        kwargs.setdefault('out', self._out)
115 76f58e2e Stavros Sachtouris
        return print_json(*args, **kwargs)
116 ddcb2e09 Stavros Sachtouris
117 ddcb2e09 Stavros Sachtouris
    def print_items(self, *args, **kwargs):
118 ddcb2e09 Stavros Sachtouris
        kwargs.setdefault('out', self._out)
119 76f58e2e Stavros Sachtouris
        return print_items(*args, **kwargs)
120 ddcb2e09 Stavros Sachtouris
121 ddcb2e09 Stavros Sachtouris
    def ask_user(self, *args, **kwargs):
122 ddcb2e09 Stavros Sachtouris
        kwargs.setdefault('user_in', self._in)
123 ddcb2e09 Stavros Sachtouris
        kwargs.setdefault('out', self._out)
124 76f58e2e Stavros Sachtouris
        return ask_user(*args, **kwargs)
125 ddcb2e09 Stavros Sachtouris
126 b4f69041 Stavros Sachtouris
    @DontRaiseKeyError
127 b4f69041 Stavros Sachtouris
    def _custom_url(self, service):
128 144b3551 Stavros Sachtouris
        return self.config.get_cloud(self.cloud, '%s_url' % service)
129 b4f69041 Stavros Sachtouris
130 b4f69041 Stavros Sachtouris
    @DontRaiseKeyError
131 b4f69041 Stavros Sachtouris
    def _custom_token(self, service):
132 144b3551 Stavros Sachtouris
        return self.config.get_cloud(self.cloud, '%s_token' % service)
133 b4f69041 Stavros Sachtouris
134 b4f69041 Stavros Sachtouris
    @DontRaiseKeyError
135 b4f69041 Stavros Sachtouris
    def _custom_type(self, service):
136 144b3551 Stavros Sachtouris
        return self.config.get_cloud(self.cloud, '%s_type' % service)
137 b4f69041 Stavros Sachtouris
138 b4f69041 Stavros Sachtouris
    @DontRaiseKeyError
139 b4f69041 Stavros Sachtouris
    def _custom_version(self, service):
140 144b3551 Stavros Sachtouris
        return self.config.get_cloud(self.cloud, '%s_version' % service)
141 b4f69041 Stavros Sachtouris
142 f1e5b343 Stavros Sachtouris
    def _uuids2usernames(self, uuids):
143 f1e5b343 Stavros Sachtouris
        return self.auth_base.post_user_catalogs(uuids).json['uuid_catalog']
144 f1e5b343 Stavros Sachtouris
145 f1e5b343 Stavros Sachtouris
    def _usernames2uuids(self, username):
146 f1e5b343 Stavros Sachtouris
        return self.auth_base.post_user_catalogs(
147 f1e5b343 Stavros Sachtouris
            displaynames=username).json['displayname_catalog']
148 f1e5b343 Stavros Sachtouris
149 95641ecc Stavros Sachtouris
    def _uuid2username(self, uuid):
150 f1e5b343 Stavros Sachtouris
        return self._uuids2usernames([uuid]).get(uuid, None)
151 95641ecc Stavros Sachtouris
152 95641ecc Stavros Sachtouris
    def _username2uuid(self, username):
153 f1e5b343 Stavros Sachtouris
        return self._usernames2uuids([username]).get(username, None)
154 95641ecc Stavros Sachtouris
155 f47417e7 Stavros Sachtouris
    def _set_log_params(self):
156 b3bb083f Stavros Sachtouris
        try:
157 64a3c0de Stavros Sachtouris
            self.client.LOG_TOKEN = (
158 534e7bbb Stavros Sachtouris
                self['config'].get('global', 'log_token').lower() == 'on')
159 64a3c0de Stavros Sachtouris
        except Exception as e:
160 64a3c0de Stavros Sachtouris
            log.debug('Failed to read custom log_token setting:'
161 64a3c0de Stavros Sachtouris
                '%s\n default for log_token is off' % e)
162 64a3c0de Stavros Sachtouris
        try:
163 64a3c0de Stavros Sachtouris
            self.client.LOG_DATA = (
164 534e7bbb Stavros Sachtouris
                self['config'].get('global', 'log_data').lower() == 'on')
165 c5b9380c Stavros Sachtouris
        except Exception as e:
166 64a3c0de Stavros Sachtouris
            log.debug('Failed to read custom log_data setting:'
167 64a3c0de Stavros Sachtouris
                '%s\n default for log_data is off' % e)
168 64a3c0de Stavros Sachtouris
        try:
169 64a3c0de Stavros Sachtouris
            self.client.LOG_PID = (
170 534e7bbb Stavros Sachtouris
                self['config'].get('global', 'log_pid').lower() == 'on')
171 64a3c0de Stavros Sachtouris
        except Exception as e:
172 64a3c0de Stavros Sachtouris
            log.debug('Failed to read custom log_pid setting:'
173 64a3c0de Stavros Sachtouris
                '%s\n default for log_pid is off' % e)
174 c5b9380c Stavros Sachtouris
175 c5b9380c Stavros Sachtouris
    def _update_max_threads(self):
176 b4f69041 Stavros Sachtouris
        if getattr(self, 'client', None):
177 534e7bbb Stavros Sachtouris
            max_threads = int(self['config'].get('global', 'max_threads'))
178 f5ff79d9 Stavros Sachtouris
            assert max_threads > 0, 'invalid max_threads config option'
179 c5b9380c Stavros Sachtouris
            self.client.MAX_THREADS = max_threads
180 5fdccdec Stavros Sachtouris
181 8547cd19 Stavros Sachtouris
    def _safe_progress_bar(
182 8547cd19 Stavros Sachtouris
            self, msg, arg='progress_bar', countdown=False, timeout=100):
183 5a673575 Stavros Sachtouris
        """Try to get a progress bar, but do not raise errors"""
184 5a673575 Stavros Sachtouris
        try:
185 5a673575 Stavros Sachtouris
            progress_bar = self.arguments[arg]
186 ff1c0296 Stavros Sachtouris
            progress_bar.file = self._err
187 8547cd19 Stavros Sachtouris
            gen = progress_bar.get_generator(
188 8547cd19 Stavros Sachtouris
                msg, countdown=countdown, timeout=timeout)
189 5a673575 Stavros Sachtouris
        except Exception:
190 5a673575 Stavros Sachtouris
            return (None, None)
191 5a673575 Stavros Sachtouris
        return (progress_bar, gen)
192 5a673575 Stavros Sachtouris
193 5a673575 Stavros Sachtouris
    def _safe_progress_bar_finish(self, progress_bar):
194 5a673575 Stavros Sachtouris
        try:
195 5a673575 Stavros Sachtouris
            progress_bar.finish()
196 5a673575 Stavros Sachtouris
        except Exception:
197 5a673575 Stavros Sachtouris
            pass
198 5a673575 Stavros Sachtouris
199 5a37a189 Stavros Sachtouris
    def __getitem__(self, argterm):
200 5a37a189 Stavros Sachtouris
        """
201 5a37a189 Stavros Sachtouris
        :param argterm: (str) the name/label of an argument in self.arguments
202 5a37a189 Stavros Sachtouris

203 b113e74b Stavros Sachtouris
        :returns: the value of the corresponding Argument (not the argument
204 b113e74b Stavros Sachtouris
            object)
205 5a37a189 Stavros Sachtouris

206 5a37a189 Stavros Sachtouris
        :raises KeyError: if argterm not in self.arguments of this object
207 5a37a189 Stavros Sachtouris
        """
208 b113e74b Stavros Sachtouris
        return self.arguments[argterm].value
209 5a37a189 Stavros Sachtouris
210 5a37a189 Stavros Sachtouris
    def __setitem__(self, argterm, arg):
211 5a37a189 Stavros Sachtouris
        """Install an argument as argterm
212 5a37a189 Stavros Sachtouris
        If argterm points to another argument, the other argument is lost
213 5a37a189 Stavros Sachtouris

214 5a37a189 Stavros Sachtouris
        :param argterm: (str)
215 5a37a189 Stavros Sachtouris

216 5a37a189 Stavros Sachtouris
        :param arg: (Argument)
217 5a37a189 Stavros Sachtouris
        """
218 5a37a189 Stavros Sachtouris
        if not hasattr(self, 'arguments'):
219 5a37a189 Stavros Sachtouris
            self.arguments = {}
220 5a37a189 Stavros Sachtouris
        self.arguments[argterm] = arg
221 5a37a189 Stavros Sachtouris
222 b113e74b Stavros Sachtouris
    def get_argument_object(self, argterm):
223 b113e74b Stavros Sachtouris
        """
224 b113e74b Stavros Sachtouris
        :param argterm: (str) the name/label of an argument in self.arguments
225 b113e74b Stavros Sachtouris

226 b113e74b Stavros Sachtouris
        :returns: the arument object
227 b113e74b Stavros Sachtouris

228 b113e74b Stavros Sachtouris
        :raises KeyError: if argterm not in self.arguments of this object
229 b113e74b Stavros Sachtouris
        """
230 b113e74b Stavros Sachtouris
        return self.arguments[argterm]
231 b113e74b Stavros Sachtouris
232 5eae854d Stavros Sachtouris
    def get_argument(self, argterm):
233 5a37a189 Stavros Sachtouris
        """
234 5a37a189 Stavros Sachtouris
        :param argterm: (str) the name/label of an argument in self.arguments
235 5a37a189 Stavros Sachtouris

236 5a37a189 Stavros Sachtouris
        :returns: the value of the arument object
237 5a37a189 Stavros Sachtouris

238 5a37a189 Stavros Sachtouris
        :raises KeyError: if argterm not in self.arguments of this object
239 5a37a189 Stavros Sachtouris
        """
240 e15d78e2 Stavros Sachtouris
        return self[argterm]
241 915b99b5 Stavros Sachtouris
242 915b99b5 Stavros Sachtouris
243 545c6c29 Stavros Sachtouris
#  feature classes - inherit them to get special features for your commands
244 545c6c29 Stavros Sachtouris
245 545c6c29 Stavros Sachtouris
246 f76c6bbc Stavros Sachtouris
class OutputFormatArgument(ValueArgument):
247 f76c6bbc Stavros Sachtouris
    """Accepted output formats: json (default)"""
248 f76c6bbc Stavros Sachtouris
249 f76c6bbc Stavros Sachtouris
    formats = ('json', )
250 f76c6bbc Stavros Sachtouris
251 f76c6bbc Stavros Sachtouris
    def ___init__(self, *args, **kwargs):
252 f76c6bbc Stavros Sachtouris
        super(OutputFormatArgument, self).___init__(*args, **kwargs)
253 f76c6bbc Stavros Sachtouris
254 f76c6bbc Stavros Sachtouris
    @property
255 f76c6bbc Stavros Sachtouris
    def value(self):
256 f76c6bbc Stavros Sachtouris
        return self._value
257 f76c6bbc Stavros Sachtouris
258 f76c6bbc Stavros Sachtouris
    @value.setter
259 f76c6bbc Stavros Sachtouris
    def value(self, newvalue):
260 f76c6bbc Stavros Sachtouris
        if not newvalue:
261 f76c6bbc Stavros Sachtouris
            self._value = self.default
262 f76c6bbc Stavros Sachtouris
        elif newvalue.lower() in self.formats:
263 f76c6bbc Stavros Sachtouris
            self._value = newvalue.lower
264 f76c6bbc Stavros Sachtouris
        else:
265 f76c6bbc Stavros Sachtouris
            raise CLIInvalidArgument(
266 f76c6bbc Stavros Sachtouris
                'Invalid value %s for argument %s' % (
267 f76c6bbc Stavros Sachtouris
                    newvalue, '/'.join(self.parsed_name)),
268 f76c6bbc Stavros Sachtouris
                details=['Valid output formats: %s' % ', '.join(self.formats)])
269 f76c6bbc Stavros Sachtouris
270 f76c6bbc Stavros Sachtouris
271 915b99b5 Stavros Sachtouris
class _optional_output_cmd(object):
272 915b99b5 Stavros Sachtouris
273 915b99b5 Stavros Sachtouris
    oo_arguments = dict(
274 915b99b5 Stavros Sachtouris
        with_output=FlagArgument('show response headers', ('--with-output')),
275 f76c6bbc Stavros Sachtouris
        json_output=FlagArgument(
276 f76c6bbc Stavros Sachtouris
            'show headers in json (DEPRECATED from v0.12,'
277 f76c6bbc Stavros Sachtouris
            ' please use --output-format=json instead)', ('-j', '--json'))
278 915b99b5 Stavros Sachtouris
    )
279 915b99b5 Stavros Sachtouris
280 915b99b5 Stavros Sachtouris
    def _optional_output(self, r):
281 915b99b5 Stavros Sachtouris
        if self['json_output']:
282 1757c616 Stavros Sachtouris
            print_json(r, out=self._out)
283 915b99b5 Stavros Sachtouris
        elif self['with_output']:
284 1757c616 Stavros Sachtouris
            print_items([r] if isinstance(r, dict) else r, out=self._out)
285 545c6c29 Stavros Sachtouris
286 545c6c29 Stavros Sachtouris
287 545c6c29 Stavros Sachtouris
class _optional_json(object):
288 545c6c29 Stavros Sachtouris
289 545c6c29 Stavros Sachtouris
    oj_arguments = dict(
290 f76c6bbc Stavros Sachtouris
        output_format=OutputFormatArgument(
291 f76c6bbc Stavros Sachtouris
            'Show output in chosen output format (%s)' % ', '.join(
292 f76c6bbc Stavros Sachtouris
                OutputFormatArgument.formats),
293 f76c6bbc Stavros Sachtouris
            '--output-format'),
294 f76c6bbc Stavros Sachtouris
        json_output=FlagArgument(
295 f76c6bbc Stavros Sachtouris
            'show output in json (DEPRECATED from v0.12,'
296 f76c6bbc Stavros Sachtouris
            ' please use --output-format instead)', ('-j', '--json'))
297 545c6c29 Stavros Sachtouris
    )
298 545c6c29 Stavros Sachtouris
299 1757c616 Stavros Sachtouris
    def _print(self, output, print_method=print_items, **print_method_kwargs):
300 f76c6bbc Stavros Sachtouris
        if self['json_output'] or self['output_format']:
301 1757c616 Stavros Sachtouris
            print_json(output, out=self._out)
302 545c6c29 Stavros Sachtouris
        else:
303 eddaace7 Stavros Sachtouris
            print_method_kwargs.setdefault('out', self._out)
304 eddaace7 Stavros Sachtouris
            print_method(output, **print_method_kwargs)
305 6d190dd1 Stavros Sachtouris
306 6d190dd1 Stavros Sachtouris
307 6d190dd1 Stavros Sachtouris
class _name_filter(object):
308 6d190dd1 Stavros Sachtouris
309 6d190dd1 Stavros Sachtouris
    nf_arguments = dict(
310 6d190dd1 Stavros Sachtouris
        name=ValueArgument('filter by name', '--name'),
311 6d190dd1 Stavros Sachtouris
        name_pref=ValueArgument(
312 6d190dd1 Stavros Sachtouris
            'filter by name prefix (case insensitive)', '--name-prefix'),
313 6d190dd1 Stavros Sachtouris
        name_suff=ValueArgument(
314 6d190dd1 Stavros Sachtouris
            'filter by name suffix (case insensitive)', '--name-suffix'),
315 6d190dd1 Stavros Sachtouris
        name_like=ValueArgument(
316 6d190dd1 Stavros Sachtouris
            'print only if name contains this (case insensitive)',
317 6d190dd1 Stavros Sachtouris
            '--name-like')
318 6d190dd1 Stavros Sachtouris
    )
319 6d190dd1 Stavros Sachtouris
320 6d190dd1 Stavros Sachtouris
    def _non_exact_name_filter(self, items):
321 6d190dd1 Stavros Sachtouris
        np, ns, nl = self['name_pref'], self['name_suff'], self['name_like']
322 6d190dd1 Stavros Sachtouris
        return [item for item in items if (
323 6d190dd1 Stavros Sachtouris
            (not np) or item['name'].lower().startswith(np.lower())) and (
324 6d190dd1 Stavros Sachtouris
            (not ns) or item['name'].lower().endswith(ns.lower())) and (
325 6d190dd1 Stavros Sachtouris
            (not nl) or nl.lower() in item['name'].lower())]
326 6d190dd1 Stavros Sachtouris
327 6d190dd1 Stavros Sachtouris
    def _exact_name_filter(self, items):
328 6d190dd1 Stavros Sachtouris
        return filter_dicts_by_dict(items, dict(name=self['name'])) if (
329 6d190dd1 Stavros Sachtouris
            self['name']) else items
330 6d190dd1 Stavros Sachtouris
331 6d190dd1 Stavros Sachtouris
    def _filter_by_name(self, items):
332 6d190dd1 Stavros Sachtouris
        return self._non_exact_name_filter(self._exact_name_filter(items))
333 6d190dd1 Stavros Sachtouris
334 6d190dd1 Stavros Sachtouris
335 6d190dd1 Stavros Sachtouris
class _id_filter(object):
336 6d190dd1 Stavros Sachtouris
337 6d190dd1 Stavros Sachtouris
    if_arguments = dict(
338 6d190dd1 Stavros Sachtouris
        id=ValueArgument('filter by id', '--id'),
339 6d190dd1 Stavros Sachtouris
        id_pref=ValueArgument(
340 6d190dd1 Stavros Sachtouris
            'filter by id prefix (case insensitive)', '--id-prefix'),
341 6d190dd1 Stavros Sachtouris
        id_suff=ValueArgument(
342 6d190dd1 Stavros Sachtouris
            'filter by id suffix (case insensitive)', '--id-suffix'),
343 6d190dd1 Stavros Sachtouris
        id_like=ValueArgument(
344 6d190dd1 Stavros Sachtouris
            'print only if id contains this (case insensitive)',
345 6d190dd1 Stavros Sachtouris
            '--id-like')
346 6d190dd1 Stavros Sachtouris
    )
347 6d190dd1 Stavros Sachtouris
348 6d190dd1 Stavros Sachtouris
    def _non_exact_id_filter(self, items):
349 6d190dd1 Stavros Sachtouris
        np, ns, nl = self['id_pref'], self['id_suff'], self['id_like']
350 6d190dd1 Stavros Sachtouris
        return [item for item in items if (
351 6d190dd1 Stavros Sachtouris
            (not np) or (
352 6d190dd1 Stavros Sachtouris
                '%s' % item['id']).lower().startswith(np.lower())) and (
353 6d190dd1 Stavros Sachtouris
            (not ns) or ('%s' % item['id']).lower().endswith(ns.lower())) and (
354 6d190dd1 Stavros Sachtouris
            (not nl) or nl.lower() in ('%s' % item['id']).lower())]
355 6d190dd1 Stavros Sachtouris
356 6d190dd1 Stavros Sachtouris
    def _exact_id_filter(self, items):
357 6d190dd1 Stavros Sachtouris
        return filter_dicts_by_dict(items, dict(id=self['id'])) if (
358 6d190dd1 Stavros Sachtouris
            self['id']) else items
359 6d190dd1 Stavros Sachtouris
360 6d190dd1 Stavros Sachtouris
    def _filter_by_id(self, items):
361 6d190dd1 Stavros Sachtouris
        return self._non_exact_id_filter(self._exact_id_filter(items))