- Refactor major-domo skill: api_client.py, cli.py, and CLI modules (admin, common, injuries, results, schedule, transactions) with significant simplification (-275 lines net) - Update CLI_REFERENCE.md and SKILL.md docs for major-domo - Update create-scheduled-task SKILL.md - Update plugins blocklist.json and known_marketplaces.json - Add patterns/ directory to repo - Update CLAUDE.md Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
1.8 KiB
1.8 KiB
Python Patterns & Preferences
Package Management
- Always use
uvfor package and environment management - Never use pip directly; prefer
uv pip,uv sync,uv run
Linting & Formatting
- Use Ruff for linting and Black for formatting
- Include both as dev dependencies in new projects (
uv add --dev ruff black)
Code Style
- Utilize dependency injection pattern whenever possible
- Never add lazy imports to the middle of a file — all imports at the top
FastAPI / Backend Services
Use Ports & Adapters (Hexagonal Architecture) to cleanly separate concerns:
project/
domain/ # Pure business logic, no framework imports
models.py # Domain entities / value objects
services.py # Use cases / business rules
ports.py # Abstract interfaces (ABC) for external dependencies
adapters/
inbound/ # FastAPI routers, CLI handlers — drive the domain
outbound/ # Database repos, API clients — implement domain ports
config/ # App wiring, dependency injection, settings
main.py # FastAPI app creation, adapter registration
Key rules
- Domain layer has zero framework imports — no FastAPI, SQLAlchemy, httpx, etc.
- Ports are abstract base classes in the domain that define what the domain needs (e.g.,
UserRepository(ABC)) - Outbound adapters implement ports (e.g.,
PostgresUserRepository(UserRepository)) - Inbound adapters (routers) depend on domain services, never on outbound adapters directly
- Dependency injection wires adapters to ports at startup in
config/ormain.py - Tests can swap outbound adapters for in-memory fakes by implementing the same port
- Models passed across boundaries should be domain models or DTOs — never ORM models in router responses