This guide provides comprehensive information for developers working with Provability-Fabric, including setup, development workflows, and contribution guidelines.
- Go 1.23+ - Core services and CLI tools
- Rust (stable) - Performance-critical components; see root
rust-toolchain.toml - Lean 4 - Formal proof development
- Docker - Container management
- Kubernetes - Local development cluster
- Node.js 20+ - UI and TypeScript components
# Clone the repository (upstream; use your fork URL if contributing)
git clone https://github.com/SentinelOps-CI/provability-fabric.git
cd provability-fabric
# Install Go dependencies (run from each Go module you use, e.g. core/cli/pf)
cd core/cli/pf && go mod download && cd ../../..
# Install Rust dependencies
cargo fetch
# Install Lean dependencies (from the Lake project you are building)
lake update
# Node.js: install per package (there is no root package.json). Examples:
# cd runtime/ledger && npm ci && npx prisma generate && cd ../..
# cd console && npm ci && cd ../..# Install development tools
make install-dev-tools
# Verify installation
pf --version
lake --version
cargo --versionprovability-fabric/
├── core/ # Core framework components
├── runtime/ # Runtime services and components
├── adapters/ # Verification engine adapters
├── bench/ # Benchmarks (SWE-bench: runner.py / RunConfig / _execute_run, runner_core.run_swebench, replay, cost accounting, atomic predictions, run_status.json, predictions.sha256, env.json, empty_patch_reason codes). Real agent runs and harness require WSL/Linux; smoke and unit tests use mock/fixtures and run on any OS.
├── tests/ # Test suites and examples
├── docs/ # Documentation
├── tools/ # Development and build tools
└── scripts/ # Automation scripts
core/cli/- Command-line interfacecore/sdk/- Client SDKs for multiple languagescore/crypto/- Cryptographic utilitiescore/lean-libs/- Lean proof libraries
runtime/admission-controller/- Kubernetes admission controller (Go)runtime/attestor/- Attestation service (Rust; Redis-backed)runtime/kms-proxy/- KMS/key proxy for signing and encryption (Rust)runtime/tool-broker/- Tool approval and broker (Rust)runtime/sidecar-watcher/- Runtime monitoring and policy enforcement (Rust)runtime/labeler/- Proof-carrying labeler for JSON path and taint rules (Rust)runtime/wasm-sandbox/- WASM execution environment for adapters (Rust; wasmtime)runtime/ledger/- Transparency ledger (Node/TypeScript)
Rust runtime crates and the Rust adapters (adapters/http-get, adapters/file-read) are part of the root Cargo workspace. See Rust workspace below.
bench/swebench/- SWE-bench runner and PF evidence pipeline. Layout:run_config.py(RunConfig,build_argument_parser),runner.py(main()→ validatedRunConfig→_execute_run),runner_core.py(run_swebench(config)for programmatic use),workspace_manager.py,instance_processor.py,evidence_writer.py,predictions_writer.py,summary_writer.py,cost_reporter.py,provider_env.py(shared OpenHands LLM provider, keys, Prime default base URL,env.jsondiagnostics),engines/(OpenHands, mock,openhands_adapter.get_engine, optionaldeterministic_engine). Run withpf bench swebench run(orpython bench/swebench/runner.pyfrom repo root). Use--experiment-dirto point at an experiment (e.g.experiments/exp-step2-lite-smoke); the runner then usesmanifest.jsonbudgets (max_steps,timeout_sec) as defaults. With--engine openhands, OpenHands must be available or the run exits (no stub). Producespredictions.jsonl(SWE-bench schema),predictions.sha256(same dir),predictions.pfmeta.jsonl(PF provenance sidecar, optionalempty_patch_reason), and evidence underruns/<run_id>/<instance_id>/(run.log, model.patch, metadata.json, patch_apply_check.json with optionalempty_patch_reason, empty_patch_reason.txt, engine_trace.json, replay_bundle.json, cost_report.json, timing.json with wall_clock_s, timeout_reached, termination_reason). When guarded:evidence/andpolicy_compliance_summary.jsonare always written. Runner writesrun_status.jsonandruns/<run_id>/env.json(python_version, platform, pip_freeze_hash, openhands_version, datasets_version, swebench_version when available). Replay:pf bench swebench replay --run_id <id>. Seebench/swebench/README.mdfor full options, entry points (pf CLI vs Python runner), known limitations (large repos, preflight caveat), reproducibility (env.json, env_drift, version pinning), and engine tuning (constants.py, PF_* env overrides). Canonical Step-2 entrypoint:bash experiments/scripts/run-baseline-pf-cycle.sh(optional--update-run-ids,--triage). Golden cycle: One trusted baseline+PF pair; seeexperiments/exp-step2-lite-smoke/golden-cycle.mdfor artifacts and acceptance checks;run-ids.mdupdated only viaupdate_run_ids_if_green.py. Makefile:make swebench-step2,make swebench-compare BASELINE_RUN_DIR=... PF_RUN_DIR=...,make swebench-triage,make swebench-regressions(list_delta_cases + extract_case_bundle + bucket for baseline_solved_pf_failed slice). Run/eval binding: Harness writeseval_metadata.jsonper eval dir (run_id, predictions_sha256, dataset/split/versions). Compare with--require-harnessenforces run_id consistency, predictions_sha256 when present, and stale-eval check (predictions file must not be newer than eval report). Budget drift: When both run dirs haveexperiment_manifest.json, compare asserts timeout_sec, max_steps, max_tool_calls, model, model_params match; drift fails the run. Compare report includes reproducibility fields,empty_patch_reasons_topN, replay (from replay_summary.json; run_replay_sample also writes replay/instance_results.jsonl; replays all when PF-resolved zero-violation count ≤20, else deterministic sample), policy (reason_codes_topN, denied_commands_topN), and denial recovery (denials_total_pf, episodes_aborted_after_denial_pf, recovered_after_denial_pf_rate); schemaexperiments/schemas/compare_report.schema.json. Green run packaging: Whenupdate_run_ids_if_green.pypasses all gates, it runs export and writespublish/PUBLISH.md, publish/GOLDEN.ok (run IDs, pf_commit, timestamp, parity_gate_passed), publish/RESULTS.md (audit summary).run-ids.mdis under experiments/exp-step2-lite-smoke/run-ids.md. Stress slice:experiments/exp-step2-lite-stress-large-repos/;.github/workflows/bench-swebench-stress-scheduled.yamlruns weekly and callsexperiments/scripts/summarize_stress_run.pyto produce stress_summary.json (timeout_rate_*, wall_clock_s median/p95, guard_overhead_s_median). Expanded slices:experiments/exp-step2-lite-medium-50/,experiments/exp-step2-lite-fullish-200/. Criterion benchmarks:make bench-save-baselinesaves Criterion baseline and writesbench/BASELINE.md(date, git_sha, machine); CI has a smoke-bench job (compile + run, no regression gate). Tests: Smokepytest tests/test_swebench_runner_smoke.py -q. Provider/compare/eval cleanup/regression bundle: seedocs/internal/swebench-stabilization-regression-matrix.md. CI (.github/workflows/bench-swebench-unit.yaml) runs: test_experiments_compare_runs, test_validate_predictions, test_check_no_stub, test_validate_pf_run, test_loader_from_file, test_workspace_plan, test_replay_roundtrip, test_swebench_runner_smoke, test_openhands_engine, test_policy_loader, test_cost_report, test_proof_hook, test_check_wsl_env, test_fill_manifest_from_run, test_list_delta_cases, test_bucket_pf_failures, test_policy_guard_deny_allow, test_provider_env, test_openhands_provider_env, test_run_swebench_eval_cleanup, test_run_config. Additional in-repo tests (run locally as needed): test_runner_core, test_instance_processor, test_workspace_manager, test_evidence_writer, test_engine_interface, test_predictions_writer, test_summary_writer, test_runner_cost_reporter_facade, test_swebench_edge_cases, test_swebench_properties, test_error_recovery, test_summarize_stress_run. Real agent runs and harness require WSL or Linux.
# Create feature branch
git checkout -b feature/your-feature-name
# Make changes and test
make test
make build
# Commit changes
git add .
git commit -m "feat: add your feature description"
# Push and create PR
git push origin feature/your-feature-name# Run all tests
make test
# Run specific test suites
make test-unit
make test-integration
make test-e2e
# Run tests with coverage
make test-coverage
# Run performance benchmarks
make benchThe repo root defines a Cargo workspace (see root Cargo.toml and rust-toolchain.toml). From the repo root:
- Build:
cargo build(all workspace members) - Test:
cargo test --workspace --exclude sidecar-watcher,cargo test -p sidecar-watcher --lib, andcargo test -p sidecar-watcher --tests(explicit[[test]]targets; seeruntime/sidecar-watcher/tests/README.md) - Clippy:
cargo clippy --workspace -- -D warnings - Policy / advisories: Install cargo-deny and run
cargo deny check(configuration in repository rootdeny.toml). CI runs this via.github/workflows/cargo-deny.ymlwhen manifests change.
Optional crates (not in workspace or need extra deps): runtime/egress-firewall (Hyperscan), core/sdk/rust (protoc), runtime/sidecar-watcher/fuzz. See root Cargo.toml comments; build them separately when their dependencies are available. See Extension points for runtime and adapter boundaries.
- Main pipeline:
.github/workflows/ci.ymland reusablereusable-ci-*.ymlfiles (see CI reference). - Editing workflows triggers actionlint (
.github/workflows/actionlint.yml), which runs a pinnedrhysd/actionlintcontainer locally equivalent to:docker run --rm -v "$PWD:/workspace" -w /workspace rhysd/actionlint:1.7.12 -color.
- Prefer targeted
#[allow(dead_code)]on specific types or impls rather than crate-level allows. Over time, remove unused code or implement stubs so allows can be narrowed or removed. - Track TODOs in issues; use
// TODO(issue-N):in comments when possible.
# Build all components
make build
# Build specific components
make build-core
make build-runtime
make build-adapters
# Build for different platforms
make build-multiarch# Start local development cluster
make dev-cluster
# Deploy to local cluster
make dev-deploy
# Monitor local deployment
make dev-monitor
# Clean up local environment
make dev-cleanup# Install Lean 4
curl -sL https://raw.githubusercontent.com/leanprover/elan/master/elan-init.sh | sh
# Install mathlib
lake update
# Build Lean libraries
lake buildimport Mathlib.Data.String.Basic
-- Define your theorem
theorem example_theorem (x : Nat) : x + 0 = x := by
-- Your proof here
rw [Nat.add_zero]
-- Use Lean tactics
theorem another_theorem (a b : Nat) : a + b = b + a := by
exact Nat.add_comm a b# Check proof quality
make lean-gate
# Check build time budgets
make lean-time-budget
# Run proofbench
make proofbench- Follow Go standard formatting (
gofmt) - Use
golintfor code quality - Write comprehensive tests
- Use meaningful variable names
package core
import (
"testing"
"github.com/stretchr/testify/assert"
)
func TestExample(t *testing.T) {
result := ExampleFunction()
assert.Equal(t, expected, result)
}# Build Go binaries
go build ./cmd/...
# Cross-compile
GOOS=linux GOARCH=amd64 go build ./cmd/...
# Install locally
go install ./cmd/...- Follow Rust formatting (
rustfmt) - Use
clippyfor linting - Write comprehensive tests
- Use proper error handling
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_example() {
let result = example_function();
assert_eq!(result, expected);
}
}# Build Rust components
cargo build
# Build with optimizations
cargo build --release
# Run tests
cargo test
# Run benchmarks
cargo bench- Use ESLint and Prettier
- Follow TypeScript best practices
- Write comprehensive tests
- Use proper type definitions
import { describe, it, expect } from 'vitest';
import { exampleFunction } from './example';
describe('exampleFunction', () => {
it('should return expected result', () => {
const result = exampleFunction();
expect(result).toBe(expected);
});
});# Install dependencies
npm install
# Build TypeScript
npm run build
# Run tests
npm test
# Run linting
npm run lint-
Lean Build Failures
# Check Lean version lean --version # Clean and rebuild lake clean lake build
-
Go Module Issues
# Clean module cache go clean -modcache # Download dependencies go mod download
-
Rust Compilation Errors
# Check Rust version rustc --version # Update Rust rustup update
# Enable debug logging
export PF_LOG_LEVEL=debug
# Run with debug flags
pf --debug
# Enable Go debug
export GODEBUG=1
# Enable Rust debug
RUST_LOG=debug cargo run# Go profiling
go test -cpuprofile=cpu.prof -memprofile=mem.prof
# Rust profiling
cargo install flamegraph
cargo flamegraph
# Lean profiling
lake build --profile# Run all benchmarks
make bench
# Run specific benchmarks
cargo bench --package core
go test -bench=. ./core/...- Create Feature Branch - Use descriptive branch names
- Write Tests - Include tests for new functionality
- Update Documentation - Keep docs current with code changes
- Submit PR - Include clear description and testing notes
- Address Feedback - Respond to review comments promptly
Use conventional commit format:
feat: add new feature
fix: resolve bug
docs: update documentation
style: format code
refactor: restructure code
test: add tests
chore: maintenance tasks
- Tests pass locally
- Code follows style guidelines
- Documentation is updated
- Changes are tested
- No breaking changes (or documented)
- Commit messages are clear
- Documentation: This guide and other docs
- GitHub Issues: Bug reports and feature requests
- Discord: Community discussions and help
- Code Examples: Check the
examples/directory
- Development Questions: GitHub Discussions
- Bug Reports: GitHub Issues
- Feature Requests: GitHub Issues with enhancement label
- Security Issues: GitHub Security Advisories
This guide provides the foundation for developing with Provability-Fabric. As you become more familiar with the framework, explore the codebase, contribute improvements, and help build a robust ecosystem for provable AI systems.
Remember to:
- Write clear, maintainable code
- Include comprehensive tests
- Update documentation
- Follow established patterns
- Contribute to the community