expli
Explicit dataclasses with automatic serialization
expli (short for "explicit") enhances Python dataclasses with automatic dictionary and JSON serialization methods, making it effortless to work with nested dataclasses, optional types, and lists.
Installation
pip install expli
Quick Start
from expli import edataclass
@edataclass
class Person:
name: str
age: int
email: str | None = None
# Automatic methods are added!
person = Person("Alice", 30, "alice@example.com")
# Convert to dict
data = person.to_dict()
# Convert to JSON
json_str = person.to_json(indent=2)
# Create from dict
person2 = Person.from_dict(data)
# Create from JSON
person3 = Person.from_json(json_str)
# Create a copy/clone
person4 = person.copy()
person5 = person.clone() # Same as copy()
Features
🎯 Enhanced Dataclass Decorator
The @edataclass decorator automatically adds six methods to your dataclass:
to_dict()- Convert instance to dictionaryfrom_dict(data)- Create instance from dictionary (class method)to_json(indent=None)- Convert instance to JSON stringfrom_json(json_str)- Create instance from JSON string (class method)copy()- Create a copy of the instanceclone()- Create a clone of the instance (alias forcopy())
🔄 Full Recursive Support
expli handles complex nested structures automatically:
from expli import edataclass
@edataclass
class Address:
street: str
city: str
country: str
@edataclass
class Company:
name: str
address: Address
@edataclass
class Person:
name: str
age: int
company: Company | None
hobbies: list[str]
person = Person(
name="Alice",
age=30,
company=Company(
name="Tech Corp",
address=Address("123 Main St", "Boston", "USA")
),
hobbies=["reading", "coding"]
)
# Everything serializes recursively
data = person.to_dict()
# {
# "name": "Alice",
# "age": 30,
# "company": {
# "name": "Tech Corp",
# "address": {
# "street": "123 Main St",
# "city": "Boston",
# "country": "USA"
# }
# },
# "hobbies": ["reading", "coding"]
# }
# And deserializes back perfectly
person2 = Person.from_dict(data)
# Create a copy with all nested objects copied
person_copy = person.copy()
🔄 Copying and Cloning
Create independent copies of your dataclass instances:
from expli import edataclass
@edataclass
class Person:
name: str
age: int
hobbies: list[str]
person = Person("Alice", 30, ["reading", "coding"])
# Create a copy
person_copy = person.copy()
# or use clone() - they're the same
person_clone = person.clone()
# The copy is independent
person_copy.hobbies.append("gaming")
print(person.hobbies) # ["reading", "coding"]
print(person_copy.hobbies) # ["reading", "coding", "gaming"]
✨ Supported Types
- Primitive types:
str,int,float,bool, etc. - Optional types:
Type | None - Lists:
list[Type] - Nested dataclasses: Any dataclass as a field
- Lists of dataclasses:
list[DataclassType] - Optional lists:
list[Type] | None
🛠️ Dataclass Parameters
@edataclass supports all standard dataclass parameters:
from expli import edataclass
@edataclass(frozen=True, order=True)
class Config:
api_key: str
timeout: int = 30
API Reference
@edataclass
Enhanced dataclass decorator that adds serialization methods.
Parameters: Same as @dataclass (frozen, order, etc.)
Added Methods:
to_dict(self) -> dict- Convert instance to dictionaryfrom_dict(cls, data: dict) -> Self- Create instance from dictionaryto_json(self, indent=None) -> str- Convert instance to JSON stringfrom_json(cls, json_str: str) -> Self- Create instance from JSON stringcopy(self) -> Self- Create a copy of the instanceclone(self) -> Self- Create a clone of the instance (alias forcopy())
to_dict(obj) / easdict(obj)
Standalone function to convert a dataclass instance to a dictionary.
from expli import to_dict, easdict
from dataclasses import dataclass
@dataclass
class Point:
x: int
y: int
point = Point(10, 20)
data = to_dict(point) # or easdict(point)
# {"x": 10, "y": 20}
from_dict(cls, data) / efromdict(cls, data)
Standalone function to create a dataclass instance from a dictionary.
from expli import from_dict, efromdict
from dataclasses import dataclass
@dataclass
class Point:
x: int
y: int
data = {"x": 10, "y": 20}
point = from_dict(Point, data) # or efromdict(Point, data)
Why expli?
Standard dataclasses don't provide built-in serialization for nested structures. While dataclasses.asdict() exists, it doesn't handle deserialization, and neither function is added to your class for convenient access.
expli solves this by:
- ✅ Adding methods directly to your dataclass
- ✅ Handling nested dataclasses recursively
- ✅ Supporting optional types and lists
- ✅ Providing both dict and JSON serialization
- ✅ Working seamlessly with type hints
- ✅ Easy copying and cloning of instances
Comparison
Without expli:
from dataclasses import dataclass, asdict
import json
@dataclass
class Person:
name: str
age: int
person = Person("Alice", 30)
# Manual serialization
data = asdict(person)
json_str = json.dumps(data)
# Manual deserialization (you have to write this!)
def from_dict(data):
return Person(**data)
person2 = from_dict(json.loads(json_str))
With expli:
from expli import edataclass
@edataclass
class Person:
name: str
age: int
person = Person("Alice", 30)
# Built-in methods
data = person.to_dict()
json_str = person.to_json()
person2 = Person.from_dict(data)
person3 = Person.from_json(json_str)
person4 = person.copy()
License
MIT
Contributing
Contributions are welcome! Please feel free to submit a Pull Request.
Metadata
Release files for expli 0.0.4
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| expli-0.0.4.tar.gz | 6.1 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| expli-0.0.4-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 12.6 kB
Release files / expli-0.0.4.tar.gz
| Download URL | expli-0.0.4.tar.gz |
|---|---|
| Size | 6.1 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
118f78e3860c8a9c06acb07ce8ad22b944e0f796f680f22820787ccfbdf9f124
|
|
BLAKE2b-256 checksum How to use checksums |
b3b0dc0a18872a2248e95588654bf72b6c69a5a579438174d5ec19d72c43c6d7
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.12.5
|
Release files / expli-0.0.4-py3-none-any.whl
| Download URL | expli-0.0.4-py3-none-any.whl |
|---|---|
| Size | 6.5 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
1419c169b29c5bc6c9b761658c29397ad52c430588d8c5d6eaa3f128e963d0f0
|
|
BLAKE2b-256 checksum How to use checksums |
626a70ac3188ec84c9ea2f162eb86b82b97f6e32c542cf5cf102aa2c1520fcec
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.12.5
|