# Contributing to error-kit
Thank you for your interest in contributing to error-kit! This document provides guidelines for contributing to this project.
## Project Philosophy
error-kit follows a philosophy of **developer-focused error handling with maximum ergonomics**. We aim to:
- Provide clear, actionable error messages for developers
- Maintain type safety through Rust's enum system
- Keep helper functions simple and explicit (no complex macros)
- Follow Rust best practices and idiomatic patterns
## Development Status
**Pre-Release Phase**: This library is currently in pre-release development. The first public release is planned once the core error handling infrastructure is complete, representing a solid foundation for Rust error management.
We maintain a clean development roadmap focused on error handling excellence, and can accommodate new requirements as they arise, but all contributions must align with the library's core principles.
## Contribution Standards
All contributions must meet these requirements:
### 1. **Code Quality**
- Follow Rust conventions and best practices
- Use `rustfmt` for code formatting
- Pass all `clippy` lints without warnings
- Maintain the existing code style and patterns
### 2. **Documentation**
- **All public APIs must have comprehensive documentation**
- Include doc comments for all public functions, structs, enums, and traits
- Provide code examples in documentation where appropriate
- Update README.md if adding new features or changing existing behavior
### 3. **Testing**
- **All new functionality must have comprehensive test coverage**
- Follow the established testing patterns (see Testing Guidelines below)
- Test edge cases and error conditions
- Ensure all tests pass before submitting
### 4. **Scope Alignment**
- Contributions should align with the library's minimalist philosophy
- New features should provide significant value without adding complexity
- Consider if the feature belongs in core or as an optional extension
## Types of Contributions
### High Priority (Welcome)
- Bug fixes with tests
- Documentation improvements
- Performance optimizations
- Test coverage improvements
- Implementation of planned features from the TODO list
### Medium Priority (Considered)
- New error types that align with common use cases
- API improvements that maintain backward compatibility
- Additional helper functions for error construction
### Low Priority (Selective)
- Large architectural changes
- Features that significantly expand the scope
- Breaking changes (will be carefully evaluated)
## Submission Process
### 1. **Before You Start**
- Check existing issues and pull requests to avoid duplication
- For significant changes, open an issue first to discuss the approach
- Ensure your contribution aligns with the project philosophy
### 2. **Development Process**
1. Fork the repository
2. Create a feature branch: `git checkout -b feature/your-feature-name`
3. Make your changes following the contribution standards
4. Write comprehensive tests
5. Update documentation
6. Ensure all tests pass: `cargo test`
7. Check code formatting: `cargo fmt --check`
8. Run clippy: `cargo clippy -- -D warnings`
### 3. **Pull Request Requirements**
- **Clear description** of what the PR does and why
- **Reference any related issues**
- **Include test results** showing all tests pass
- **Documentation updates** for any API changes
- **Breaking changes** must be clearly marked and justified
### 4. **Review Process**
- All PRs require review and approval
- Reviews focus on code quality, test coverage, and alignment with project goals
- Be prepared to make revisions based on feedback
- Maintain a respectful and collaborative tone
## Development Setup
```bash
# Clone the repository
git clone https://github.com/dominikj111/error-kit.git
cd error-kit
# Run tests
cargo test
# Check formatting
cargo fmt --check
# Run clippy
cargo clippy -- -D warnings
# Build documentation
cargo doc --open
```
## Code Style Guidelines
### Naming Conventions
- Use descriptive names for functions and variables
- Follow Rust naming conventions (snake_case for functions/variables, PascalCase for types)
- Use meaningful type names that reflect their purpose
### Error Handling
- Use `Result` types for operations that can fail
- Provide descriptive error messages using `thiserror`
- Follow the existing error handling patterns
- Use helper functions over macros for error construction
- Keep error messages developer-focused and actionable
### Constructor Function Requirements
When adding new error variants and their constructor functions, follow these strict guidelines:
- **No-argument constructors** for simple error variants that don't require additional context
- **Arguments only when the error message requires parameters** (e.g., `serialization(detail: &'static str)`)
- **No cross-calling between constructors** - each constructor should directly create its specific variant
- **One constructor per error variant** - avoid multiple paths to the same error type
- **Reduce verbosity** - constructors should make error creation simpler, not more complex
```rust
// ✅ Good: No-arg constructor for simple errors
pub fn timeout() -> Self {
CommonError::Timeout
}
// ✅ Good: Arguments only when message needs them
pub fn serialization(detail: &'static str) -> Self {
CommonError::Serialization(detail)
}
// ❌ Bad: Unnecessary arguments for simple errors
pub fn timeout(message: &str) -> Self { /* ... */ }
// ❌ Bad: Cross-calling between constructors
pub fn filename_error() -> Self {
Self::io_error("filename issue") // Don't do this
}
```
### Documentation Style
````rust
/// Brief description of what the function does.
///
/// More detailed explanation if needed, including:
/// - Important behavior notes
/// - Examples of usage
/// - Error conditions
///
/// # Arguments
///
/// * `param` - Description of the parameter
///
/// # Returns
///
/// Description of what is returned
///
/// # Errors
///
/// When this function will return an error
///
/// # Examples
///
/// ```rust
/// // Example usage
/// ```
pub fn example_function(param: Type) -> Result<ReturnType, Error> {
// Implementation
}
````
## Testing Guidelines
Since error-kit is a simple library focused on ergonomic error handling, our testing strategy prioritizes **essential functionality** over exhaustive coverage. Follow these patterns when adding tests:
### Core Testing Principles
1. **Constructor Verification** - Test that helper functions create the correct error types
2. **Message Consistency** - Verify error display uses the correct message constants
3. **Variant Construction** - Ensure all error variants can be instantiated
### What to Test (High Priority)
- **New Error Variants**: Test construction and display message
- **Constructor Functions**: Verify they return the expected error type without cross-calling
- **Message Constants**: Ensure they're used correctly in error display
- **Error Conversions**: Test `From` implementations work correctly
### What NOT to Test (Keep Simple)
- **thiserror Implementation Details**: Don't test the derive macro internals
- **Standard Library Behavior**: Don't test `std::io::Error` functionality
- **Display Formatting Edge Cases**: Basic message verification is sufficient
- **Complex Integration Scenarios**: Keep tests focused on the library's scope
### Testing Patterns
```rust
// Pattern 1: Constructor verification
#[test]
fn test_constructor_creates_correct_type() {
let error = CommonError::timeout();
assert!(matches!(error, CommonError::Timeout));
let error_with_param = CommonError::serialization("JSON");
assert!(matches!(error_with_param, CommonError::Serialization(_)));
}
// Pattern 2: Message consistency
#[test]
fn test_error_uses_constant() {
let error = CommonError::SomeVariant;
assert_eq!(error.to_string(), messages::SOME_CONSTANT);
}
// Pattern 3: Variant construction
#[test]
fn test_all_variants_constructible() {
let _variant1 = CommonError::Variant1("param");
let _variant2 = CommonError::Variant2;
// Ensure compilation succeeds
}
```
### File Organization
- `constructors_test.rs` - Test helper functions and error construction
- `types_test.rs` - Test error variants, display, and message constants
- Add new files only when a module grows significantly
## Questions and Support
- **Issues**: For bugs, feature requests, or questions
- **Discussions**: For general questions about usage or design
- **Email**: For private inquiries
## Recognition
Contributors will be recognized in the project documentation and release notes. We appreciate all contributions that help make error-kit better!
## License
By contributing to error-kit, you agree that your contributions will be licensed under the BSD 3-Clause License.