Functional programming patterns for Python
Project description
better-py
Functional programming patterns for Python - pragmatic, type-safe, and developer-friendly.
✨ Features
Monads & Functional Types
Maybe[T]- Handle optional values safelyResult<T, E>- Explicit error handlingEither<L, R>- Two-value alternativesValidation<T, E>- Accumulate validation errors- And more:
Try,IO,Reader,Writer,State,Task, etc.
Functional Collections
MappableList[T]- List with functional operationsImmutableDict[K, V]- Safe immutable dictionariesLazySequence[T]- Lazy evaluation sequencesBidirectionalMap[K, V]- Two-way lookups
Function Utilities
curry(f)- Incremental argument applicationcompose(f, g)- Function compositionpipe(value, f, g)- Left-to-right pipelinespartial(f, ...)- Fix function arguments
OOP-First Design
- Protocol-based (like
collections.abc) - Generic types with full type hints
- Method chaining and fluent APIs
- Modern Python patterns (dataclasses, protocols, etc.)
🚀 Quick Start
from better_py import Maybe, Result, pipe
# Maybe: Safe optional handling
user = Maybe.from_value(get_user(id))
name = user.map(lambda u: u.name).unwrap_or_else(lambda: "Guest")
# Result: Explicit error handling
def divide(a: int, b: int) -> Result[float, str]:
if b == 0:
return Result.error("Division by zero")
return Result.ok(a / b)
result = divide(10, 2)
if result.is_ok():
print(f"Result: {result.unwrap()}")
else:
print(f"Error: {result.unwrap_error()}")
# Pipe: Data pipelines
result = pipe(
data,
validate,
transform,
save
)
📦 Installation
# Install from PyPI
pip install better-py
# Or with uv (recommended)
uv pip install better-py
Requirements: Python 3.11+
📚 Documentation
💡 Why better-py?
Pragmatic FP
Not academic functional programming - practical patterns that make software development easier.
Type-Safe
Full type hints with mypy strict mode. Catch errors before runtime.
OOP-First
Everything is an object. Operations are functional. Works naturally with Python.
Developer-Friendly
Clear error messages, helpful APIs, extensive documentation.
🎯 Use Cases
# REST API error handling
from better_py import Result
async def get_user(id: int) -> Result[User, Error]:
user = await db.fetch_user(id)
if not user:
return Result.error(Error("User not found"))
return Result.ok(user)
# Data validation
from better_py import Validation
email_validated = Validation.validate(email, EmailValidator())
password_validated = Validation.validate(password, PasswordValidator())
user_validation = email_validated.and_then(password_validated)
if user_validation.is_valid():
create_user(email, password)
# Data processing pipeline
from better_py import pipe
result = pipe(
raw_data,
clean,
validate,
transform,
load_to_db
)
🏗️ Project Status
Current Version: 0.1.0 (Alpha)
What's Working:
- ✅ Documentation framework
- ✅ CI/CD pipeline
- ✅ Type system design
In Development:
- 🔄 Core protocols (Mappable, Reducible, etc.)
- 🔄 Monad implementations
- 🔄 Functional collections
- 🔄 Function utilities
Planned:
- 📋 More monads (Writer, State, etc.)
- 📋 Performance benchmarks
- 📋 Integration examples (FastAPI, SQLAlchemy, etc.)
See Issues for detailed roadmap.
🤝 Contributing
Contributions are welcome! Please see CONTRIBUTING.md for details.
Quick start:
# Clone repository
git clone https://github.com/nesalia-inc/better-py.git
cd better-py
# Install with uv
uv venv && source .venv/bin/activate # Windows: .venv\Scripts\activate
uv sync --all-extras
# Run tests
uv run pytest
# Run checks
uv run ruff check .
uv run mypy better_py
📄 License
MIT License - see LICENSE for details.
🙏 Acknowledgments
Inspired by:
📮 Contact
- GitHub: nesalia-inc/better-py
- Issues: GitHub Issues
Made with ❤️ by nesalia-inc
Project details
Release history Release notifications | RSS feed
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 better_py_fp-0.2.0.tar.gz.
File metadata
- Download URL: better_py_fp-0.2.0.tar.gz
- Upload date:
- Size: 34.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.9.21 {"installer":{"name":"uv","version":"0.9.21","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Fedora Linux","version":"43","id":"","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
8337c8c3519e4d41a945a6e2924859de9da2cfa47934cd28e381f1acb8697147
|
|
| MD5 |
7d6ddfd12457b4028eabf57223edf2c1
|
|
| BLAKE2b-256 |
df0ad141de663d5a9a88670ed895d362131884d6a864dd06b0170ce8d235e740
|
File details
Details for the file better_py_fp-0.2.0-py3-none-any.whl.
File metadata
- Download URL: better_py_fp-0.2.0-py3-none-any.whl
- Upload date:
- Size: 51.5 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.9.21 {"installer":{"name":"uv","version":"0.9.21","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Fedora Linux","version":"43","id":"","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
f7edb5310c44a5988c6e236471710c0af51e8becc16c0e395b6828d361670130
|
|
| MD5 |
3d49b56cc82dd2a1b4c7c79157a7fbc2
|
|
| BLAKE2b-256 |
1fd253fe8737717f83796e15f5813bed921391fc37dbf79924695463f3995243
|