Thank you for your interest in contributing to FlashRecord! This guide will help you get started.
- Development Setup
- Running Tests
- Code Style
- Testing Your Changes
- Submitting a PR
- Project Architecture
- Python 3.8+
- Poetry (for dependency management)
- Git
-
Clone the repository
git clone https://github.com/yourusername/flashrecord.git cd flashrecord -
Install Poetry (if not already installed)
curl -sSL https://install.python-poetry.org | python3 - -
Install dependencies
poetry install
-
Activate virtual environment
poetry shell
# Run tests to verify setup
pytest tests/ -v
# Check code style
ruff check flashrecord/poetry run pytest tests/ -vpoetry run pytest tests/test_cli.py -vpoetry run pytest tests/ --cov=flashrecord --cov-report=term-missing====== 38 passed in 0.18s ======
All tests must pass before submitting a PR.
Check for style issues:
poetry run ruff check flashrecord/Fix automatically (where possible):
poetry run ruff check flashrecord/ --fix- Line Length: Max 100 characters
- Naming:
- Functions/variables:
snake_case - Classes:
PascalCase - Constants:
UPPER_CASE
- Functions/variables:
- Imports: Group as stdlib, third-party, local (alphabetical within groups)
- Docstrings: One-line for simple functions, multi-line for complex ones
"""
Module docstring - one line summary
"""
from typing import Optional
from pydantic import BaseModel
class ConfigManager(BaseModel):
"""Configuration management with validation"""
name: str
value: Optional[int] = None
def load(self) -> dict:
"""Load configuration and return as dict"""
return {"name": self.name, "value": self.value}-
Create a new branch
git checkout -b feature/your-feature-name
-
Make your changes
-
Run tests locally
poetry run pytest tests/ -v --cov=flashrecord
When adding new functionality, include tests:
# tests/test_your_feature.py
import pytest
from flashrecord.your_module import YourClass
def test_basic_functionality():
"""Test basic functionality"""
obj = YourClass()
assert obj.method() is not None
def test_error_handling():
"""Test error handling"""
obj = YourClass()
with pytest.raises(ValueError):
obj.method(invalid_input)- New code should have at least 80% test coverage
- Critical paths should have 100% coverage
-
Run full test suite
poetry run pytest tests/ -v --cov=flashrecord --cov-report=html
-
Check code style
poetry run ruff check flashrecord/
-
Update documentation
- Update README.md if user-facing changes
- Update docstrings if API changes
- Update CHANGELOG.md
[AREA] Brief description
Examples:
[CLI] Add new command style 'compact'
[CONFIG] Implement Pydantic validation
[API] Add new /recording/gif endpoint
[DOCS] Update README with API examples
[TEST] Improve coverage for manager.py
## Summary
Brief description of changes
## Type of Change
- [ ] Bug fix
- [ ] New feature
- [ ] Breaking change
- [ ] Documentation
## Testing
- [ ] Tests added/updated
- [ ] All tests pass
- [ ] Coverage maintained (>80%)
## Checklist
- [ ] Code follows style guidelines
- [ ] Docstrings updated
- [ ] README updated (if user-facing)
- [ ] No breaking changes (or documented)flashrecord/
├── flashrecord/ # Main package
│ ├── __init__.py # Package init
│ ├── cli.py # CLI interface
│ ├── api.py # REST API (FastAPI)
│ ├── config.py # Configuration (Pydantic)
│ ├── screenshot.py # Screenshot capture
│ ├── video_recorder.py # Video recording
│ ├── ai_prompt.py # AI session saving
│ ├── manager.py # File management
│ ├── utils.py # Utilities
│ └── install.py # Setup wizard
├── tests/ # Test suite
│ ├── test_cli.py
│ ├── test_config.py
│ ├── test_screenshot.py
│ ├── test_video_recorder.py
│ ├── test_manager.py
│ ├── test_utils.py
│ └── test_ai_prompt.py
├── output/ # Media root (auto-created, dated subfolders)
├── .github/workflows/ # CI/CD
├── pyproject.toml # Poetry config
├── README.md # User guide
├── CONTRIBUTING.md # This file
└── LICENSE # MIT License
| Module | Purpose |
|---|---|
| cli.py | User input processing and command routing |
| api.py | REST API endpoints for programmatic access |
| config.py | Configuration loading and validation (Pydantic) |
| screenshot.py | Screen capture integration with hcap |
| video_recorder.py | Terminal recording and GIF conversion |
| ai_prompt.py | Session markdown file management |
| manager.py | File lifecycle and cleanup |
| utils.py | Timestamp and formatting utilities |
| install.py | First-time setup wizard |
User Input (CLI/API)
↓
Command Router (cli.py or api.py)
↓
Action Handler (screenshot/video_recorder/ai_prompt)
↓
File Manager (manager.py)
↓
Output (output/<date>/screenshots|gifs|sessions)
config.json
↓
Config class (Pydantic validation)
↓
FlashRecordConfig (type-safe model)
↓
Available in CLI/API
Start the API server:
poetry run python -m flashrecord.apiVisit http://localhost:8000/docs for interactive API documentation.
Enable debug logging:
import logging
logging.basicConfig(level=logging.DEBUG)Add a new command style:
- Update
FlashRecordConfig.command_styleLiteral inconfig.py - Add mapping in
cli.py:map_command() - Add tests in
test_cli.py - Update README.md
Add a new API endpoint:
- Create endpoint function in
api.py - Use Pydantic models for request/response
- Add tests (or use
/docsto test manually) - Document in README.md
Improve performance:
- Profile with
cProfileorpy-spy - Write benchmarks
- Submit with measurements
All PRs require:
- ✅ All tests pass
- ✅ Code coverage > 80%
- ✅ Ruff check passes
- ✅ Documentation updated
- ✅ At least one approval
- Open an issue on GitHub
- Check existing issues first
- Include error messages and reproduction steps
By contributing, you agree that your contributions will be licensed under the MIT License.
Thank you for contributing to FlashRecord!
- DEPLOYMENT.md: Detailed deployment and release instructions
- README.md: User-facing documentation
- .DEVELOPMENT_ROADMAP.md: Future development plans (contributors only)
For questions, open an issue or discussion on GitHub.