2022-06-22 17:17:20 +00:00
|
|
|
import time
|
2022-07-24 20:02:25 +00:00
|
|
|
|
|
|
|
import aiohttp.web_request
|
|
|
|
|
2021-06-05 11:12:23 +00:00
|
|
|
from src.config import settings
|
|
|
|
from typing import Union, Optional
|
2022-06-22 17:17:20 +00:00
|
|
|
from enum import Enum
|
|
|
|
|
|
|
|
|
|
|
|
class LogType(Enum):
|
2022-10-29 15:04:25 +00:00
|
|
|
CONNECTION_ERROR = 1
|
|
|
|
HTTP_ERROR = 2
|
|
|
|
MEDIAWIKI_ERROR = 3
|
|
|
|
VALUE_UPDATE = 4
|
|
|
|
SCAN_REASON = 5
|
2021-06-05 11:12:23 +00:00
|
|
|
|
2022-11-10 14:16:35 +00:00
|
|
|
|
2021-06-05 11:12:23 +00:00
|
|
|
queue_limit = settings.get("queue_limit", 30)
|
|
|
|
|
2022-06-22 17:17:20 +00:00
|
|
|
|
2021-06-05 11:12:23 +00:00
|
|
|
class Log:
|
2022-06-22 17:17:20 +00:00
|
|
|
"""Log class represents an event that happened to a wiki fetch. Main purpose of those logs is debug and error-tracking."""
|
2021-06-05 11:12:23 +00:00
|
|
|
def __init__(self, **kwargs):
|
2022-06-22 17:17:20 +00:00
|
|
|
self.type: LogType = kwargs["type"]
|
|
|
|
self.time: int = int(time.time())
|
|
|
|
self.title: str = kwargs["title"]
|
|
|
|
self.details: Optional[str] = kwargs.get("details", None)
|
2021-06-05 11:12:23 +00:00
|
|
|
|
2022-11-07 14:46:15 +00:00
|
|
|
|
2021-06-05 11:12:23 +00:00
|
|
|
class LimitedList(list):
|
|
|
|
def __init__(self, *args):
|
|
|
|
list.__init__(self, *args)
|
|
|
|
|
|
|
|
def append(self, obj: Log) -> None:
|
|
|
|
if len(self) > queue_limit:
|
|
|
|
self.pop()
|
|
|
|
|
|
|
|
|
|
|
|
class Statistics:
|
2022-06-22 17:17:20 +00:00
|
|
|
def __init__(self, rc_id: Optional[int], discussion_id: Optional[int]):
|
2022-07-24 20:02:25 +00:00
|
|
|
self.last_request: Optional[aiohttp.web_request.Request] = None
|
2021-06-05 11:12:23 +00:00
|
|
|
self.last_checked_rc: Optional[int] = None
|
|
|
|
self.last_action: Optional[int] = rc_id
|
|
|
|
self.last_checked_discussion: Optional[int] = None
|
2022-11-10 14:16:35 +00:00
|
|
|
self.last_post: Optional[str] = discussion_id
|
2022-08-09 14:08:30 +00:00
|
|
|
self.logs: LimitedList[Log] = LimitedList()
|
2021-06-05 11:12:23 +00:00
|
|
|
|
|
|
|
def update(self, *args: Log, **kwargs: dict[str, Union[float, int]]):
|
2022-11-04 14:59:26 +00:00
|
|
|
for key, value in kwargs.items():
|
2021-06-05 11:12:23 +00:00
|
|
|
self.__setattr__(key, value)
|
|
|
|
for log in args:
|
2022-08-09 14:08:30 +00:00
|
|
|
self.logs.append(log)
|
|
|
|
|
|
|
|
def filter_by_time(self, time_ago: int, logs: list = None): # cannot have self.logs in here as this is evaluated once
|
|
|
|
"""Returns logs with time between time_ago seconds ago and now"""
|
|
|
|
time_limit = int(time.time()) - time_ago
|
|
|
|
return [x for x in (self.logs if logs is None else logs) if x.time > time_limit]
|
|
|
|
|
|
|
|
def filter_by_type(self, log_type: LogType, logs: list = None):
|
|
|
|
"""Returns logs with same type as in log_type"""
|
|
|
|
return [x for x in (self.logs if logs is None else logs) if x.type == log_type]
|
|
|
|
|
|
|
|
def recent_connection_errors(self) -> int:
|
|
|
|
"""Count how many connection errors there were recently (2 minutes)"""
|
|
|
|
return len(self.filter_by_type(LogType.CONNECTION_ERROR, logs=self.filter_by_time(120))) # find connection errors from 2 minutes ago
|