Thanks for your interest. src-control is a pre-1.0 research/MVP codebase built one vertical-slice "phase" at a time; contributions are welcome, and this guide covers what you need to get a change merged cleanly.
- Read
CLAUDE.md— it is the working guide: what the project is, the crate layout, and the core invariants that must not break. (AGENTS.mdis a pointer to it, for tooling that looks for that filename.) - Read
ARCHITECTURE.mdfor the design, and skimdocs/adr/for the decision records behind each subsystem. - For anything security-relevant, read
docs/THREAT-MODEL.mdfirst — several "limitations" are deliberate, documented boundaries, not bugs.
The toolchain is pinned in rust-toolchain.toml; rustup
will install it automatically. From a clone:
cargo test --workspace # the whole suite
cargo fmt --all # format (CI enforces --check)
cargo clippy --workspace --all-targets -- -D warnings # lint (CI enforces this)The workspace includes the Tauri desktop crate (apps/desktop/src-tauri), so on
Linux cargo test --workspace needs the Tauri v2 system packages (WebKitGTK
and friends; the exact list is in the Install Tauri Linux prerequisites step
of .github/workflows/ci.yml). If you touch the
desktop frontend, also run npm ci, npm run typecheck and npm test in
apps/desktop (see apps/desktop/README.md).
The demos under demo/ are independent end-to-end proofs and double as
integration tests — if you touch a subsystem, run the relevant demo/run_*.sh.
CI (ci.yml) runs fmt --check, clippy -D warnings, cargo test --workspace --all-targets (Linux and macOS) and cargo doc for the Rust workspace, plus a
desktop job (npm ci, npm audit --audit-level=high, typecheck, test).
An advisory windows job (cargo check and clippy for the workspace, plus
the owner_only, cache::, serve-key, tlsio identity and keygen tests, which
verify the owner-only ACL on .sc/local-key, the sc keygen identity and the TLS
serve key) is not a required check; keep it green when you touch
Windows-specific code. Your PR must be green on all required jobs. Changes to
Cargo.toml or Cargo.lock also run the RustSec audit workflow (it runs daily
as well). CodeQL, Scorecard, the SBOM generation, the vendor-provenance check
(vendored glib only) and a nightly wire_decode fuzz run (also on PRs that touch
fuzz/) live in their own workflows. In addition:
- Every new behavior ships with a test. Tests live in
#[cfg(test)] mod testsnext to the code. A test that materializes to disk must clean up after itself and assert the path is gone. - Respect the dependency rule and quarantines (enforced socially, not just by
the compiler): the adapters
clianddesktopsit on top ofrepo, andrepo → {vfs, crypto} → coreplus the leaf edgesrepo → tlsioandrepo → objio(tlsioandobjiohave no workspace deps).gitiodepends only oncore;reponever links it (clilinks both and passes imported snapshots down).corenever depends on Git, worktrees, or crypto.gixstays ingitioonly; RustCrypto stays incryptoonly; rustls/rcgen stay intlsioonly; the S3 SDK stays inobjioonly. If you find yourself reaching forgix, a RustCrypto type, TLS, or an object-store SDK elsewhere, add a function togitio/crypto/tlsio/objioinstead. - Do not break the core invariants in
CLAUDE.md— content addressing (BLAKE3(canonical_encoding)),Arc<[u8]>-shared blobs, the mode-scoped disk invariant (ephemeral = zero residue), and "never silently drop data." - Public types/fns get a doc comment explaining intent, not mechanics.
- Keep the demos honest.
sc demomust still end by proving zero residue, and any new capability that warrants it gets ademo/run_*.shproof.
Some changes get a security pass before merge as standing policy, not ad-hoc judgment. If your PR does any of the following, say so in the PR description and walk the checklist:
- Touches
crates/crypto,crates/tlsio,crates/objio, or any transport/wire code → re-read the relevantdocs/THREAT-MODEL.mdsection; state in the PR whether any documented boundary moves. If one does, the PR must also updateTHREAT-MODEL.md(and add an ADR if the decision changes). - Adds or swaps a dependency (cargo or npm) → the daily/PR advisory scans
must be green against it; add it to
docs/security/third-party-inventory.mdin the same PR; vendored or patched copies additionally need aPROVENANCE.mdand an inventory annotation. - Adds a CI workflow, action, permission, or secret → SHA-pin the action,
keep write permissions job-scoped, and update
docs/agents/ACCESS.md(seedocs/security/opsec-baseline.md). - Is a security fix → follow
docs/security/vulnerability-response.md: tracked in a draft advisory, human review distinct from the author, no public vulnerability detail before disclosure. - First release / publish channel (future) → reopens the deferred audit
items (reproducible builds, SLSA provenance, published SBOM) — see
docs/audit/ostif-best-practices-audit.md§5, T-22…T-24.
The project records significant decisions as ADRs (docs/adr/, Nygard format:
Context → Decision → Consequences → Alternatives). An Accepted ADR is
immutable — to change a decision, add a new ADR that supersedes it. If your change
alters the architecture, open an issue to discuss the design before a large PR, and
expect to add or amend an ADR alongside the code.
- Bugs / features: open a GitHub issue.
- Security vulnerabilities: do not open a public issue — follow
SECURITY.md(private email or GitHub private reporting).
By submitting a contribution you agree it is licensed under the project's Apache License 2.0, consistent with Section 5 of that license.