Statistics
| Branch: | Tag: | Revision:

root / snf-astakos-app / astakos / test / stress.py @ a1ed6730

History | View | Annotate | Download (7.4 kB)

1 0932ac43 Giorgos Korfiatis
#!/usr/bin/env python
2 0932ac43 Giorgos Korfiatis
# -*- coding: utf-8 -*-
3 0932ac43 Giorgos Korfiatis
4 0932ac43 Giorgos Korfiatis
# Copyright 2013 GRNET S.A. All rights reserved.
5 0932ac43 Giorgos Korfiatis
#
6 0932ac43 Giorgos Korfiatis
# Redistribution and use in source and binary forms, with or
7 0932ac43 Giorgos Korfiatis
# without modification, are permitted provided that the following
8 0932ac43 Giorgos Korfiatis
# conditions are met:
9 0932ac43 Giorgos Korfiatis
#
10 0932ac43 Giorgos Korfiatis
#   1. Redistributions of source code must retain the above
11 0932ac43 Giorgos Korfiatis
#      copyright notice, this list of conditions and the following
12 0932ac43 Giorgos Korfiatis
#      disclaimer.
13 0932ac43 Giorgos Korfiatis
#
14 0932ac43 Giorgos Korfiatis
#   2. Redistributions in binary form must reproduce the above
15 0932ac43 Giorgos Korfiatis
#      copyright notice, this list of conditions and the following
16 0932ac43 Giorgos Korfiatis
#      disclaimer in the documentation and/or other materials
17 0932ac43 Giorgos Korfiatis
#      provided with the distribution.
18 0932ac43 Giorgos Korfiatis
#
19 0932ac43 Giorgos Korfiatis
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
20 0932ac43 Giorgos Korfiatis
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
21 0932ac43 Giorgos Korfiatis
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 0932ac43 Giorgos Korfiatis
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
23 0932ac43 Giorgos Korfiatis
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 0932ac43 Giorgos Korfiatis
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 0932ac43 Giorgos Korfiatis
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
26 0932ac43 Giorgos Korfiatis
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
27 0932ac43 Giorgos Korfiatis
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28 0932ac43 Giorgos Korfiatis
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
29 0932ac43 Giorgos Korfiatis
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
30 0932ac43 Giorgos Korfiatis
# POSSIBILITY OF SUCH DAMAGE.
31 0932ac43 Giorgos Korfiatis
#
32 0932ac43 Giorgos Korfiatis
# The views and conclusions contained in the software and
33 0932ac43 Giorgos Korfiatis
# documentation are those of the authors and should not be
34 0932ac43 Giorgos Korfiatis
# interpreted as representing official policies, either expressed
35 0932ac43 Giorgos Korfiatis
# or implied, of GRNET S.A.
36 0932ac43 Giorgos Korfiatis
37 0932ac43 Giorgos Korfiatis
import os
38 0932ac43 Giorgos Korfiatis
from optparse import OptionParser
39 0932ac43 Giorgos Korfiatis
from time import sleep
40 0932ac43 Giorgos Korfiatis
import threading
41 0932ac43 Giorgos Korfiatis
import datetime
42 0932ac43 Giorgos Korfiatis
from random import choice, randint
43 0932ac43 Giorgos Korfiatis
import logging
44 0932ac43 Giorgos Korfiatis
45 0932ac43 Giorgos Korfiatis
path = os.path.dirname(os.path.realpath(__file__))
46 0932ac43 Giorgos Korfiatis
os.environ['SYNNEFO_SETTINGS_DIR'] = path + '/settings'
47 0932ac43 Giorgos Korfiatis
os.environ['DJANGO_SETTINGS_MODULE'] = 'synnefo.settings'
48 0932ac43 Giorgos Korfiatis
49 770dba12 Giorgos Korfiatis
from astakos.im.models import AstakosUser
50 0932ac43 Giorgos Korfiatis
from astakos.im.functions import get_chain_of_application_id
51 770dba12 Giorgos Korfiatis
from astakos.im import quotas
52 0932ac43 Giorgos Korfiatis
from views import submit, approve, join, leave
53 b830f774 Giorgos Korfiatis
from snf_django.lib.db.transaction import commit_on_success_strict
54 770dba12 Giorgos Korfiatis
from django.core.exceptions import PermissionDenied
55 0932ac43 Giorgos Korfiatis
56 0932ac43 Giorgos Korfiatis
USERS = {}
57 0932ac43 Giorgos Korfiatis
PROJECTS = {}
58 0932ac43 Giorgos Korfiatis
59 327eb666 Giorgos Korfiatis
logger = logging.getLogger(__name__)
60 327eb666 Giorgos Korfiatis
logger.setLevel(logging.INFO)
61 327eb666 Giorgos Korfiatis
62 0932ac43 Giorgos Korfiatis
63 0932ac43 Giorgos Korfiatis
def random_name():
64 0932ac43 Giorgos Korfiatis
    alphabet = u'abcdef_123490αβγδεζ'
65 0932ac43 Giorgos Korfiatis
    length = randint(1, 15)
66 0932ac43 Giorgos Korfiatis
    return ''.join(choice(alphabet) for _ in xrange(length))
67 0932ac43 Giorgos Korfiatis
68 0932ac43 Giorgos Korfiatis
69 0932ac43 Giorgos Korfiatis
def random_email():
70 0932ac43 Giorgos Korfiatis
    alphabet = u'abcdef_123490'
71 0932ac43 Giorgos Korfiatis
    length = randint(1, 10)
72 0932ac43 Giorgos Korfiatis
    first = ''.join(choice(alphabet) for _ in xrange(length))
73 0932ac43 Giorgos Korfiatis
74 0932ac43 Giorgos Korfiatis
    alphabet = u'abcdef'
75 327eb666 Giorgos Korfiatis
    length = randint(2, 4)
76 0932ac43 Giorgos Korfiatis
    last = ''.join(choice(alphabet) for _ in xrange(length))
77 770dba12 Giorgos Korfiatis
    return first + '@' + last + '.com'
78 0932ac43 Giorgos Korfiatis
79 0932ac43 Giorgos Korfiatis
80 0932ac43 Giorgos Korfiatis
def new_user():
81 0932ac43 Giorgos Korfiatis
    email = random_email()
82 770dba12 Giorgos Korfiatis
    defaults = {'first_name': random_name(),
83 770dba12 Giorgos Korfiatis
                'last_name': random_name(),
84 770dba12 Giorgos Korfiatis
                'is_active': True,
85 770dba12 Giorgos Korfiatis
                }
86 770dba12 Giorgos Korfiatis
    u, created = AstakosUser.objects.get_or_create(
87 770dba12 Giorgos Korfiatis
        email=email, defaults=defaults)
88 770dba12 Giorgos Korfiatis
    if created:
89 770dba12 Giorgos Korfiatis
        quotas.qh_sync_user(u)
90 770dba12 Giorgos Korfiatis
        return u.id, u.email
91 770dba12 Giorgos Korfiatis
    return None
92 0932ac43 Giorgos Korfiatis
93 0932ac43 Giorgos Korfiatis
94 757f3256 Giorgos Korfiatis
@commit_on_success_strict()
95 0932ac43 Giorgos Korfiatis
def new_users(count):
96 0932ac43 Giorgos Korfiatis
    for i in range(count):
97 770dba12 Giorgos Korfiatis
        while True:
98 770dba12 Giorgos Korfiatis
            result = new_user()
99 770dba12 Giorgos Korfiatis
            if result is not None:
100 770dba12 Giorgos Korfiatis
                uid, email = result
101 770dba12 Giorgos Korfiatis
                USERS[uid] = email
102 770dba12 Giorgos Korfiatis
                break
103 0932ac43 Giorgos Korfiatis
104 0932ac43 Giorgos Korfiatis
105 0932ac43 Giorgos Korfiatis
class SubmitApproveT(threading.Thread):
106 0932ac43 Giorgos Korfiatis
    def __init__(self, *args, **kwargs):
107 0932ac43 Giorgos Korfiatis
        self.repeat = kwargs.pop('repeat', 1)
108 0932ac43 Giorgos Korfiatis
        threading.Thread.__init__(self, *args, **kwargs)
109 0932ac43 Giorgos Korfiatis
110 0932ac43 Giorgos Korfiatis
    def run(self):
111 0932ac43 Giorgos Korfiatis
        owner = choice(USERS.keys())
112 0932ac43 Giorgos Korfiatis
        p_name = random_name()
113 0932ac43 Giorgos Korfiatis
        submit_and_approve(p_name, owner, None, self.repeat,
114 327eb666 Giorgos Korfiatis
                           prefix=self.name)
115 0932ac43 Giorgos Korfiatis
116 0932ac43 Giorgos Korfiatis
117 0932ac43 Giorgos Korfiatis
def submit_and_approve(name, user_id, prec, repeat, prefix=""):
118 0932ac43 Giorgos Korfiatis
    if prefix:
119 0932ac43 Giorgos Korfiatis
        prefix += ' '
120 0932ac43 Giorgos Korfiatis
121 0932ac43 Giorgos Korfiatis
    for i in range(repeat):
122 0932ac43 Giorgos Korfiatis
        try:
123 0932ac43 Giorgos Korfiatis
            now = datetime.datetime.now()
124 327eb666 Giorgos Korfiatis
            logger.info('%s%s: submitting with precursor %s'
125 327eb666 Giorgos Korfiatis
                        % (prefix, now, prec))
126 0932ac43 Giorgos Korfiatis
            app_id = submit(name, user_id, prec)
127 0932ac43 Giorgos Korfiatis
            prec = app_id
128 770dba12 Giorgos Korfiatis
        except PermissionDenied as e:
129 770dba12 Giorgos Korfiatis
            logger.info('Limit reached')
130 0932ac43 Giorgos Korfiatis
        except Exception as e:
131 327eb666 Giorgos Korfiatis
            logger.exception(e)
132 770dba12 Giorgos Korfiatis
            continue
133 0932ac43 Giorgos Korfiatis
        try:
134 0932ac43 Giorgos Korfiatis
            now = datetime.datetime.now()
135 0932ac43 Giorgos Korfiatis
            pid = get_chain_of_application_id(app_id)
136 327eb666 Giorgos Korfiatis
            logger.info('%s%s: approving application %s of project %s'
137 327eb666 Giorgos Korfiatis
                        % (prefix, now, app_id, pid))
138 0932ac43 Giorgos Korfiatis
            approve(app_id)
139 0932ac43 Giorgos Korfiatis
            PROJECTS[pid] = True
140 0932ac43 Giorgos Korfiatis
        except Exception as e:
141 327eb666 Giorgos Korfiatis
            logger.exception(e)
142 327eb666 Giorgos Korfiatis
143 0932ac43 Giorgos Korfiatis
144 0932ac43 Giorgos Korfiatis
class JoinLeaveT(threading.Thread):
145 0932ac43 Giorgos Korfiatis
    def __init__(self, *args, **kwargs):
146 0932ac43 Giorgos Korfiatis
        self.repeat = kwargs.pop('repeat', 1)
147 0932ac43 Giorgos Korfiatis
        threading.Thread.__init__(self, *args, **kwargs)
148 0932ac43 Giorgos Korfiatis
149 0932ac43 Giorgos Korfiatis
    def run(self):
150 0932ac43 Giorgos Korfiatis
        owner = choice(USERS.keys())
151 0932ac43 Giorgos Korfiatis
        while True:
152 0932ac43 Giorgos Korfiatis
            projects = PROJECTS.keys()
153 0932ac43 Giorgos Korfiatis
            if projects:
154 0932ac43 Giorgos Korfiatis
                pid = choice(projects)
155 0932ac43 Giorgos Korfiatis
                break
156 0932ac43 Giorgos Korfiatis
            sleep(0.1)
157 327eb666 Giorgos Korfiatis
        join_and_leave(pid, owner, self.repeat, prefix=self.name)
158 0932ac43 Giorgos Korfiatis
159 0932ac43 Giorgos Korfiatis
160 0932ac43 Giorgos Korfiatis
def join_and_leave(proj_id, user_id, repeat, prefix=""):
161 0932ac43 Giorgos Korfiatis
    if prefix:
162 0932ac43 Giorgos Korfiatis
        prefix += ' '
163 0932ac43 Giorgos Korfiatis
164 0932ac43 Giorgos Korfiatis
    for i in range(repeat):
165 0932ac43 Giorgos Korfiatis
        try:
166 0932ac43 Giorgos Korfiatis
            now = datetime.datetime.now()
167 327eb666 Giorgos Korfiatis
            logger.info('%s%s: user %s joining project %s'
168 327eb666 Giorgos Korfiatis
                        % (prefix, now, user_id, proj_id))
169 0932ac43 Giorgos Korfiatis
            join(proj_id, user_id)
170 770dba12 Giorgos Korfiatis
        except PermissionDenied as e:
171 770dba12 Giorgos Korfiatis
            logger.info('Membership already exists')
172 0932ac43 Giorgos Korfiatis
        except Exception as e:
173 327eb666 Giorgos Korfiatis
            logger.exception(e)
174 327eb666 Giorgos Korfiatis
175 0932ac43 Giorgos Korfiatis
        try:
176 0932ac43 Giorgos Korfiatis
            now = datetime.datetime.now()
177 327eb666 Giorgos Korfiatis
            logger.info('%s%s: user %s leaving project %s'
178 327eb666 Giorgos Korfiatis
                        % (prefix, now, user_id, proj_id))
179 0932ac43 Giorgos Korfiatis
            leave(proj_id, user_id)
180 770dba12 Giorgos Korfiatis
        except IOError as e:
181 770dba12 Giorgos Korfiatis
            logger.info('No such membership')
182 0932ac43 Giorgos Korfiatis
        except Exception as e:
183 327eb666 Giorgos Korfiatis
            logger.exception(e)
184 0932ac43 Giorgos Korfiatis
185 0932ac43 Giorgos Korfiatis
186 0932ac43 Giorgos Korfiatis
def test(users, projects, memb, repeat):
187 0932ac43 Giorgos Korfiatis
    logging.basicConfig()
188 0932ac43 Giorgos Korfiatis
189 0932ac43 Giorgos Korfiatis
    new_users(users)
190 0932ac43 Giorgos Korfiatis
191 0932ac43 Giorgos Korfiatis
    for i in range(projects):
192 0932ac43 Giorgos Korfiatis
        SubmitApproveT(repeat=repeat).start()
193 0932ac43 Giorgos Korfiatis
194 0932ac43 Giorgos Korfiatis
    for i in range(memb):
195 0932ac43 Giorgos Korfiatis
        JoinLeaveT(repeat=repeat).start()
196 0932ac43 Giorgos Korfiatis
197 327eb666 Giorgos Korfiatis
    for thread in threading.enumerate():
198 327eb666 Giorgos Korfiatis
        if thread is not threading.currentThread():
199 327eb666 Giorgos Korfiatis
            thread.join()
200 327eb666 Giorgos Korfiatis
201 0932ac43 Giorgos Korfiatis
202 0932ac43 Giorgos Korfiatis
def main():
203 0932ac43 Giorgos Korfiatis
    parser = OptionParser()
204 0932ac43 Giorgos Korfiatis
    parser.add_option('--users',
205 0932ac43 Giorgos Korfiatis
                      dest='users',
206 0932ac43 Giorgos Korfiatis
                      default=2,
207 0932ac43 Giorgos Korfiatis
                      help="Number of users (default=2)")
208 0932ac43 Giorgos Korfiatis
    parser.add_option('--projects',
209 0932ac43 Giorgos Korfiatis
                      dest='projects',
210 0932ac43 Giorgos Korfiatis
                      default=2,
211 0932ac43 Giorgos Korfiatis
                      help="Number of projects (default=2)")
212 0932ac43 Giorgos Korfiatis
    parser.add_option('--memb',
213 0932ac43 Giorgos Korfiatis
                      dest='memb',
214 0932ac43 Giorgos Korfiatis
                      default=2,
215 0932ac43 Giorgos Korfiatis
                      help="Number of membership requests (default=2)")
216 0932ac43 Giorgos Korfiatis
    parser.add_option('--repeat',
217 0932ac43 Giorgos Korfiatis
                      dest='repeat',
218 0932ac43 Giorgos Korfiatis
                      default=20,
219 0932ac43 Giorgos Korfiatis
                      help="Number of iterations (default=20)")
220 327eb666 Giorgos Korfiatis
    parser.add_option('-q', '--quiet',
221 327eb666 Giorgos Korfiatis
                      action='store_true',
222 327eb666 Giorgos Korfiatis
                      dest='quiet',
223 327eb666 Giorgos Korfiatis
                      default=False,
224 327eb666 Giorgos Korfiatis
                      help="Print only errors")
225 0932ac43 Giorgos Korfiatis
226 0932ac43 Giorgos Korfiatis
    (options, args) = parser.parse_args()
227 0932ac43 Giorgos Korfiatis
228 327eb666 Giorgos Korfiatis
    if options.quiet:
229 327eb666 Giorgos Korfiatis
        logger.setLevel(logging.WARNING)
230 327eb666 Giorgos Korfiatis
231 0932ac43 Giorgos Korfiatis
    users = int(options.users)
232 0932ac43 Giorgos Korfiatis
    projects = int(options.projects)
233 0932ac43 Giorgos Korfiatis
    memb = int(options.memb)
234 0932ac43 Giorgos Korfiatis
    repeat = int(options.repeat)
235 0932ac43 Giorgos Korfiatis
    test(users, projects, memb, repeat)
236 0932ac43 Giorgos Korfiatis
237 0932ac43 Giorgos Korfiatis
238 0932ac43 Giorgos Korfiatis
if __name__ == "__main__":
239 0932ac43 Giorgos Korfiatis
    main()