-
Notifications
You must be signed in to change notification settings - Fork 20
Coding standards
Coding standards should mostly be enforced by mypy and ruff but some things are worth mentioning:
Prefix private/protected members with _.
...
Do not re-export symbols from __init__.py files. Always import from the module that defines the symbol.
The reason is because Python executes every __init__.py on the import path.
Re-exports create hidden, eager imports and cause unrelated dependencies to load.
Bad example:
# dimos/models/__init__.py
from dimos.models.base import HuggingFaceModel, LocalModel
__all__ = ["HuggingFaceModel", "LocalModel"]This makes any import under dimos.models.* load Hugging Face and Torch.
It's not good to have classes which are too heavy. Some classes are just for storing data, but they have a lot of functionality as methods to the class. This means that even places which just need the data have to import all the dependencies for all the functionality of the classes.
Bad example:
class CarImage
data: bytes
@classmethod
def from_tensor(cls, tensor: torch.Tensor):
return cls()
def get_predominant_color(self):
# analizes the image to get the predominant colorThis makes it easy to use (CarImage.from_tensor(...).get_predominant_color()), but:
-
forces all imports together (even if you just care about the bytes, you have to import torch)
-
joins unrelated things together in the same class just because they act on
CarImage -
doesn't easily allow for multiple strategies (i.e. there are multiple ways of getting the predominant color in an image, but
CarImage.get_predominant_colormakes it seem like there's only one) -
anything that inherits from CarImage is forced to take those methods whether they are needed or not.
The alternative is to just break up the class:
# car_image/image.py
class CarImage
data: bytes
# car_image/factories.py
def tensor_to_car_image(tensor: torch.Tensor) -> CarImage:
...
# car_image/color_utilities.py
def predominant_color_by_strategy_1(car_image: CarImage) -> ...
def predominant_color_by_strategy_2(car_image: CarImage) -> ...Only use except Exception if you truly expect anything to fail. LLMs tend to generate code which handles all possible errors, even when it's better to just fail on unknown issues rather than pass and continue processing even when the system is in an inconsistent state.
When a try-except wraps a long sequence of code it's unclear what part of it is expected to fail. It's better to wrap the specific part that triggers the exception.