5.9 KiB
5.9 KiB
Contributing to SymClaw
Thank you for your interest in SymClaw! This guide will help you get started.
Development Environment
Nix (Recommended)
git clone https://github.com/symclaw/symclaw.git
cd symclaw
nix develop # Drops you into a shell with Rust, wasm-pack, and all tools
cargo test # Verify everything works
Manual Setup
Requirements:
- Rust 1.93.0+ (edition 2024)
- wasm-pack (for WASM builds)
- cargo-nextest (recommended for faster test runs)
git clone https://github.com/symclaw/symclaw.git
cd symclaw
rustup toolchain install stable
cargo test
Code Style
- Format:
cargo fmt— all code must passcargo fmt --check - Lint:
cargo clippy— zero warnings policy (pedantic + nursery enabled) - No unsafe:
unsafecode is denied workspace-wide - File limit: Keep files under 1,250 lines. If a module grows past this, split it.
- Documentation: All public items should have doc comments (
missing_docsis warned) - Error handling: Use
thiserrorfor library errors,anyhowfor binary crates. No.unwrap()or.expect()(clippy-denied).
Testing
All PRs must pass the full test suite:
# Run all tests
cargo test --workspace
# Run property-based tests (proptest)
cargo test --workspace -- --include-ignored proptest
# Run with nextest for parallel execution
cargo nextest run --workspace
Test Requirements
- Unit tests: Every public function needs at least one test
- Property tests: Mathematical operations must have proptest coverage verifying algebraic identities (e.g.,
simplify(simplify(x)) == simplify(x),d/dx(integral(f, x)) == f) - Edge cases: Test with zero, negative numbers, large coefficients, deeply nested expressions
- No flaky tests: Tests must be deterministic. If randomized, use a fixed seed.
Current test count: 426 tests — PRs should not reduce this number.
Pull Request Process
- Fork the repository and create a branch from
main - Branch naming:
feat/description,fix/description, orrefactor/description - Make your changes with tests
- Run the full check suite:
cargo fmt --check cargo clippy --workspace -- -D warnings cargo test --workspace - Open a PR with a clear description of what and why
- CI must pass — GitHub Actions runs tests on Linux, macOS, Windows, and WASM
- One approval required from a maintainer
Commit Messages
Follow Conventional Commits:
feat(simplify): add trig identity sin²+cos²=1
fix(parser): handle implicit multiplication with parentheses
docs: update API reference for taylor function
test(integrate): add proptest for by-parts rule
Adding Rewrite Rules
Rewrite rules are the heart of SymClaw's simplification engine. Adding new rules requires extra rigor:
- Correctness proof sketch: In your PR description, provide a brief mathematical proof or reference that the rewrite is always valid
- Proptest coverage: Add a property test that generates random expressions and verifies the rule preserves equality (via numeric evaluation)
- Benchmark: Run
cargo benchbefore and after. Rules that cause >5% regression in saturation time need justification - E-graph tests: Add a test in
egraph/showing the rule fires and produces the expected extraction
Example PR description for a new rule:
## New rule: `ln(a*b) → ln(a) + ln(b)` (for a > 0, b > 0)
**Proof**: Direct consequence of logarithm properties.
Restriction to positive reals avoids complex branch issues.
**Proptest**: Generates random positive a, b ∈ (0.01, 1000),
verifies |ln(a*b) - (ln(a) + ln(b))| < 1e-10.
**Benchmark**: No measurable change in saturation time (30 rules → 31).
Good First Issues
Looking for a place to start? These are great entry points:
- Add missing trig identities — e.g., double-angle formulas as rewrite rules
- Improve LaTeX rendering — Better spacing for specific expression patterns
- CLI quality-of-life — Tab completion for function names
- More integration patterns —
∫ sec(x) dx,∫ csc(x) dx - WASM examples — A simple web page demonstrating the WASM API
- Documentation — Examples, tutorials, fixing typos
- Error messages — Make parser errors more user-friendly with span information
Check the issue tracker for labeled issues.
Architecture Overview for New Contributors
symclaw-core (the engine — start here)
├── ast.rs # Expression tree: Arc<Expr> with Symbol interning
├── parser.rs # nom-based parser: string → Arc<Expr>
├── simplify.rs # Multi-pass simplification pipeline
├── egraph.rs # E-graph equality saturation (egg crate)
├── differentiate.rs# Symbolic differentiation
├── integrate.rs # Symbolic integration
├── solve.rs # Equation solver
├── series.rs # Taylor/Maclaurin expansion
├── eval.rs # Numeric evaluation (f64)
├── latex.rs # LaTeX rendering
└── interner.rs # String interning for symbols
Key design decisions:
- Expressions are
Arc<Expr>— immutable, cheaply cloneable, shared subtrees - Symbols are interned integers, not strings — fast comparison
- Simplification runs before other operations — canonical form matters
- E-graph is opt-in (used for deep simplification, not every operation)
See docs/ARCHITECTURE.md for the full deep dive.
Code of Conduct
This project follows the Rust Code of Conduct. Be kind, be constructive, be welcoming.
Questions?
- Open a Discussion on GitHub
- Join our Discord
- Email: [email protected]
Thank you for helping make symbolic computing accessible to everyone! 🦀