Thank you for your interest in contributing to codegraph! This document provides guidelines and instructions for contributing.
This project adheres to the Rust Code of Conduct. Please read CODE_OF_CONDUCT.md before contributing.
Before contributing, please read our Constitution which defines our core principles and governance model.
- Rust 1.70+ (install via rustup)
- Git
git clone https://github.com/anvanster/codegraph.git
cd codegraph
# Build entire workspace
cargo build --workspace
# Test entire workspace (421+ tests)
cargo test --workspace
# Build specific crate
cargo build -p codegraph-python
cargo test -p codegraph-rustcodegraph/
├── crates/
│ ├── codegraph/ # Graph database core
│ ├── codegraph-parser-api/ # Parser trait and types
│ ├── codegraph-python/ # Python parser
│ ├── codegraph-rust/ # Rust parser
│ ├── codegraph-typescript/ # TypeScript/JavaScript parser
│ └── codegraph-go/ # Go parser
├── Cargo.toml # Workspace root
└── docs/ # Documentation
All code MUST be developed using TDD methodology:
- RED: Write failing test first
- GREEN: Implement minimum code to pass
- REFACTOR: Clean up while keeping tests green
Pull requests without tests will be rejected.
Before submitting:
# Format code (workspace-wide)
cargo fmt --all
# Lint with clippy (workspace-wide)
cargo clippy --workspace --all-targets --all-features -- -D warnings
# Run all tests (workspace-wide)
cargo test --workspace
# Test specific crate
cargo test -p codegraph-python
# Check documentation
cargo doc --workspace --no-depsAll checks must pass.
- Fork the repository
- Create a branch for your feature/fix
git checkout -b feature/my-new-feature
- Write tests first (TDD)
- Implement your changes
- Ensure all tests pass
- Commit with clear messages
git commit -m "Add feature: description" - Push to your fork
git push origin feature/my-new-feature
- Open a Pull Request with:
- Clear description of changes
- Link to related issue (if any)
- Test coverage information
- Performance impact (if applicable)
Follow conventional commits:
<type>: <description>
[optional body]
[optional footer]
Types:
feat: New featurefix: Bug fixdocs: Documentation changestest: Adding testsrefactor: Code refactoringperf: Performance improvementschore: Maintenance tasks
Examples:
feat: add GraphML export format
fix: prevent panic on empty graph traversal
docs: update README with parser examples
test: add integration tests for RocksDB backend
Open an issue with:
- Clear description of the bug
- Steps to reproduce
- Expected vs actual behavior
- Environment details (OS, Rust version)
- Minimal code example
Open an issue with:
- Clear use case description
- Proposed API design
- Alignment with constitution principles
- Alternative approaches considered
For major features, an RFC may be required.
We welcome new language parsers! Follow this guide:
cd crates
cargo new codegraph-<language> --libUpdate Cargo.toml:
[package]
name = "codegraph-<language>"
version = "0.1.0"
edition.workspace = true
license.workspace = true
authors.workspace = true
[dependencies]
codegraph-parser-api = { workspace = true }
codegraph = { workspace = true }
# Add language-specific parser (tree-sitter, syn, etc.)Create src/parser_impl.rs:
use codegraph::CodeGraph;
use codegraph_parser_api::{CodeParser, FileInfo, ParserConfig, ParserError, ParserMetrics};
use std::path::Path;
pub struct YourLanguageParser {
config: ParserConfig,
metrics: Mutex<ParserMetrics>,
}
impl CodeParser for YourLanguageParser {
fn language(&self) -> &str {
"your-language"
}
fn file_extensions(&self) -> &[&str] {
&[".ext"]
}
fn parse_source(&self, source: &str, file_path: &Path, graph: &mut CodeGraph)
-> Result<FileInfo, ParserError> {
// Implementation
}
// ... other trait methods
}Create src/visitor.rs and src/extractor.rs to:
- Parse source code using language-specific parser
- Extract functions, classes, modules, etc.
- Extract imports and relationships
- Convert to CodeIR format
Add comprehensive tests in tests/:
unit_tests.rs- Test visitor and extractor logicintegration_tests.rs- End-to-end parsing testsparser_impl_tests.rs- CodeParser trait tests
Aim for 60+ tests with >85% coverage.
- Add README with usage examples
- Document language-specific features
- Add to workspace README
Update workspace Cargo.toml:
[workspace]
members = [
# ...existing crates
"crates/codegraph-<language>",
]See existing implementations for reference:
codegraph-python- Uses rustpython-parsercodegraph-rust- Uses syncodegraph-typescript- Uses tree-sitter-typescriptcodegraph-go- Uses tree-sitter-go
- Any maintainer can approve and merge
- No RFC needed
- Keep PR description clear
- RFC as GitHub issue required
- At least 2 maintainer approvals
- 7-day comment period
- Update docs and tests
- Formal RFC required
- All maintainers must approve
- 14-day comment period
- Deprecation cycle required
- Migration guide mandatory
Respect the layer boundaries:
User Tools (you build this)
↓
Code Helpers (convenience API)
↓
Query Builder (fluent interface)
↓
Core Graph (nodes, edges)
↓
Storage Backend (RocksDB, memory)
❌ Bad (Magic):
// Auto-detects language, scans directory, parses files
let graph = CodeGraph::from_directory("./src")?;✅ Good (Explicit):
let mut graph = CodeGraph::open("./project.graph")?;
let file_id = graph.add_file(Path::new("main.rs"), "rust")?;
// User explicitly parses and adds entitiesAlways use Result<T> for fallible operations:
pub fn get_node(&self, id: &NodeId) -> Result<Node> {
// Implementation
}Never panic in library code. Use proper error types.
Every public item must be documented:
/// Get a node by ID.
///
/// # Errors
///
/// Returns [`GraphError::NodeNotFound`] if the node doesn't exist.
///
/// # Example
///
/// ```
/// let node = graph.get_node(&node_id)?;
/// ```
pub fn get_node(&self, id: &NodeId) -> Result<Node> {
// Implementation
}- Core graph: 95%+
- Storage backends: 90%+
- Helpers: 85%+
- Export functions: 80%+
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_specific_behavior() {
// Arrange
let mut graph = CodeGraph::in_memory().unwrap();
// Act
let result = graph.add_node(node);
// Assert
assert!(result.is_ok());
}
}Place in tests/ directory:
// tests/integration_test.rs
use codegraph::*;
#[test]
fn test_end_to_end_workflow() {
// Test complete workflows
}For performance-critical changes, include benchmarks:
use criterion::{black_box, criterion_group, criterion_main, Criterion};
fn benchmark_add_node(c: &mut Criterion) {
c.bench_function("add_node", |b| {
b.iter(|| {
// Benchmark code
});
});
}
criterion_group!(benches, benchmark_add_node);
criterion_main!(benches);Run benchmarks:
cargo benchMaintainers follow this process for releases:
- Update version in
Cargo.toml - Update
CHANGELOG.md - Run full test suite
- Create git tag:
v0.x.y - Push to crates.io:
cargo publish - Create GitHub release with notes
- Questions: Open a GitHub Discussion
- Bugs: Open a GitHub Issue
- Security: Email maintainers directly (see SECURITY.md)
Contributors will be recognized in:
CONTRIBUTORS.mdfile- Release notes
- Project README
Thank you for contributing to codegraph! 🎉