13
13
14
14
import pytest
15
15
import requests
16
+ import py
16
17
17
18
from . import Account , const , account_hookimpl , get_core_info
18
19
from .events import FFIEventLogger , FFIEventTracker
@@ -178,6 +179,50 @@ def get_liveconfig_producer(self):
178
179
yield config
179
180
pytest .fail ("more than {} live accounts requested." .format (MAX_LIVE_CREATED_ACCOUNTS ))
180
181
182
+ def cache_maybe_retrieve_configured_db_files (self , cache_addr , db_target_path ):
183
+ db_target_path = py .path .local (db_target_path )
184
+ assert not db_target_path .exists ()
185
+
186
+ print ("checking cache for" , cache_addr )
187
+ try :
188
+ filescache = self ._addr2files [cache_addr ]
189
+ except KeyError :
190
+ print ("CACHE FAIL for" , cache_addr )
191
+ return False
192
+ else :
193
+ print ("CACHE HIT for" , cache_addr )
194
+ targetdir = db_target_path .dirpath ()
195
+ write_dict_to_dir (filescache , targetdir )
196
+ return True
197
+
198
+ def cache_maybe_store_configured_db_files (self , acc ):
199
+ addr = acc .get_config ("addr" )
200
+ assert acc .is_configured ()
201
+ # don't overwrite existing entries
202
+ if addr not in self ._addr2files :
203
+ print ("storing cache for" , addr )
204
+ basedir = py .path .local (acc .get_blobdir ()).dirpath ()
205
+ self ._addr2files [addr ] = create_dict_from_files_in_path (basedir )
206
+ return True
207
+
208
+
209
+ def create_dict_from_files_in_path (path ):
210
+ base = py .path .local (path )
211
+ cachedict = {}
212
+ for path in base .visit (fil = py .path .local .isfile ):
213
+ cachedict [path .relto (base )] = path .read_binary ()
214
+ return cachedict
215
+
216
+
217
+ def write_dict_to_dir (dic , target_dir ):
218
+ assert dic
219
+ target_dir = py .path .local (target_dir )
220
+ for relpath , content in dic .items ():
221
+ path = target_dir .join (relpath )
222
+ if not path .dirpath ().exists ():
223
+ path .dirpath ().ensure (dir = 1 )
224
+ path .write_binary (content )
225
+
181
226
182
227
@pytest .fixture
183
228
def data (request ):
@@ -225,6 +270,16 @@ def __init__(self, testprocess, init_time):
225
270
self .testprocess = testprocess
226
271
self .init_time = init_time
227
272
273
+ def log (self , * args ):
274
+ print ("[acsetup]" , "{:.3f}" .format (time .time () - self .init_time ), * args )
275
+
276
+ def add_configured (self , account ):
277
+ """ add an already configured account. """
278
+ assert account .is_configured ()
279
+ self ._account2state [account ] = self .CONFIGURED
280
+ self .log ("added already configured account" , account , account .get_config ("addr" ))
281
+ return
282
+
228
283
def start_configure (self , account , reconfigure = False ):
229
284
""" add an account and start its configure process. """
230
285
class PendingTracker :
@@ -235,7 +290,7 @@ def ac_configure_completed(this, success):
235
290
account .add_account_plugin (PendingTracker (), name = "pending_tracker" )
236
291
self ._account2state [account ] = self .CONFIGURING
237
292
account .configure (reconfigure = reconfigure )
238
- print ("started configure on pending " , account )
293
+ self . log ("started configure on" , account )
239
294
240
295
def wait_one_configured (self , account ):
241
296
""" wait until this account has successfully configured. """
@@ -328,6 +383,9 @@ def __init__(self, request, testprocess, tmpdir, data) -> None:
328
383
self .set_logging_default (False )
329
384
request .addfinalizer (self .finalize )
330
385
386
+ def log (self , * args ):
387
+ print ("[acfactory]" , "{:.3f}" .format (time .time () - self .init_time ), * args )
388
+
331
389
def finalize (self ):
332
390
while self ._finalizers :
333
391
fin = self ._finalizers .pop ()
@@ -359,9 +417,19 @@ def get_next_liveconfig(self):
359
417
assert "addr" in configdict and "mail_pw" in configdict
360
418
return configdict
361
419
420
+ def _get_cached_account (self , addr ):
421
+ if addr in self .testprocess ._addr2files :
422
+ return self ._getaccount (addr )
423
+
362
424
def get_unconfigured_account (self ):
425
+ return self ._getaccount ()
426
+
427
+ def _getaccount (self , try_cache_addr = None ):
363
428
logid = "ac{}" .format (len (self ._accounts ) + 1 )
364
- path = self .tmpdir .join (logid )
429
+ # we need to use fixed database basename for maybe_cache_* functions to work
430
+ path = self .tmpdir .mkdir (logid ).join ("dc.db" )
431
+ if try_cache_addr :
432
+ self .testprocess .cache_maybe_retrieve_configured_db_files (try_cache_addr , path )
365
433
ac = Account (path .strpath , logging = self ._logging )
366
434
ac ._logid = logid # later instantiated FFIEventLogger needs this
367
435
ac ._evtracker = ac .add_account_plugin (FFIEventTracker (ac ))
@@ -394,7 +462,7 @@ def _preconfigure_key(self, account, addr):
394
462
def get_pseudo_configured_account (self ):
395
463
# do a pseudo-configured account
396
464
ac = self .get_unconfigured_account ()
397
- acname = os . path . basename ( ac .db_path )
465
+ acname = ac ._logid
398
466
addr = "{}@offline.org" .format (acname )
399
467
ac .update_config (dict (
400
468
addr = addr , displayname = acname , mail_pw = "123" ,
@@ -405,7 +473,7 @@ def get_pseudo_configured_account(self):
405
473
self ._acsetup .init_logging (ac )
406
474
return ac
407
475
408
- def new_online_configuring_account (self , cloned_from = None , ** kwargs ):
476
+ def new_online_configuring_account (self , cloned_from = None , cache = False , ** kwargs ):
409
477
if cloned_from is None :
410
478
configdict = self .get_next_liveconfig ()
411
479
else :
@@ -415,6 +483,12 @@ def new_online_configuring_account(self, cloned_from=None, **kwargs):
415
483
mail_pw = cloned_from .get_config ("mail_pw" ),
416
484
)
417
485
configdict .update (kwargs )
486
+ ac = self ._get_cached_account (addr = configdict ["addr" ]) if cache else None
487
+ if ac is not None :
488
+ # make sure we consume a preconfig key, as if we had created a fresh account
489
+ self ._preconfigured_keys .pop (0 )
490
+ self ._acsetup .add_configured (ac )
491
+ return ac
418
492
ac = self .prepare_account_from_liveconfig (configdict )
419
493
self ._acsetup .start_configure (ac )
420
494
return ac
@@ -439,9 +513,11 @@ def bring_accounts_online(self):
439
513
print ("all accounts online" )
440
514
441
515
def get_online_accounts (self , num ):
442
- # to reduce number of log events logging starts after accounts can receive
443
- accounts = [self .new_online_configuring_account () for i in range (num )]
516
+ accounts = [self .new_online_configuring_account (cache = True ) for i in range (num )]
444
517
self .bring_accounts_online ()
518
+ # we cache fully configured and started accounts
519
+ for acc in accounts :
520
+ self .testprocess .cache_maybe_store_configured_db_files (acc )
445
521
return accounts
446
522
447
523
def run_bot_process (self , module , ffi = True ):
0 commit comments