Lightweight validation library for (micro)Python
Project description
uzod
uzod is a lightweight validation library inspired by zod for (micro)python that provides runtime type checking and validation with a clean, chainable API.
Features
🦾 Ergonomic API - Fluent, chainable interface
🛡️ Type-safe - Comes with complete type stubs for IDE support
🪶 Lightweight - Zero dependencies, single file (~220 lines)
🤸🏻 Flexible - Built-in validators + custom refinements
🧩 Composable - Build complex schemas from simple primitives
Installation
Install from PyPI:
pip install uzod
Or just copy uzod.py into your project - it's standalone!
Quick Start
from uzod import z, ValidationError
# Define a schema
user_schema = z.object({
"name": z.string(min=2, max=50),
"email": z.string().refine(lambda s: "@" in s, "invalid email"),
"age": z.integer(min=0, max=120).optional,
})
# Validate data
try:
user = user_schema.parse({
"name": "Alice",
"email": "alice@example.com",
"age": 30
})
print(user) # {'name': 'Alice', 'email': 'alice@example.com', 'age': 30}
except ValidationError as error:
print(f"Validation failed: {error}")
API Reference
String
z.string() # Any string
z.string(min=3) # At least 3 characters
z.string(max=100) # At most 100 characters
z.string(min=3, max=100) # Between 3-100 characters
Integer
z.integer() # Any integer
z.integer(min=0) # Non-negative
z.integer(min=1, max=10) # Between 1-10
Float
z.float() # Any float
z.float(min=0.0) # Non-negative
z.float(min=0.0, max=1.0) # Between 0.0-1.0
Boolean
z.boolean() # true or false
Literal
z.literal("admin", "user") # Must be "admin" or "user"
z.literal(1, 2, 3) # Must be 1, 2, or 3
Array
z.array(z.string()) # Array of strings
z.array(z.integer(), min=1, max=10) # 1-10 integers
z.array(z.object({...})) # Array of objects
Object
z.object({
"name": z.string(),
"age": z.integer()
})
# Strict mode - reject unknown keys (can also be used with chainable method)
z.object({"name": z.string()}, strict=True)
Union
z.union(z.string(), z.integer()) # String OR integer
z.union(z.literal("yes", "no"), z.boolean())
Modifiers
Optional
# Field can be omitted (returns None)
z.object({
"name": z.string(),
"nickname": z.string().optional
})
# parse({"name": "Alice"}) -> {"name": "Alice", "nickname": None}
Nullable
# Field can be None
z.object({
"name": z.string().nullable
})
# parse({"name": None}) -> {"name": None}
Default
# Provide default value when field is missing or None
z.object({
"role": z.string().default("user")
})
# parse({}) -> {"role": "user"}
Refine (Custom Validation)
# Add custom validation logic
z.string().refine(lambda s: s.isalnum(), "must be alphanumeric")
z.integer().refine(lambda n: n % 2 == 0, "must be even")
Error Messages
uzod provides helpful error messages:
>>> z.string(min=5).parse("hi")
ValidationError: too short, at least 5 chars
>>> z.integer().parse("123")
ValidationError: expected int, got str
>>> z.object({"name": z.string()}).parse({"name": 123})
ValidationError: name: expected str, got int
>>> z.object({"a": z.string()}, strict=True).parse({"a": "x", "b": "y"})
ValidationError: unexpected keys: b
Contributing
Contributions are welcome! This is a small, focused library - let's keep it that way.
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file uzod-1.0.0.tar.gz.
File metadata
- Download URL: uzod-1.0.0.tar.gz
- Upload date:
- Size: 6.1 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
ddda9c26f2c4601ae20a2d1332f27be36a8bbb3000d4b2b0295650fdce8b9242
|
|
| MD5 |
73d70825bf152015778528f0c1707a44
|
|
| BLAKE2b-256 |
89ff1356c27f362e891bc04d79e71fc70b8bb597f02d628e8e81eb678527ec6a
|
Provenance
The following attestation bundles were made for uzod-1.0.0.tar.gz:
Publisher:
publish-to-pypi.yml on markusand/uzod
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
uzod-1.0.0.tar.gz -
Subject digest:
ddda9c26f2c4601ae20a2d1332f27be36a8bbb3000d4b2b0295650fdce8b9242 - Sigstore transparency entry: 1154408174
- Sigstore integration time:
-
Permalink:
markusand/uzod@a937037a054ffb5f175336d13e439fb47d60a0a9 -
Branch / Tag:
refs/tags/1.0.0 - Owner: https://github.com/markusand
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish-to-pypi.yml@a937037a054ffb5f175336d13e439fb47d60a0a9 -
Trigger Event:
release
-
Statement type:
File details
Details for the file uzod-1.0.0-py3-none-any.whl.
File metadata
- Download URL: uzod-1.0.0-py3-none-any.whl
- Upload date:
- Size: 5.6 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0cf36d365b85fc86fc43fbde69edfc2712d0317b5e3d2ba2785fcb8c09fb766c
|
|
| MD5 |
172238ddc2ca5652c861b6e555fe1a22
|
|
| BLAKE2b-256 |
57cf739ef80ccf163b2e2ebc13f156eee4911226506409a2b75ddcf833ac5262
|
Provenance
The following attestation bundles were made for uzod-1.0.0-py3-none-any.whl:
Publisher:
publish-to-pypi.yml on markusand/uzod
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
uzod-1.0.0-py3-none-any.whl -
Subject digest:
0cf36d365b85fc86fc43fbde69edfc2712d0317b5e3d2ba2785fcb8c09fb766c - Sigstore transparency entry: 1154408182
- Sigstore integration time:
-
Permalink:
markusand/uzod@a937037a054ffb5f175336d13e439fb47d60a0a9 -
Branch / Tag:
refs/tags/1.0.0 - Owner: https://github.com/markusand
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish-to-pypi.yml@a937037a054ffb5f175336d13e439fb47d60a0a9 -
Trigger Event:
release
-
Statement type: