nanovna-saver/src/NanoVNASaver/Version.py

89 wiersze
2.7 KiB
Python
Czysty Zwykły widok Historia

2020-06-09 17:14:01 +00:00
# NanoVNASaver
# A python program to view and export Touchstone data from a NanoVNA
2020-06-25 17:52:30 +00:00
# Copyright (C) 2019, 2020 Rune B. Broberg
2021-06-30 05:21:14 +00:00
# Copyright (C) 2020,2021 NanoVNA-Saver Authors
2020-06-09 17:14:01 +00:00
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <https://www.gnu.org/licenses/>.
import logging
import re
2020-06-09 17:14:01 +00:00
logger = logging.getLogger(__name__)
class Version:
2020-07-04 12:26:20 +00:00
RXP = re.compile(r"""^
\D*
(?P<major>\d+)\.
(?P<minor>\d+)\.?
(?P<revision>\d+)?
2020-07-04 12:26:20 +00:00
(?P<note>.*)
$""", re.VERBOSE)
def __init__(self, vstring: str = "0.0.0"):
self.data = {
"major": 0,
"minor": 0,
"revision": 0,
"note": "",
}
try:
self.data = Version.RXP.search(vstring).groupdict()
for name in ("major", "minor", "revision"):
self.data[name] = int(self.data[name])
except TypeError:
self.data["revision"] = 0
2020-07-04 12:26:20 +00:00
except AttributeError:
logger.error("Unable to parse version: %s", vstring)
def __gt__(self, other: "Version") -> bool:
left, right = self.data, other.data
2020-07-04 12:26:20 +00:00
for name in ("major", "minor", "revision"):
if left[name] > right[name]:
2020-07-04 12:26:20 +00:00
return True
if left[name] < right[name]:
2020-07-04 12:26:20 +00:00
return False
return False
def __lt__(self, other: "Version") -> bool:
Version: avoid infinite recursion The comparison operators (<, >, etc.) are not translated 1:1 to customisation methods (__lt__, __gt__, ...) in Python. Instead the type of the operands plays a role in determining on which of the two sides the customisation method is invoked (see Python Language Reference section 3.3.1 [1]). This means 'a > b' can end up invoking b.__lt__(a) rather than a.__gt__(b). This behaviour can causes infinite recursion in Version.__lt__(): 2022-03-07 13:47:52,087 - NanoVNASaver.Hardware.NanoVNA_V2 - ERROR - Timeout reading version registers Traceback (most recent call last): File "/home/sascha/nanovna-saver/NanoVNASaver/Controls/SerialControl.py", line 73, in serialButtonClick self.connect_device() File "/home/sascha/nanovna-saver/NanoVNASaver/Controls/SerialControl.py", line 93, in connect_device self.app.vna = get_VNA(self.interface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/Hardware.py", line 101, in get_VNA return NAME2DEVICE[iface.comment](iface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/NanoVNA_V2.py", line 76, in __init__ super().__init__(iface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/VNA.py", line 71, in __init__ self.read_features() File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/NanoVNA_V2.py", line 107, in read_features if self.board_revision >= Version("2.0.4"): File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 63, in __le__ return self < other or self == other File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self [Previous line repeated 491 more times] RecursionError: maximum recursion depth exceeded in comparison Fix it by explicitly invoking the customisation methods we expect. [1] https://docs.python.org/3/reference/datamodel.html#object.__lt__
2022-03-07 13:51:51 +00:00
return other.__gt__(self)
def __ge__(self, other: "Version") -> bool:
Version: avoid infinite recursion The comparison operators (<, >, etc.) are not translated 1:1 to customisation methods (__lt__, __gt__, ...) in Python. Instead the type of the operands plays a role in determining on which of the two sides the customisation method is invoked (see Python Language Reference section 3.3.1 [1]). This means 'a > b' can end up invoking b.__lt__(a) rather than a.__gt__(b). This behaviour can causes infinite recursion in Version.__lt__(): 2022-03-07 13:47:52,087 - NanoVNASaver.Hardware.NanoVNA_V2 - ERROR - Timeout reading version registers Traceback (most recent call last): File "/home/sascha/nanovna-saver/NanoVNASaver/Controls/SerialControl.py", line 73, in serialButtonClick self.connect_device() File "/home/sascha/nanovna-saver/NanoVNASaver/Controls/SerialControl.py", line 93, in connect_device self.app.vna = get_VNA(self.interface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/Hardware.py", line 101, in get_VNA return NAME2DEVICE[iface.comment](iface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/NanoVNA_V2.py", line 76, in __init__ super().__init__(iface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/VNA.py", line 71, in __init__ self.read_features() File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/NanoVNA_V2.py", line 107, in read_features if self.board_revision >= Version("2.0.4"): File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 63, in __le__ return self < other or self == other File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self [Previous line repeated 491 more times] RecursionError: maximum recursion depth exceeded in comparison Fix it by explicitly invoking the customisation methods we expect. [1] https://docs.python.org/3/reference/datamodel.html#object.__lt__
2022-03-07 13:51:51 +00:00
return self.__gt__(other) or self.__eq__(other)
def __le__(self, other: "Version") -> bool:
Version: avoid infinite recursion The comparison operators (<, >, etc.) are not translated 1:1 to customisation methods (__lt__, __gt__, ...) in Python. Instead the type of the operands plays a role in determining on which of the two sides the customisation method is invoked (see Python Language Reference section 3.3.1 [1]). This means 'a > b' can end up invoking b.__lt__(a) rather than a.__gt__(b). This behaviour can causes infinite recursion in Version.__lt__(): 2022-03-07 13:47:52,087 - NanoVNASaver.Hardware.NanoVNA_V2 - ERROR - Timeout reading version registers Traceback (most recent call last): File "/home/sascha/nanovna-saver/NanoVNASaver/Controls/SerialControl.py", line 73, in serialButtonClick self.connect_device() File "/home/sascha/nanovna-saver/NanoVNASaver/Controls/SerialControl.py", line 93, in connect_device self.app.vna = get_VNA(self.interface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/Hardware.py", line 101, in get_VNA return NAME2DEVICE[iface.comment](iface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/NanoVNA_V2.py", line 76, in __init__ super().__init__(iface) File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/VNA.py", line 71, in __init__ self.read_features() File "/home/sascha/nanovna-saver/NanoVNASaver/Hardware/NanoVNA_V2.py", line 107, in read_features if self.board_revision >= Version("2.0.4"): File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 63, in __le__ return self < other or self == other File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self File "/home/sascha/nanovna-saver/NanoVNASaver/Version.py", line 57, in __lt__ return other > self [Previous line repeated 491 more times] RecursionError: maximum recursion depth exceeded in comparison Fix it by explicitly invoking the customisation methods we expect. [1] https://docs.python.org/3/reference/datamodel.html#object.__lt__
2022-03-07 13:51:51 +00:00
return other.__gt__(self) or self.__eq__(other)
def __eq__(self, other: "Version") -> bool:
2020-07-04 12:26:20 +00:00
return self.data == other.data
def __str__(self) -> str:
2020-07-04 12:26:20 +00:00
return (f'{self.data["major"]}.{self.data["minor"]}'
f'.{self.data["revision"]}{self.data["note"]}')
2020-07-08 15:14:16 +00:00
@property
def major(self) -> int:
return self.data["major"]
@property
def minor(self) -> int:
return self.data["minor"]
@property
def revision(self) -> int:
return self.data["revision"]
@property
def note(self) -> str:
return self.data["note"]