Statistics
| Branch: | Tag: | Revision:

root / snf-astakos-app / astakos / im / endpoints / qh.py @ 469d0997

History | View | Annotate | Download (13.8 kB)

1 fc1e2f02 Sofia Papagiannaki
# Copyright 2011-2012 GRNET S.A. All rights reserved.
2 5ce3ce4f Sofia Papagiannaki
#
3 fc1e2f02 Sofia Papagiannaki
# Redistribution and use in source and binary forms, with or
4 fc1e2f02 Sofia Papagiannaki
# without modification, are permitted provided that the following
5 fc1e2f02 Sofia Papagiannaki
# conditions are met:
6 5ce3ce4f Sofia Papagiannaki
#
7 fc1e2f02 Sofia Papagiannaki
#   1. Redistributions of source code must retain the above
8 fc1e2f02 Sofia Papagiannaki
#      copyright notice, this list of conditions and the following
9 fc1e2f02 Sofia Papagiannaki
#      disclaimer.
10 5ce3ce4f Sofia Papagiannaki
#
11 fc1e2f02 Sofia Papagiannaki
#   2. Redistributions in binary form must reproduce the above
12 fc1e2f02 Sofia Papagiannaki
#      copyright notice, this list of conditions and the following
13 fc1e2f02 Sofia Papagiannaki
#      disclaimer in the documentation and/or other materials
14 fc1e2f02 Sofia Papagiannaki
#      provided with the distribution.
15 5ce3ce4f Sofia Papagiannaki
#
16 fc1e2f02 Sofia Papagiannaki
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17 fc1e2f02 Sofia Papagiannaki
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 fc1e2f02 Sofia Papagiannaki
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19 fc1e2f02 Sofia Papagiannaki
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20 fc1e2f02 Sofia Papagiannaki
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 fc1e2f02 Sofia Papagiannaki
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 fc1e2f02 Sofia Papagiannaki
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23 fc1e2f02 Sofia Papagiannaki
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24 fc1e2f02 Sofia Papagiannaki
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 fc1e2f02 Sofia Papagiannaki
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26 fc1e2f02 Sofia Papagiannaki
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27 fc1e2f02 Sofia Papagiannaki
# POSSIBILITY OF SUCH DAMAGE.
28 5ce3ce4f Sofia Papagiannaki
#
29 fc1e2f02 Sofia Papagiannaki
# The views and conclusions contained in the software and
30 fc1e2f02 Sofia Papagiannaki
# documentation are those of the authors and should not be
31 fc1e2f02 Sofia Papagiannaki
# interpreted as representing official policies, either expressed
32 fc1e2f02 Sofia Papagiannaki
# or implied, of GRNET S.A.
33 fc1e2f02 Sofia Papagiannaki
34 fc1e2f02 Sofia Papagiannaki
import logging
35 bd4f356c Sofia Papagiannaki
import itertools
36 bd4f356c Sofia Papagiannaki
37 bd4f356c Sofia Papagiannaki
from functools import wraps
38 4fc7d569 Sofia Papagiannaki
from collections import namedtuple
39 fc1e2f02 Sofia Papagiannaki
40 fc1e2f02 Sofia Papagiannaki
from django.utils.translation import ugettext as _
41 fc1e2f02 Sofia Papagiannaki
42 30d92d1e Georgios D. Tsoukalas
from astakos.im.settings import (
43 0ea1f32b Georgios D. Tsoukalas
        QUOTAHOLDER_URL, QUOTAHOLDER_TOKEN, LOGGING_LEVEL)
44 fc1e2f02 Sofia Papagiannaki
45 30d92d1e Georgios D. Tsoukalas
if QUOTAHOLDER_URL:
46 c836d69f Georgios D. Tsoukalas
    from kamaki.clients.quotaholder import QuotaholderClient
47 6f00ed3e Sofia Papagiannaki
    from kamaki.clients.quotaholder import QH_PRACTICALLY_INFINITE
48 8b59b8ea Sofia Papagiannaki
49 437c0052 Sofia Papagiannaki
from synnefo.util.number import strbigdec
50 437c0052 Sofia Papagiannaki
51 fc1e2f02 Sofia Papagiannaki
ENTITY_KEY = '1'
52 fc1e2f02 Sofia Papagiannaki
53 ae497612 Olga Brani
54 fc1e2f02 Sofia Papagiannaki
logger = logging.getLogger(__name__)
55 fc1e2f02 Sofia Papagiannaki
56 ae497612 Olga Brani
inf = float('inf')
57 5ce3ce4f Sofia Papagiannaki
58 ee45eb81 Giorgos Korfiatis
clientkey = 'astakos'
59 ee45eb81 Giorgos Korfiatis
60 73fbaec4 Sofia Papagiannaki
_client = None
61 73fbaec4 Sofia Papagiannaki
def get_client():
62 73fbaec4 Sofia Papagiannaki
    global _client
63 73fbaec4 Sofia Papagiannaki
    if _client:
64 73fbaec4 Sofia Papagiannaki
        return _client
65 73fbaec4 Sofia Papagiannaki
    if not QUOTAHOLDER_URL:
66 73fbaec4 Sofia Papagiannaki
        return
67 73fbaec4 Sofia Papagiannaki
    _client = QuotaholderClient(QUOTAHOLDER_URL, token=QUOTAHOLDER_TOKEN)
68 52116521 Sofia Papagiannaki
    return _client
69 73fbaec4 Sofia Papagiannaki
70 8978cfbd Sofia Papagiannaki
def set_quota(payload):
71 8978cfbd Sofia Papagiannaki
    c = get_client()
72 8978cfbd Sofia Papagiannaki
    if not c:
73 8978cfbd Sofia Papagiannaki
        return
74 8978cfbd Sofia Papagiannaki
    result = c.set_quota(context={}, clientkey=clientkey, set_quota=payload)
75 5cdd7df3 Georgios D. Tsoukalas
    logger.debug('set_quota: %s rejected: %s' % (payload, result))
76 8978cfbd Sofia Papagiannaki
    return result
77 8978cfbd Sofia Papagiannaki
78 84a3f701 Giorgos Korfiatis
def get_entity(payload):
79 84a3f701 Giorgos Korfiatis
    c = get_client()
80 84a3f701 Giorgos Korfiatis
    if not c:
81 84a3f701 Giorgos Korfiatis
        return
82 84a3f701 Giorgos Korfiatis
    result = c.get_entity(context={}, get_entity=payload)
83 5cdd7df3 Georgios D. Tsoukalas
    logger.debug('get_entity: %s reply: %s' % (payload, result))
84 84a3f701 Giorgos Korfiatis
    return result
85 84a3f701 Giorgos Korfiatis
86 84a3f701 Giorgos Korfiatis
def get_holding(payload):
87 84a3f701 Giorgos Korfiatis
    c = get_client()
88 84a3f701 Giorgos Korfiatis
    if not c:
89 84a3f701 Giorgos Korfiatis
        return
90 84a3f701 Giorgos Korfiatis
    result = c.get_holding(context={}, get_holding=payload)
91 5cdd7df3 Georgios D. Tsoukalas
    logger.debug('get_holding: %s reply: %s' % (payload, result))
92 84a3f701 Giorgos Korfiatis
    return result
93 84a3f701 Giorgos Korfiatis
94 84a3f701 Giorgos Korfiatis
def qh_get_holdings(users, resources):
95 84a3f701 Giorgos Korfiatis
    payload = []
96 84a3f701 Giorgos Korfiatis
    append = payload.append
97 84a3f701 Giorgos Korfiatis
    for user in users:
98 84a3f701 Giorgos Korfiatis
        for resource in resources:
99 84a3f701 Giorgos Korfiatis
            append((user.uuid, resource, ENTITY_KEY),)
100 84a3f701 Giorgos Korfiatis
    result = get_holding(payload)
101 84a3f701 Giorgos Korfiatis
    return result
102 84a3f701 Giorgos Korfiatis
103 5aac5dc4 Giorgos Korfiatis
def quota_limits_per_user_from_get(lst):
104 5aac5dc4 Giorgos Korfiatis
    quotas = {}
105 5aac5dc4 Giorgos Korfiatis
    for holder, resource, q, c, il, el, imp, exp, ret, rel, flags in lst:
106 5aac5dc4 Giorgos Korfiatis
        userquotas = quotas.get(holder, {})
107 5aac5dc4 Giorgos Korfiatis
        userquotas[resource] = QuotaValues(quantity=q, capacity=c,
108 5aac5dc4 Giorgos Korfiatis
                                           import_limit=il, export_limit=el)
109 5aac5dc4 Giorgos Korfiatis
        quotas[holder] = userquotas
110 5aac5dc4 Giorgos Korfiatis
    return quotas
111 5aac5dc4 Giorgos Korfiatis
112 84a3f701 Giorgos Korfiatis
def qh_get_quota(users, resources):
113 8978cfbd Sofia Papagiannaki
    c = get_client()
114 8978cfbd Sofia Papagiannaki
    if not c:
115 8978cfbd Sofia Papagiannaki
        return
116 16cfac45 Sofia Papagiannaki
    payload = []
117 16cfac45 Sofia Papagiannaki
    append = payload.append
118 84a3f701 Giorgos Korfiatis
    for user in users:
119 84a3f701 Giorgos Korfiatis
        for resource in resources:
120 84a3f701 Giorgos Korfiatis
            append((user.uuid, resource, ENTITY_KEY),)
121 84a3f701 Giorgos Korfiatis
122 8978cfbd Sofia Papagiannaki
    result = c.get_quota(context={}, clientkey=clientkey, get_quota=payload)
123 5cdd7df3 Georgios D. Tsoukalas
    logger.debug('get_quota: %s rejected: %s' % (payload, result))
124 8978cfbd Sofia Papagiannaki
    return result
125 8978cfbd Sofia Papagiannaki
126 84a3f701 Giorgos Korfiatis
def qh_get_quota_limits(users, resources):
127 84a3f701 Giorgos Korfiatis
    result = qh_get_quota(users, resources)
128 5aac5dc4 Giorgos Korfiatis
    return quota_limits_per_user_from_get(result)
129 84a3f701 Giorgos Korfiatis
130 8978cfbd Sofia Papagiannaki
def create_entity(payload):
131 8978cfbd Sofia Papagiannaki
    c = get_client()
132 8978cfbd Sofia Papagiannaki
    if not c:
133 8978cfbd Sofia Papagiannaki
        return
134 6c997921 Sofia Papagiannaki
    result = c.create_entity(
135 6c997921 Sofia Papagiannaki
        context={}, clientkey=clientkey, create_entity=payload)
136 5cdd7df3 Georgios D. Tsoukalas
    logger.debug('create_entity: %s rejected: %s' % (payload, result))
137 8978cfbd Sofia Papagiannaki
    return result
138 5ce3ce4f Sofia Papagiannaki
139 8978cfbd Sofia Papagiannaki
SetQuotaPayload = namedtuple('SetQuotaPayload', ('holder',
140 8978cfbd Sofia Papagiannaki
                                                 'resource',
141 8978cfbd Sofia Papagiannaki
                                                 'key',
142 8978cfbd Sofia Papagiannaki
                                                 'quantity',
143 8978cfbd Sofia Papagiannaki
                                                 'capacity',
144 8978cfbd Sofia Papagiannaki
                                                 'import_limit',
145 8978cfbd Sofia Papagiannaki
                                                 'export_limit',
146 8978cfbd Sofia Papagiannaki
                                                 'flags'))
147 8978cfbd Sofia Papagiannaki
148 8978cfbd Sofia Papagiannaki
GetQuotaPayload = namedtuple('GetQuotaPayload', ('holder',
149 8978cfbd Sofia Papagiannaki
                                                 'resource',
150 8978cfbd Sofia Papagiannaki
                                                 'key'))
151 8978cfbd Sofia Papagiannaki
152 8978cfbd Sofia Papagiannaki
CreateEntityPayload = namedtuple('CreateEntityPayload', ('entity',
153 16cfac45 Sofia Papagiannaki
                                                         'owner',
154 16cfac45 Sofia Papagiannaki
                                                         'key',
155 16cfac45 Sofia Papagiannaki
                                                         'ownerkey'))
156 2a97d93b Giorgos Korfiatis
QuotaLimits = namedtuple('QuotaLimits', ('holder',
157 5cfd4acb Sofia Papagiannaki
                                         'resource',
158 2a97d93b Giorgos Korfiatis
                                         'capacity',
159 437c0052 Sofia Papagiannaki
                                        'import_limit',
160 2a97d93b Giorgos Korfiatis
                                         'export_limit'))
161 2a97d93b Giorgos Korfiatis
162 437c0052 Sofia Papagiannaki
class QuotaValues(namedtuple('QuotaValues', ('quantity',
163 437c0052 Sofia Papagiannaki
                                             'capacity',
164 437c0052 Sofia Papagiannaki
                                             'import_limit',
165 437c0052 Sofia Papagiannaki
                                             'export_limit'))):
166 437c0052 Sofia Papagiannaki
    __slots__ = ()
167 437c0052 Sofia Papagiannaki
    def __dir__(self):
168 437c0052 Sofia Papagiannaki
            return ['quantity', 'capacity', 'import_limit', 'export_limit']
169 437c0052 Sofia Papagiannaki
170 437c0052 Sofia Papagiannaki
    def __str__(self):
171 437c0052 Sofia Papagiannaki
        return '\t'.join(['%s=%s' % (f, strbigdec(getattr(self, f))) for f in dir(self)])
172 0514bcc7 Giorgos Korfiatis
173 0514bcc7 Giorgos Korfiatis
def add_quota_values(q1, q2):
174 0514bcc7 Giorgos Korfiatis
    return QuotaValues(
175 0514bcc7 Giorgos Korfiatis
        quantity = q1.quantity + q2.quantity,
176 0514bcc7 Giorgos Korfiatis
        capacity = q1.capacity + q2.capacity,
177 0514bcc7 Giorgos Korfiatis
        import_limit = q1.import_limit + q2.import_limit,
178 0514bcc7 Giorgos Korfiatis
        export_limit = q1.export_limit + q2.export_limit)
179 0514bcc7 Giorgos Korfiatis
180 84a3f701 Giorgos Korfiatis
def qh_register_user_with_quotas(user):
181 84a3f701 Giorgos Korfiatis
    return register_users_with_quotas([user])
182 b4be4eee Giorgos Korfiatis
183 84a3f701 Giorgos Korfiatis
def register_users_with_quotas(users):
184 84a3f701 Giorgos Korfiatis
    rejected = register_users(users)
185 0514bcc7 Giorgos Korfiatis
    if not rejected:
186 0514bcc7 Giorgos Korfiatis
        register_quotas(users)
187 0514bcc7 Giorgos Korfiatis
188 84a3f701 Giorgos Korfiatis
def register_users(users):
189 84a3f701 Giorgos Korfiatis
    if not users:
190 84a3f701 Giorgos Korfiatis
        return
191 84a3f701 Giorgos Korfiatis
192 8978cfbd Sofia Papagiannaki
    payload = list(CreateEntityPayload(
193 8978cfbd Sofia Papagiannaki
                    entity=u.uuid,
194 8978cfbd Sofia Papagiannaki
                    owner='system',
195 8978cfbd Sofia Papagiannaki
                    key=ENTITY_KEY,
196 8978cfbd Sofia Papagiannaki
                    ownerkey='') for u in users)
197 0514bcc7 Giorgos Korfiatis
    return create_entity(payload)
198 8978cfbd Sofia Papagiannaki
199 0514bcc7 Giorgos Korfiatis
def register_quotas(users):
200 84a3f701 Giorgos Korfiatis
    if not users:
201 84a3f701 Giorgos Korfiatis
        return
202 84a3f701 Giorgos Korfiatis
203 0514bcc7 Giorgos Korfiatis
    payload = []
204 0514bcc7 Giorgos Korfiatis
    append = payload.append
205 0514bcc7 Giorgos Korfiatis
    for u in users:
206 0514bcc7 Giorgos Korfiatis
        for resource, q in u.all_quotas().iteritems():
207 0514bcc7 Giorgos Korfiatis
            append( SetQuotaPayload(
208 0514bcc7 Giorgos Korfiatis
                    holder=u.uuid,
209 0514bcc7 Giorgos Korfiatis
                    resource=resource,
210 0514bcc7 Giorgos Korfiatis
                    key=ENTITY_KEY,
211 0514bcc7 Giorgos Korfiatis
                    quantity=q.quantity,
212 0514bcc7 Giorgos Korfiatis
                    capacity=q.capacity,
213 0514bcc7 Giorgos Korfiatis
                    import_limit=q.import_limit,
214 0514bcc7 Giorgos Korfiatis
                    export_limit=q.export_limit,
215 0514bcc7 Giorgos Korfiatis
                    flags=0))
216 0514bcc7 Giorgos Korfiatis
    return set_quota(payload)
217 0514bcc7 Giorgos Korfiatis
218 5aac5dc4 Giorgos Korfiatis
def send_quotas(userquotas):
219 5aac5dc4 Giorgos Korfiatis
    if not userquotas:
220 5aac5dc4 Giorgos Korfiatis
        return
221 5aac5dc4 Giorgos Korfiatis
222 5aac5dc4 Giorgos Korfiatis
    payload = []
223 5aac5dc4 Giorgos Korfiatis
    append = payload.append
224 5aac5dc4 Giorgos Korfiatis
    for holder, quotas in userquotas.iteritems():
225 5aac5dc4 Giorgos Korfiatis
        for resource, q in quotas.iteritems():
226 5aac5dc4 Giorgos Korfiatis
            append( SetQuotaPayload(
227 5aac5dc4 Giorgos Korfiatis
                    holder=holder,
228 5aac5dc4 Giorgos Korfiatis
                    resource=resource,
229 5aac5dc4 Giorgos Korfiatis
                    key=ENTITY_KEY,
230 5aac5dc4 Giorgos Korfiatis
                    quantity=q.quantity,
231 5aac5dc4 Giorgos Korfiatis
                    capacity=q.capacity,
232 5aac5dc4 Giorgos Korfiatis
                    import_limit=q.import_limit,
233 5aac5dc4 Giorgos Korfiatis
                    export_limit=q.export_limit,
234 5aac5dc4 Giorgos Korfiatis
                    flags=0))
235 5aac5dc4 Giorgos Korfiatis
    return set_quota(payload)
236 5aac5dc4 Giorgos Korfiatis
237 0514bcc7 Giorgos Korfiatis
def register_services(services):
238 cc5e8965 Giorgos Korfiatis
    def payload(services):
239 cc5e8965 Giorgos Korfiatis
        return list(CreateEntityPayload(
240 cc5e8965 Giorgos Korfiatis
                entity=service,
241 cc5e8965 Giorgos Korfiatis
                owner='system',
242 cc5e8965 Giorgos Korfiatis
                key=ENTITY_KEY,
243 cc5e8965 Giorgos Korfiatis
                ownerkey='')
244 cc5e8965 Giorgos Korfiatis
                    for service in set(services))
245 cc5e8965 Giorgos Korfiatis
246 cc5e8965 Giorgos Korfiatis
    if not services:
247 cc5e8965 Giorgos Korfiatis
        return
248 cc5e8965 Giorgos Korfiatis
    existing = create_entity(payload(services))
249 cc5e8965 Giorgos Korfiatis
    if 0 < len(existing) < len(services):
250 cc5e8965 Giorgos Korfiatis
        nonexisting = [s for i, s in enumerate(services)
251 cc5e8965 Giorgos Korfiatis
                       if i not in existing]
252 cc5e8965 Giorgos Korfiatis
        r = create_entity(payload(nonexisting))
253 cc5e8965 Giorgos Korfiatis
        if r:
254 cc5e8965 Giorgos Korfiatis
            failed = [s for i, s in enumerate(nonexisting)
255 cc5e8965 Giorgos Korfiatis
                      if i in r]
256 cc5e8965 Giorgos Korfiatis
            m = "Failed to register services: %s" % (failed,)
257 cc5e8965 Giorgos Korfiatis
            raise RuntimeError(m)
258 0514bcc7 Giorgos Korfiatis
259 0514bcc7 Giorgos Korfiatis
def register_resources(resources):
260 05375e71 root
    try:
261 05375e71 root
        QH_PRACTICALLY_INFINITE
262 05375e71 root
    except NameError:
263 05375e71 root
        return
264 05375e71 root
265 0514bcc7 Giorgos Korfiatis
    payload = list(SetQuotaPayload(
266 0514bcc7 Giorgos Korfiatis
            holder=resource.service,
267 0514bcc7 Giorgos Korfiatis
            resource=resource,
268 0514bcc7 Giorgos Korfiatis
            key=ENTITY_KEY,
269 0514bcc7 Giorgos Korfiatis
            quantity=QH_PRACTICALLY_INFINITE,
270 9ca6197a Georgios D. Tsoukalas
            capacity=QH_PRACTICALLY_INFINITE,
271 0514bcc7 Giorgos Korfiatis
            import_limit=QH_PRACTICALLY_INFINITE,
272 0514bcc7 Giorgos Korfiatis
            export_limit=QH_PRACTICALLY_INFINITE,
273 0514bcc7 Giorgos Korfiatis
            flags=0) for resource in resources)
274 0514bcc7 Giorgos Korfiatis
    return set_quota(payload)
275 8978cfbd Sofia Papagiannaki
276 84a3f701 Giorgos Korfiatis
def qh_check_users(users):
277 84a3f701 Giorgos Korfiatis
    payload = [(u.uuid, ENTITY_KEY) for u in users]
278 84a3f701 Giorgos Korfiatis
    result = get_entity(payload)
279 84a3f701 Giorgos Korfiatis
    uuids = [entity for (entity, owner) in result]
280 84a3f701 Giorgos Korfiatis
281 84a3f701 Giorgos Korfiatis
    existing = []
282 84a3f701 Giorgos Korfiatis
    nonexisting = []
283 84a3f701 Giorgos Korfiatis
    for u in users:
284 84a3f701 Giorgos Korfiatis
        if u.uuid in uuids:
285 84a3f701 Giorgos Korfiatis
            existing.append(u)
286 84a3f701 Giorgos Korfiatis
        else:
287 84a3f701 Giorgos Korfiatis
            nonexisting.append(u)
288 84a3f701 Giorgos Korfiatis
    return (existing, nonexisting)
289 84a3f701 Giorgos Korfiatis
290 d2b32360 Giorgos Korfiatis
def qh_add_quota(serial, sub_list, add_list):
291 ee45eb81 Giorgos Korfiatis
    if not QUOTAHOLDER_URL:
292 ee45eb81 Giorgos Korfiatis
        return ()
293 ee45eb81 Giorgos Korfiatis
294 ee45eb81 Giorgos Korfiatis
    context = {}
295 ee45eb81 Giorgos Korfiatis
    c = get_client()
296 4319c408 Kostas Papadimitriou
297 d2b32360 Giorgos Korfiatis
    sub_quota = []
298 d2b32360 Giorgos Korfiatis
    sub_append = sub_quota.append
299 d2b32360 Giorgos Korfiatis
    add_quota = []
300 d2b32360 Giorgos Korfiatis
    add_append = add_quota.append
301 d2b32360 Giorgos Korfiatis
302 5cfd4acb Sofia Papagiannaki
    for ql in sub_list:
303 d2b32360 Giorgos Korfiatis
        args = (ql.holder, ql.resource, ENTITY_KEY,
304 d2b32360 Giorgos Korfiatis
                0, ql.capacity, ql.import_limit, ql.export_limit)
305 d2b32360 Giorgos Korfiatis
        sub_append(args)
306 d2b32360 Giorgos Korfiatis
307 5cfd4acb Sofia Papagiannaki
    for ql in add_list:
308 2a97d93b Giorgos Korfiatis
        args = (ql.holder, ql.resource, ENTITY_KEY,
309 2a97d93b Giorgos Korfiatis
                0, ql.capacity, ql.import_limit, ql.export_limit)
310 d2b32360 Giorgos Korfiatis
        add_append(args)
311 2a97d93b Giorgos Korfiatis
312 ee45eb81 Giorgos Korfiatis
    result = c.add_quota(context=context,
313 ee45eb81 Giorgos Korfiatis
                         clientkey=clientkey,
314 ee45eb81 Giorgos Korfiatis
                         serial=serial,
315 d2b32360 Giorgos Korfiatis
                         sub_quota=sub_quota,
316 d2b32360 Giorgos Korfiatis
                         add_quota=add_quota)
317 ee45eb81 Giorgos Korfiatis
318 ee45eb81 Giorgos Korfiatis
    return result
319 ee45eb81 Giorgos Korfiatis
320 ee45eb81 Giorgos Korfiatis
def qh_query_serials(serials):
321 ee45eb81 Giorgos Korfiatis
    if not QUOTAHOLDER_URL:
322 ee45eb81 Giorgos Korfiatis
        return ()
323 ee45eb81 Giorgos Korfiatis
324 ee45eb81 Giorgos Korfiatis
    context = {}
325 ee45eb81 Giorgos Korfiatis
    c = get_client()
326 ee45eb81 Giorgos Korfiatis
    result = c.query_serials(context=context,
327 ee45eb81 Giorgos Korfiatis
                             clientkey=clientkey,
328 ee45eb81 Giorgos Korfiatis
                             serials=serials)
329 ee45eb81 Giorgos Korfiatis
    return result
330 ee45eb81 Giorgos Korfiatis
331 ee45eb81 Giorgos Korfiatis
def qh_ack_serials(serials):
332 ee45eb81 Giorgos Korfiatis
    if not QUOTAHOLDER_URL:
333 ee45eb81 Giorgos Korfiatis
        return ()
334 ee45eb81 Giorgos Korfiatis
335 ee45eb81 Giorgos Korfiatis
    context = {}
336 ee45eb81 Giorgos Korfiatis
    c = get_client()
337 ee45eb81 Giorgos Korfiatis
    result = c.ack_serials(context=context,
338 ee45eb81 Giorgos Korfiatis
                           clientkey=clientkey,
339 ee45eb81 Giorgos Korfiatis
                           serials=serials)
340 ee45eb81 Giorgos Korfiatis
    return
341 5ce3ce4f Sofia Papagiannaki
342 2925e285 root
from datetime import datetime
343 2925e285 root
344 2925e285 root
strptime = datetime.strptime
345 2925e285 root
timefmt = '%Y-%m-%dT%H:%M:%S.%f'
346 2925e285 root
347 476fdba1 root
SECOND_RESOLUTION = 1
348 476fdba1 root
349 9a06d96f Olga Brani
350 2925e285 root
def total_seconds(timedelta_object):
351 2925e285 root
    return timedelta_object.seconds + timedelta_object.days * 86400
352 2925e285 root
353 9a06d96f Olga Brani
354 476fdba1 root
def iter_timeline(timeline, before):
355 476fdba1 root
    if not timeline:
356 476fdba1 root
        return
357 476fdba1 root
358 476fdba1 root
    for t in timeline:
359 476fdba1 root
        yield t
360 476fdba1 root
361 476fdba1 root
    t = dict(t)
362 476fdba1 root
    t['issue_time'] = before
363 476fdba1 root
    yield t
364 476fdba1 root
365 9a06d96f Olga Brani
366 476fdba1 root
def _usage_units(timeline, after, before, details=0):
367 476fdba1 root
368 2925e285 root
    t_total = 0
369 476fdba1 root
    uu_total = 0
370 476fdba1 root
    t_after = strptime(after, timefmt)
371 476fdba1 root
    t_before = strptime(before, timefmt)
372 476fdba1 root
    t0 = t_after
373 476fdba1 root
    u0 = 0
374 2925e285 root
375 476fdba1 root
    for point in iter_timeline(timeline, before):
376 2925e285 root
        issue_time = point['issue_time']
377 2925e285 root
378 476fdba1 root
        if issue_time <= after:
379 476fdba1 root
            u0 = point['target_allocated_through']
380 2925e285 root
            continue
381 2925e285 root
382 476fdba1 root
        t = strptime(issue_time, timefmt) if issue_time <= before else t_before
383 476fdba1 root
        t_diff = int(total_seconds(t - t0) * SECOND_RESOLUTION)
384 2925e285 root
        t_total += t_diff
385 2925e285 root
        uu_cost = u0 * t_diff
386 2925e285 root
        uu_total += uu_cost
387 476fdba1 root
        t0 = t
388 476fdba1 root
        u0 = point['target_allocated_through']
389 2925e285 root
390 476fdba1 root
        target = point['target']
391 2925e285 root
        if details:
392 2925e285 root
            yield  (target,
393 2925e285 root
                    point['resource'],
394 2925e285 root
                    point['name'],
395 2925e285 root
                    issue_time,
396 2925e285 root
                    uu_cost,
397 2925e285 root
                    uu_total)
398 2925e285 root
399 2925e285 root
    if not t_total:
400 2925e285 root
        return
401 2925e285 root
402 2925e285 root
    yield  (target,
403 2925e285 root
            'total',
404 2925e285 root
            point['resource'],
405 2925e285 root
            issue_time,
406 9a06d96f Olga Brani
            uu_total / t_total,
407 2925e285 root
            uu_total)
408 2925e285 root
409 9a06d96f Olga Brani
410 476fdba1 root
def usage_units(timeline, after, before, details=0):
411 476fdba1 root
    return list(_usage_units(timeline, after, before, details=details))
412 2925e285 root
413 9a06d96f Olga Brani
414 476fdba1 root
def traffic_units(timeline, after, before, details=0):
415 82b05401 root
    tu_total = 0
416 82b05401 root
    target = None
417 82b05401 root
    issue_time = None
418 82b05401 root
419 82b05401 root
    for point in timeline:
420 82b05401 root
        issue_time = point['issue_time']
421 476fdba1 root
        if issue_time <= after:
422 476fdba1 root
            continue
423 476fdba1 root
        if issue_time > before:
424 476fdba1 root
            break
425 476fdba1 root
426 476fdba1 root
        target = point['target']
427 82b05401 root
        tu = point['target_allocated_through']
428 82b05401 root
        tu_total += tu
429 82b05401 root
430 82b05401 root
        if details:
431 82b05401 root
            yield  (target,
432 82b05401 root
                    point['resource'],
433 82b05401 root
                    point['name'],
434 82b05401 root
                    issue_time,
435 82b05401 root
                    tu,
436 82b05401 root
                    tu_total)
437 82b05401 root
438 82b05401 root
    if not tu_total:
439 82b05401 root
        return
440 82b05401 root
441 82b05401 root
    yield  (target,
442 82b05401 root
            'total',
443 82b05401 root
            point['resource'],
444 82b05401 root
            issue_time,
445 9a06d96f Olga Brani
            tu_total // len(timeline),
446 82b05401 root
            tu_total)
447 2925e285 root
448 9a06d96f Olga Brani
449 2925e285 root
def timeline_charge(entity, resource, after, before, details, charge_type):
450 2925e285 root
    key = '1'
451 2925e285 root
    if charge_type == 'charge_usage':
452 2925e285 root
        charge_units = usage_units
453 2925e285 root
    elif charge_type == 'charge_traffic':
454 2925e285 root
        charge_units = traffic_units
455 2925e285 root
    else:
456 2925e285 root
        m = 'charge type %s not supported' % charge_type
457 2925e285 root
        raise ValueError(m)
458 2925e285 root
459 30d92d1e Georgios D. Tsoukalas
    quotaholder = QuotaholderClient(QUOTAHOLDER_URL, token=QUOTAHOLDER_TOKEN)
460 2925e285 root
    timeline = quotaholder.get_timeline(
461 9a06d96f Olga Brani
        context={},
462 9a06d96f Olga Brani
        after=after,
463 9a06d96f Olga Brani
        before=before,
464 9a06d96f Olga Brani
        get_timeline=[[entity, resource, key]])
465 476fdba1 root
    cu = charge_units(timeline, after, before, details=details)
466 82b05401 root
    return cu