Skip to content
This repository was archived by the owner on Mar 31, 2020. It is now read-only.

Commit abfe82b

Browse files
committed
Cache keeps a cache of its cache to cache for later caching
1 parent e1c4548 commit abfe82b

2 files changed

Lines changed: 38 additions & 50 deletions

File tree

src/cache.py

Lines changed: 27 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -2,26 +2,29 @@
22
import requests
33
import time
44
import multiprocessing as mp
5+
6+
from typing import List, Text
57
from random import randint, choice, sample
68

79
from . import API
810

911

1012
class ImageCache:
11-
'''Class used for caching images'''
13+
"""Class used for caching images"""
1214

1315
ratelimit = 0.05
1416
with API.open() as fp:
1517
api = json.load(fp)
1618

19+
api_cache = {
20+
'info': None,
21+
'hobbies': None
22+
}
23+
1724
def __init__(self, size):
18-
self.manager = mp.Manager()
19-
self.queue = self.manager.Queue(size)
25+
self.queue = mp.Queue(size)
2026
self.worker = None
2127

22-
self.infocache = None
23-
self.hobbycache = None
24-
2528
def __del__(self):
2629
self.stop()
2730

@@ -31,60 +34,54 @@ def __get(self, url, **kwargs):
3134
except ConnectionError as e:
3235
return e
3336

34-
def __parse_image(self, data: dict):
35-
data = response.json()
37+
def __parse_image(self, data: List[dict]) -> dict:
3638
url = data[0]['url']
3739
response = self.__get(url)
3840
return {'image': response.content}
3941

40-
def __parse_hobbies(self, response):
41-
all_hobbies = response.text.split("\n")
42-
return {'hobbies': sample(all_hobbies, 5)}
42+
def __parse_hobbies(self, data: Text):
43+
return {'hobbies': sample(data, 5)}
4344

44-
def __parse_info(self, response):
45-
data = response.json()
45+
def __parse_info(self, data: dict):
4646
letter = choice('acdefghijklmnopqrstuvwxyz')
4747
data = choice(data[letter])
4848
return {
49+
'name': data['name'],
4950
'info': {
50-
'name': data['name'],
5151
'gender': data['gender'],
5252
'age': randint(1, 42),
5353
'location': f'{randint(1, 9999)} miles away'
5454
}
5555
}
5656

5757
def get_profile(self):
58-
api = [self.api['image']]
59-
if self.infocache is None:
60-
api.append(self.api['info'])
61-
if self.
62-
63-
with mp.Pool(poolsize) as pool:
64-
response = pool.map(self.__get, self.api.values())
65-
if ConnectionError not in responses: # TODO Record connection errors
58+
response = {k: self.__get(v) for k, v in self.api.items() if self.api_cache.get(k) is None}
59+
if ConnectionError not in response: # TODO Record connection errors
60+
if 'info' in response:
61+
self.api_cache['info'] = response['info'].json()
62+
if 'hobbies' in response:
63+
self.api_cache['hobbies'] = response['hobbies'].text.split('\n')
6664
return {
67-
**self.__parse_info(response['info']),
68-
**self.__parse_image(response['image']),
69-
**self.__parse_hobbies(response['hobbies'])
65+
**self.__parse_info(self.api_cache['info']),
66+
**self.__parse_hobbies(self.api_cache['hobbies']),
67+
**self.__parse_image(response['image'].json())
7068
}
7169

72-
def next(self):
73-
return self.queue.get()
74-
7570
def mainloop(self, queue):
7671
while True:
7772
profile = self.get_profile()
7873
if profile is not None:
7974
queue.put(profile)
8075
time.sleep(self.ratelimit)
8176

77+
def next(self):
78+
return self.queue.get()
79+
8280
def start(self):
8381
if self.worker is not None and self.worker.is_alive():
8482
self.stop()
8583
self.worker = mp.Process(target=self.mainloop, args=(self.queue,))
8684
self.worker.start()
8785

8886
def stop(self):
89-
for worker in mp.active_children():
90-
worker.terminate()
87+
self.worker.terminate()

src/front.py

Lines changed: 11 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ class Front(widget.PrimaryFrame):
2222
# doesn't delete it before the animation ends
2323
_last = None
2424

25-
def __next(self):
25+
def __next(self, direction: Direction = None):
2626
data: dict = self.cache.next()
2727
image = process_image(
2828
data.pop('image'),
@@ -31,6 +31,10 @@ def __next(self):
3131
)
3232
name = data.pop('name')
3333
self.__load(name, image, data)
34+
if direction is None:
35+
self.window.set_view(self.image)
36+
else:
37+
self.window.change_view(self.image, direction)
3438

3539
def __load(self, name, image, data):
3640
self.title.config(text=name)
@@ -41,10 +45,6 @@ def __load(self, name, image, data):
4145
self.bio.data.load(data)
4246
self.update()
4347

44-
def __change_image(self, direction: Direction):
45-
self.__next()
46-
self.window.change_view(self.image, direction)
47-
4848
def init(self):
4949
self.title = widget.PrimaryLabel(self)
5050
self.window = Window(self)
@@ -71,33 +71,24 @@ def init(self):
7171
self.btn_like.pack(side='left')
7272

7373
self.cache = ImageCache(self.cachesize)
74+
self.cache.start()
75+
# Prime the pump
76+
self.after_idle(self.__next)
7477

7578
def cmd_dislike(self):
76-
self.__change_image('left')
79+
self.__next('left')
7780

7881
def cmd_like(self):
79-
self.__change_image('right')
82+
self.__next('right')
8083

8184
def cmd_bio(self):
8285
if self.window.current != self.bio:
8386
self.window.change_view(self.bio, 'up')
8487
else:
8588
self.window.change_view(self.image, 'down')
8689

87-
@property
88-
def cache(self):
89-
return self._cache
90-
91-
@cache.setter
92-
def cache(self, imagecache: ImageCache):
93-
self._cache = imagecache
94-
self._cache.start()
95-
# Prime the pump
96-
self.__next()
97-
self.window.set_view(self.image)
98-
9990
def cleanup(self):
100-
self._cache.stop()
91+
self.cache.stop()
10192

10293

10394
class Bio(widget.PrimaryFrame):

0 commit comments

Comments
 (0)