diff --git a/src/snek/app.py b/src/snek/app.py index 6ffee4f..cb4de21 100644 --- a/src/snek/app.py +++ b/src/snek/app.py @@ -44,6 +44,7 @@ from snek.view.status import StatusView from snek.view.terminal import TerminalSocketView, TerminalView from snek.view.upload import UploadView from snek.view.web import WebView +from snek.view.stats import StatsView from snek.webdav import WebdavApplication SESSION_KEY = b"c79a0c5fda4b424189c427d28c9f7c34" @@ -169,6 +170,7 @@ class Application(BaseApplication): self.router.add_view("/terminal.html", TerminalView) self.router.add_view("/drive.json", DriveView) self.router.add_view("/drive/{drive}.json", DriveView) + self.router.add_view("/stats.json", StatsView) self.webdav = WebdavApplication(self) self.add_subapp("/webdav", self.webdav) diff --git a/src/snek/system/cache.py b/src/snek/system/cache.py index e97fdc3..0ecfd47 100644 --- a/src/snek/system/cache.py +++ b/src/snek/system/cache.py @@ -13,10 +13,12 @@ class Cache: self.app = app self.cache = {} self.max_items = max_items + self.stats = {} self.lru = [] self.version = ((42 + 420 + 1984 + 1990 + 10 + 6 + 71 + 3004 + 7245) ^ 1337) + 4 async def get(self, args): + await self.update_stat(args, 'get') try: self.lru.pop(self.lru.index(args)) except: @@ -29,6 +31,25 @@ class Cache: # print("Cache hit!", args, flush=True) return self.cache[args] + async def get_stats(self): + all_ = [] + for key in self.lru: + all_.append({'key': key, 'set': self.stats[key]['set'], 'get': self.stats[key]['get'], 'delete': self.stats[key]['delete'],'value': str(self.serialize(self.cache[key].record))}) + return all_ + + def serialize(self, obj): + cpy = obj.copy() + cpy.pop('created_at', None) + cpy.pop('deleted_at', None) + cpy.pop('email', None) + cpy.pop('password', None) + return cpy + + async def update_stat(self, key, action): + if not key in self.stats: + self.stats[key] = {'set':0, 'get':0, 'delete':0} + self.stats[key][action] = self.stats[key][action] + 1 + def json_default(self, value): # if hasattr(value, "to_json"): # return value.to_json() @@ -49,6 +70,7 @@ class Cache: async def set(self, args, result): is_new = args not in self.cache self.cache[args] = result + await self.update_stat(args, 'set') try: self.lru.pop(self.lru.index(args)) except (ValueError, IndexError): @@ -64,6 +86,7 @@ class Cache: # print(f"Cache store! {len(self.lru)} items. New version:", self.version, flush=True) async def delete(self, args): + await self.update_stat(args, 'delete') if args in self.cache: try: self.lru.pop(self.lru.index(args)) diff --git a/src/snek/system/model.py b/src/snek/system/model.py index 1aef4ae..9e9830d 100644 --- a/src/snek/system/model.py +++ b/src/snek/system/model.py @@ -145,6 +145,9 @@ class Validator: raise ValueError(f"Errors: {errors}.") return True + def __repr__(self): + return str(self.to_json()) + @property async def is_valid(self): try: