321 lines
11 KiB
Markdown
321 lines
11 KiB
Markdown
# Project Context
|
|||
|
|
|
||
|
|
## Purpose
|
||
|
|
This project provides a toolset for managing members of a non-profit society. It consists of a graphql api. A simple MCP server that connects to the graphql api provides the tools for AI agents to manage the society administration.
|
||
|
|
|
||
|
|
## Tech Stack
|
||
|
|
|
||
|
|
### Core Framework
|
||
|
|
- **Python 3.11+** - Primary language
|
||
|
|
- **uv** - Fast Python package and project manager
|
||
|
|
- **FastAPI** - Async web framework and HTTP layer
|
||
|
|
- **Strawberry GraphQL** - Schema-first GraphQL with Python type hints
|
||
|
|
|
||
|
|
### Data Layer
|
||
|
|
- **SQLAlchemy 2.0** - ORM with modern async support
|
||
|
|
- **Alembic** - Database migration management
|
||
|
|
- **SQLite** - Development and testing database
|
||
|
|
- **PostgreSQL** - Production database (future)
|
||
|
|
|
||
|
|
### Integration Layer
|
||
|
|
- **MCP Server (Python)** - AI assistant integration
|
||
|
|
- **httpx** - HTTP client for GraphQL queries
|
||
|
|
|
||
|
|
## Project Conventions
|
||
|
|
|
||
|
|
### Code Style
|
||
|
|
|
||
|
|
#### Formatting
|
||
|
|
- **Black** - Code formatting (line length: 88)
|
||
|
|
- **isort** - Import sorting (Black-compatible profile)
|
||
|
|
- **ruff** - Fast linting and additional formatting
|
||
|
|
|
||
|
|
#### Type Hints
|
||
|
|
- Use type hints extensively for all function signatures
|
||
|
|
- Leverage Strawberry's type system for GraphQL schema
|
||
|
|
- SQLAlchemy models should use Mapped[] type annotations
|
||
|
|
- Prefer explicit types over Any where possible
|
||
|
|
|
||
|
|
#### Naming Conventions
|
||
|
|
- **Files**: lowercase_with_underscores.py
|
||
|
|
- **Classes**: PascalCase (e.g., MemberModel, MemberType)
|
||
|
|
- **Functions/Variables**: snake_case (e.g., get_member, member_id)
|
||
|
|
- **Constants**: UPPER_SNAKE_CASE (e.g., MAX_MEMBERS)
|
||
|
|
- **GraphQL Types**: PascalCase matching domain entities
|
||
|
|
- **GraphQL Fields**: camelCase (Strawberry default)
|
||
|
|
|
||
|
|
#### Code Organization
|
||
|
|
- Keep modules focused and single-purpose
|
||
|
|
- Prefer flat structure until complexity requires hierarchy
|
||
|
|
- Group related functionality (models, resolvers, services)
|
||
|
|
- Avoid circular dependencies through clear layering
|
||
|
|
|
||
|
|
#### Dependency Management
|
||
|
|
- **uv** for all Python package management
|
||
|
|
- `uv pip install <package>` - Install packages
|
||
|
|
- `uv pip compile requirements.in -o requirements.txt` - Lock dependencies
|
||
|
|
- `uv venv` - Create virtual environments
|
||
|
|
- `uv run` - Run commands in virtual environment
|
||
|
|
- **pyproject.toml** - Project metadata and dependencies
|
||
|
|
- **requirements.txt** or **uv.lock** - Locked dependency versions
|
||
|
|
- Pin major versions, allow minor/patch updates
|
||
|
|
- Regular dependency updates for security patches
|
||
|
|
- Separate dev dependencies from production dependencies
|
||
|
|
|
||
|
|
#### Documentation
|
||
|
|
- **README.md** - Primary project documentation
|
||
|
|
- Project overview and purpose
|
||
|
|
- Quick start guide
|
||
|
|
- Installation instructions (uv setup)
|
||
|
|
- Basic usage examples
|
||
|
|
- Links to OpenSpec documentation
|
||
|
|
- Contributing guidelines
|
||
|
|
- License information
|
||
|
|
- Keep README.md up-to-date with major changes
|
||
|
|
- README is the entry point for new developers and AI assistants
|
||
|
|
- For detailed specs, refer to `openspec/` directory
|
||
|
|
|
||
|
|
### Architecture Patterns
|
||
|
|
|
||
|
|
#### Layered Architecture
|
||
|
|
```
|
||
|
|
API Layer (FastAPI + Strawberry)
|
||
|
|
↓
|
||
|
|
Service Layer (Business Logic)
|
||
|
|
↓
|
||
|
|
Data Layer (SQLAlchemy Models)
|
||
|
|
↓
|
||
|
|
Database (SQLite/PostgreSQL)
|
||
|
|
```
|
||
|
|
|
||
|
|
#### GraphQL Schema Design
|
||
|
|
- **Type hints as schema**: Use Python types to define GraphQL schema
|
||
|
|
- **Simple, consistent filters**: Prefer explicit arguments over complex nested filters
|
||
|
|
- Good: `members(status: MemberStatus, joinedAfter: Date)`
|
||
|
|
- Avoid: `members(where: {and: [{status: {eq: ACTIVE}}]})`
|
||
|
|
- **Introspection-friendly**: Design schema for AI consumption via introspection
|
||
|
|
- **Field descriptions**: Document all fields for self-describing API
|
||
|
|
|
||
|
|
#### Database Patterns
|
||
|
|
- **Database-agnostic code**: Write portable SQLAlchemy code for SQLite/PostgreSQL
|
||
|
|
- **Connection string switching**: Same code works with different databases
|
||
|
|
- **Alembic migrations**: All schema changes via migrations
|
||
|
|
- **Async operations**: Use async SQLAlchemy patterns where beneficial
|
||
|
|
|
||
|
|
#### Authentication
|
||
|
|
- **JWT tokens** at HTTP layer (FastAPI middleware)
|
||
|
|
- **Service account** for MCP server (admin privileges)
|
||
|
|
- GraphQL resolvers assume authenticated context
|
||
|
|
- Future: User-specific MCP instances
|
||
|
|
|
||
|
|
#### Simplicity Principles
|
||
|
|
- Default to single-file implementations (<100 lines)
|
||
|
|
- Avoid frameworks/abstractions without clear justification
|
||
|
|
- Choose boring, proven patterns
|
||
|
|
- Add complexity only with:
|
||
|
|
- Performance data showing need
|
||
|
|
- Concrete scale requirements
|
||
|
|
- Multiple proven use cases
|
||
|
|
|
||
|
|
### Testing Strategy
|
||
|
|
|
||
|
|
#### Testing Pyramid
|
||
|
|
- **Unit Tests**: Core business logic and utilities
|
||
|
|
- **Integration Tests**: Database operations and GraphQL resolvers
|
||
|
|
- **E2E Tests**: Complete GraphQL query/mutation flows
|
||
|
|
- **MCP Tests**: Tool definitions and API integration
|
||
|
|
|
||
|
|
#### Framework & Tools
|
||
|
|
- **pytest** - Test runner with async support
|
||
|
|
- **pytest-asyncio** - Async test support
|
||
|
|
- **httpx** - Test client for FastAPI/GraphQL
|
||
|
|
- **SQLAlchemy test fixtures** - In-memory SQLite for fast tests
|
||
|
|
|
||
|
|
#### Test Organization
|
||
|
|
```
|
||
|
|
tests/
|
||
|
|
├── unit/ # Pure logic tests
|
||
|
|
├── integration/ # Database + resolver tests
|
||
|
|
├── e2e/ # Full API tests
|
||
|
|
└── mcp/ # MCP server tests
|
||
|
|
```
|
||
|
|
|
||
|
|
#### Coverage Goals
|
||
|
|
- Aim for >80% coverage on business logic
|
||
|
|
- 100% coverage on critical paths (payments, memberships)
|
||
|
|
- Focus on behavior, not implementation details
|
||
|
|
- Test error cases and edge conditions
|
||
|
|
|
||
|
|
#### Testing Conventions
|
||
|
|
- One test file per module: `test_<module>.py`
|
||
|
|
- Descriptive test names: `test_member_creation_with_valid_data`
|
||
|
|
- Use fixtures for common setup (db session, test data)
|
||
|
|
- Clean database state between tests
|
||
|
|
- Mock external services (future: email, payment providers)
|
||
|
|
|
||
|
|
### Git Workflow
|
||
|
|
|
||
|
|
#### Branching Strategy with Worktrees
|
||
|
|
- **main** - Production-ready code (primary worktree)
|
||
|
|
- **Feature branches** - `feature/<description>` or `<change-id>` from OpenSpec
|
||
|
|
- **Hotfix branches** - `hotfix/<issue>`
|
||
|
|
- Use **git worktrees** for parallel development:
|
||
|
|
- Each branch gets its own directory
|
||
|
|
- Work on multiple features simultaneously
|
||
|
|
- No need to stash or switch contexts
|
||
|
|
- Example: `git worktree add ../clubber-feature-payments feature/payments`
|
||
|
|
- Keep branches short-lived (1-3 days max)
|
||
|
|
- Remove worktree and delete branch after merge
|
||
|
|
|
||
|
|
#### Commit Conventions
|
||
|
|
- Use conventional commits format:
|
||
|
|
- `feat:` - New features
|
||
|
|
- `fix:` - Bug fixes
|
||
|
|
- `refactor:` - Code refactoring
|
||
|
|
- `docs:` - Documentation changes
|
||
|
|
- `test:` - Test additions/changes
|
||
|
|
- `chore:` - Build, config, dependencies
|
||
|
|
- Examples:
|
||
|
|
- `feat: add member payment tracking`
|
||
|
|
- `fix: correct member status calculation`
|
||
|
|
- `refactor: simplify GraphQL resolver logic`
|
||
|
|
|
||
|
|
#### Pull Request Process
|
||
|
|
1. Create worktree for feature branch from main
|
||
|
|
2. Implement changes with tests in worktree
|
||
|
|
3. Run tests and linting locally
|
||
|
|
4. Create PR with clear description
|
||
|
|
5. Link to OpenSpec change if applicable
|
||
|
|
6. Review and address feedback
|
||
|
|
7. Squash merge to main
|
||
|
|
8. Remove worktree: `git worktree remove <path>`
|
||
|
|
|
||
|
|
#### Pre-commit Checks
|
||
|
|
- Black formatting
|
||
|
|
- isort import sorting
|
||
|
|
- ruff linting
|
||
|
|
- Type checking (mypy)
|
||
|
|
- Tests pass
|
||
|
|
|
||
|
|
## Domain Context
|
||
|
|
|
||
|
|
### Non-Profit Society Management
|
||
|
|
This system manages members of a registered non-profit society (Verein/club).
|
||
|
|
|
||
|
|
#### Core Entities
|
||
|
|
- **Members**: Individuals who belong to the society
|
||
|
|
- Active, inactive, honorary members
|
||
|
|
- Membership start/end dates
|
||
|
|
- Contact information
|
||
|
|
- Payment status
|
||
|
|
|
||
|
|
- **Memberships**: The relationship between members and the society
|
||
|
|
- Annual/lifetime memberships
|
||
|
|
- Membership fees
|
||
|
|
- Payment tracking
|
||
|
|
- Status changes over time
|
||
|
|
|
||
|
|
- **Payments**: Financial transactions
|
||
|
|
- Membership fees
|
||
|
|
- Donations
|
||
|
|
- Event fees
|
||
|
|
- Payment methods and tracking
|
||
|
|
|
||
|
|
- **Events** (future): Society activities and meetings
|
||
|
|
- Member participation
|
||
|
|
- Registration and attendance
|
||
|
|
|
||
|
|
#### Business Rules
|
||
|
|
- Members must have valid contact information
|
||
|
|
- Membership status changes based on payment history
|
||
|
|
- Privacy considerations for member data (GDPR compliance)
|
||
|
|
- Financial records must be auditable
|
||
|
|
- Society governance (board members, voting rights)
|
||
|
|
|
||
|
|
#### Common Operations
|
||
|
|
- Add new members
|
||
|
|
- Track membership payments
|
||
|
|
- Generate membership lists
|
||
|
|
- Send payment reminders
|
||
|
|
- Export reports for annual meetings
|
||
|
|
- Member communication
|
||
|
|
|
||
|
|
## Important Constraints
|
||
|
|
|
||
|
|
### Technical Constraints
|
||
|
|
- **Database portability**: Code must work with both SQLite and PostgreSQL
|
||
|
|
- **Async-first**: Use async patterns for scalability
|
||
|
|
- **Single-server deployment**: No distributed systems initially
|
||
|
|
- **Limited resources**: Optimize for small-scale (<1000 members initially)
|
||
|
|
- **Python-only**: Keep the stack simple with one primary language
|
||
|
|
|
||
|
|
### Business Constraints
|
||
|
|
- **Data privacy**: GDPR compliance for EU member data
|
||
|
|
- Right to access (export member data)
|
||
|
|
- Right to deletion (full data removal)
|
||
|
|
- Consent tracking for communications
|
||
|
|
- Data minimization principles
|
||
|
|
- **Audit trail**: Financial transactions must be traceable
|
||
|
|
- **Offline capability**: Export functionality for offline access to critical data
|
||
|
|
- **Non-profit requirements**: Transparent financial reporting
|
||
|
|
|
||
|
|
### AI Integration Constraints
|
||
|
|
- **Schema introspection**: GraphQL schema must be AI-readable
|
||
|
|
- **Simple query patterns**: Avoid complex nested filters
|
||
|
|
- **Service account authentication**: MCP server uses admin credentials
|
||
|
|
- **Rate limiting**: Protect against excessive API usage (future)
|
||
|
|
- **Query complexity limits**: Prevent resource-intensive operations
|
||
|
|
|
||
|
|
### Development Constraints
|
||
|
|
- **Simplicity first**: Avoid premature optimization
|
||
|
|
- **Incremental delivery**: Start with core features, expand gradually
|
||
|
|
- **Solo developer**: Optimize for maintainability over cleverness
|
||
|
|
- **Open source ready**: Clean, documented code for potential future contributors
|
||
|
|
|
||
|
|
## External Dependencies
|
||
|
|
|
||
|
|
### Current Dependencies
|
||
|
|
- **Python Package Index (PyPI)**: Package registry (managed via uv)
|
||
|
|
- strawberry-graphql
|
||
|
|
- fastapi
|
||
|
|
- sqlalchemy
|
||
|
|
- alembic
|
||
|
|
- httpx
|
||
|
|
- pytest and testing tools
|
||
|
|
- **uv**: Fast package installer and resolver
|
||
|
|
|
||
|
|
### Future/Planned Dependencies
|
||
|
|
- **Email Service** (future): Transactional emails
|
||
|
|
- Payment reminders
|
||
|
|
- Membership notifications
|
||
|
|
- Board communications
|
||
|
|
- Consider: SMTP, SendGrid, or similar
|
||
|
|
|
||
|
|
- **Payment Processing** (future): Online payment collection
|
||
|
|
- Bank transfers (EU SEPA)
|
||
|
|
- Credit card processing
|
||
|
|
- Payment reconciliation
|
||
|
|
- Consider: Stripe, PayPal, or EU-specific providers
|
||
|
|
|
||
|
|
- **Document Storage** (future): Member documents and files
|
||
|
|
- Meeting minutes
|
||
|
|
- Member applications
|
||
|
|
- Financial reports
|
||
|
|
- Consider: Local filesystem, S3-compatible storage
|
||
|
|
|
||
|
|
- **Backup Service** (future): Automated backups
|
||
|
|
- Database backups
|
||
|
|
- Document backups
|
||
|
|
- Disaster recovery
|
||
|
|
|
||
|
|
### MCP Integration
|
||
|
|
- **Claude AI API**: For AI assistant features via MCP
|
||
|
|
- **MCP Protocol**: Standard protocol for AI tool integration
|
||
|
|
- **GraphQL Introspection**: Self-documenting API for AI consumption
|
||
|
|
|
||
|
|
### Development Tools
|
||
|
|
- **Git**: Version control
|
||
|
|
- **GitHub** (optional): Code hosting and collaboration
|
||
|
|
- **Docker** (optional): Containerization for deployment
|
||
|
|
- **CI/CD** (future): Automated testing and deployment
|