1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
|
# Copyright (c) 2016 Egor Tensin <egor@tensin.name>
# This file is part of the "VK scripts" project.
# For details, see https://github.com/egor-tensin/vk-scripts
# Distributed under the MIT License.
from collections import OrderedDict
from collections.abc import MutableMapping
from datetime import datetime, timezone
from enum import auto, StrEnum
from numbers import Integral, Real
from .platform import Platform
def _parse_time(x):
if isinstance(x, datetime):
if x.tzinfo is None or x.tzinfo.utcoffset(x) is None:
x = x.replace(tzinfo=timezone.utc)
return x
if isinstance(x, (Integral, Real)):
return datetime.fromtimestamp(x, tz=timezone.utc)
raise TypeError()
def _parse_platform(x):
if isinstance(x, Platform):
return x
if isinstance(x, str):
return Platform.from_string(x)
return Platform(x)
class LastSeenField(StrEnum):
TIME = auto()
PLATFORM = auto()
class LastSeen(MutableMapping):
@staticmethod
def from_api_response(source):
instance = LastSeen()
for field in LastSeenField:
if str(field) in source:
instance[field] = source[str(field)]
return instance
def __init__(self, fields=None):
if fields is None:
fields = OrderedDict()
self._fields = fields
def __getitem__(self, field):
return self._fields[field]
def __setitem__(self, field, value):
self._fields[field] = self.parse(field, value)
def __delitem__(self, field):
del self._fields[field]
def __iter__(self):
return iter(self._fields)
def __len__(self):
return len(self._fields)
@staticmethod
def parse(field, value):
if field in LastSeen._FIELD_PARSERS:
return LastSeen._FIELD_PARSERS[field](value)
return LastSeen._DEFAULT_FIELD_PARSER(value)
_FIELD_PARSERS = {
LastSeenField.TIME: _parse_time,
LastSeenField.PLATFORM: _parse_platform,
}
_DEFAULT_FIELD_PARSER = str
@property
def time(self):
return self[LastSeenField.TIME]
@property
def time_local(self):
return self.time.astimezone()
@property
def platform(self):
return self[LastSeenField.PLATFORM]
|