stash data_structures.py

pull/33208/head
Shane Smiskol 11 months ago
parent 965f692f2e
commit bc242022d0
  1. 183
      selfdrive/car/data_structures.py

@ -1,7 +1,8 @@
from dataclasses import dataclass, fields, is_dataclass
from dataclasses import dataclass, fields, field, is_dataclass
from enum import Enum, StrEnum as _StrEnum, auto
# from typing import Type, TypeVar
from typing import Type, TypeVar, TYPE_CHECKING, Any, get_type_hints, get_origin
from typing import TypeVar, TYPE_CHECKING, Any, get_type_hints, get_origin
from selfdrive.car.data_test_kinda_works_chatgpt import auto_field, apply_auto_fields
if TYPE_CHECKING:
from _typeshed import DataclassInstance
@ -10,6 +11,8 @@ if TYPE_CHECKING:
#
# T = TypeVar('T', bound='Struct')
_FIELDS = '__dataclass_fields__'
class StrEnum(_StrEnum):
@staticmethod
@ -30,35 +33,35 @@ class StrEnum(_StrEnum):
T = TypeVar('T', bound='DataclassInstance')
class Struct:
@classmethod
def new_message(cls: Type[T], **kwargs: Any) -> T:
if not is_dataclass(cls):
raise TypeError(f"{cls.__name__} is not a dataclass")
init_values = {}
type_hints = get_type_hints(cls)
print(type_hints)
for f in fields(cls):
field_type = type_hints[f.name]
print(f.name, f.type, field_type)
print(issubclass(field_type, Enum))
if issubclass(field_type, Enum):
init_values[f.name] = kwargs.get(f.name, list(field_type)[0])
# TODO: fix this
# assert issubclass(init_values[f.name], type(field_type)), f"Expected {field_type} for {f.name}, got {type(init_values[f.name])}"
else:
# FIXME: typing check hack since mypy doesn't catch anything
init_values[f.name] = kwargs.get(f.name, field_type())
print('field_type', field_type, f.type)
# TODO: this is so bad
assert isinstance(init_values[f.name], get_origin(f.type) or f.type), f"Expected {field_type} for {f.name}, got {type(init_values[f.name])}"
return cls(**init_values)
# class Struct:
# @classmethod
# def new_message(cls: type[T], **kwargs: Any) -> T:
# if not is_dataclass(cls):
# raise TypeError(f"{cls.__name__} is not a dataclass")
#
# init_values = {}
# type_hints = get_type_hints(cls)
# print(type_hints)
# for f in fields(cls):
# field_type = type_hints[f.name]
# print(f.name, f.type, field_type)
# print(issubclass(field_type, Enum))
# if issubclass(field_type, Enum):
# init_values[f.name] = kwargs.get(f.name, list(field_type)[0])
# # TODO: fix this
# # assert issubclass(init_values[f.name], type(field_type)), f"Expected {field_type} for {f.name}, got {type(init_values[f.name])}"
# else:
# # FIXME: typing check hack since mypy doesn't catch anything
# init_values[f.name] = kwargs.get(f.name, field_type())
# print('field_type', field_type, f.type)
# # TODO: this is so bad
# assert isinstance(init_values[f.name], get_origin(f.type) or f.type), f"Expected {field_type} for {f.name}, got {type(init_values[f.name])}"
#
# return cls(**init_values)
@dataclass
class RadarData(Struct):
class RadarData:
errors: list['Error']
points: list['RadarPoint']
@ -68,7 +71,7 @@ class RadarData(Struct):
wrongConfig = auto()
@dataclass
class RadarPoint(Struct):
class RadarPoint:
trackId: int # no trackId reuse
# these 3 are the minimum required
@ -85,31 +88,33 @@ class RadarData(Struct):
@dataclass
class CarParams(Struct):
carName: str
carFingerprint: str
fuzzyFingerprint: bool
@apply_auto_fields
class CarParams:
carName: str = auto_field()
carFingerprint: str = auto_field()
fuzzyFingerprint: bool = auto_field()
notCar: bool # flag for non-car robotics platforms
notCar: bool = auto_field() # flag for non-car robotics platforms
carFw: list['CarFw']
carFw: list['CarParams.CarFw'] = auto_field()
class SteerControlType(StrEnum):
torque = auto()
angle = auto()
@dataclass
class CarFw(Struct):
ecu: 'CarParams.Ecu'
fwVersion: bytes
address: int
subAddress: int
responseAddress: int
request: list[bytes]
brand: str
bus: int
logging: bool
obdMultiplexing: bool
@apply_auto_fields
class CarFw:
ecu: 'CarParams.Ecu' = field(default_factory=lambda: CarParams.Ecu.unknown)
fwVersion: bytes = auto_field()
address: int = auto_field()
subAddress: int = auto_field()
responseAddress: int = auto_field()
request: list[bytes] = auto_field()
brand: str = auto_field()
bus: int = auto_field()
logging: bool = auto_field()
obdMultiplexing: bool = auto_field()
class Ecu(StrEnum):
eps = auto()
@ -144,10 +149,88 @@ class CarParams(Struct):
debug = auto()
# CP: CarParams = CarParams.new_message(carName='toyota', fuzzyFingerprint=123)
# CP: CarParams = CarParams(carName='toyota', fuzzyFingerprint=123)
# # CP: CarParams = CarParams.new_message(carName='toyota', fuzzyFingerprint=123)
# # CP: CarParams = CarParams(carName='toyota', fuzzyFingerprint=123)
#
# # import ast
#
#
# # test = ast.literal_eval('CarParams.CarFw')
#
# def mywrapper(cls):
#
# cls_annotations = cls.__dict__.get('__annotations__', {})
# fields = {}
# for name, _type in cls_annotations.items():
# f = field(default_factory=_type)
# setattr(cls, name, f)
# fields[name] = f
#
# setattr(cls, _FIELDS, fields)
#
# print('cls_annotations', cls_annotations)
# # cls.hi = 123
#
# return cls
#
#
# # def mywrapper2(cls):
# # class Test:
# # pass
# # return Test
#
#
# @dataclass
# class CarControl1:
# enabled: bool
#
# @dataclass
# class CarControl2:
# enabled: bool = field(default_factory=bool)
#
#
# # @mywrapper2
# @dataclass()
# @mywrapper
# class CarControl:
# # enabled: bool = field(default_factory=bool)
# enabled: bool = None
# pts: list[int] = None
# logMonoTime: int = None
#
#
# CC = CarControl()
import ast
@dataclass
@apply_auto_fields
class CarControl:
enabled: bool = auto_field()
pts: list[int] = auto_field()
logMonoTime: int = auto_field()
test: None = auto_field()
# test = ast.literal_eval('CarParams.CarFw')
# testing: if origin_typ in (int, float, str, bytes, list, tuple, set, dict, bool):
@dataclass
@apply_auto_fields
class Test997:
a: int = auto_field()
b: float = auto_field()
c: str = auto_field()
d: bytes = auto_field()
e: list[int] = auto_field()
f: tuple[int] = auto_field()
g: set[int] = auto_field()
h: dict[str, int] = auto_field()
i: bool = auto_field()
ecu: CarParams.Ecu = auto_field()
carFw: CarParams.CarFw = auto_field()
# Out[4]: Test997(a=0, b=0.0, c='', d=b'', e=[], f=(), g=set(), h={}, i=False)
CarControl()
CP = CarParams()
CP.carFw = [CarParams.CarFw()]
CP.carFw = [CarParams.Ecu.eps]

Loading…
Cancel
Save