Contributing to Oleafly
Thanks for wanting to make Oleafly better! This guide gets you from a fresh clone to a working dev build, and covers how we review and land changes.
Esta página aún no está disponible en tu idioma.
Thanks for wanting to make Oleafly better! This guide gets you from a fresh clone to a working dev build, and covers how we review and land changes.
Ways to contribute
Section titled “Ways to contribute”- Report a bug: open a bug report.
- Request a feature: open a feature request.
- Report a vulnerability privately by following SECURITY.md.
- Send a pull request: see below.
For anything larger than a small fix, open an issue first so we can agree on the approach before you invest time.
Prerequisites
Section titled “Prerequisites”| Tool | Version | Notes |
|---|---|---|
| Node.js | 22.13+ | Required by pnpm 11 |
| pnpm | 11.9+ | Enable Corepack or install the version declared in package.json |
| Rust | stable (1.77+) | includes cargo |
| Platform deps | - | See the Tauri v2 prerequisites for your OS (on Linux: libwebkit2gtk-4.1-dev, librsvg2-dev, patchelf, …) |
Getting started
Section titled “Getting started”git clone https://github.com/Oleafly/Oleafly.gitcd Oleaflypnpm install
# Find your target with `rustc -vV | grep host`.bash scripts/fetch-tectonic.sh aarch64-apple-darwin # or your host triplebash scripts/fetch-typst.sh aarch64-apple-darwin
# Run the app in dev mode (hot-reloads the frontend, rebuilds Rust on change):pnpm tauri devThe Tectonic, Biber, and Typst binaries are git-ignored on purpose - never commit them. The fetch script drops them in
src-tauri/binaries/, which is wherebundle.externalBinexpects them.
Building a production bundle locally
Section titled “Building a production bundle locally”pnpm tauri buildInstallers land in src-tauri/target/release/bundle/.
Project layout
Section titled “Project layout”src/ React + TypeScript app shell components/ UI (editor, pdf, ai, layout, files, …) lib/ framework-agnostic helpers (ai-providers, github, …) store/ Zustand state slicespackages/ @oleafly/* engine packages, consumed as TypeScript sourcesrc-tauri/src/ Rust backend (Tauri commands) commands.rs Tauri command handlers and compile entry points latex_engine.rs Tectonic and latexmk selection mcp/ local MCP server, routing, and native tools project.rs project/file CRUD (path-sandboxed - see `resolve`) git.rs git integration github.rs GitHub OAuth device flow paths.rs path helpers + project-id validationdocs/ user-facing documentationscripts/ sidecar fetchers, language servers, release checks, icon generationpnpm test # frontend unit tests (Vitest)cd src-tauri && cargo test --lib # Rust backend testsBackend logic that touches the filesystem, git, or user paths must have a
test. The path-sandboxing helpers (resolve_within, validate_project_id) and
log/URL parsers are covered in #[cfg(test)] modules - extend them when you
change that code. On the frontend, the LaTeX masking that decides what the
spell/grammar checker sees is pure and unit-tested in
src/components/editor/cm/latex-mask.test.ts - add a case there when you change
what counts as prose.
Code style
Section titled “Code style”- TypeScript - the frontend must typecheck and build:
pnpm build, and pass the Biome lint gate:pnpm lint(auto-fix what’s safe withpnpm lint:fix). The gate blocks on correctness errors. An existing accessibility/style backlog is reported as non-blocking warnings (seebiome.json). Prefer not adding new warnings. - Rust - the backend must be
cargo fmt-clean andcargo clippy-clean. Both are blocking in CI (clippyruns with-D warnings). Runcargo fmtandcargo clippy --all-targets --fixbefore pushing. - Match the surrounding code - comment density, naming, and idiom.
Pull requests
Section titled “Pull requests”- Fork and branch from
main(git checkout -b fix/short-description). - Keep the change focused. Put unrelated refactors in their own PR.
- Make sure
pnpm lint,pnpm build, andcargo test --libpass locally. - Fill out the PR template - link the issue, describe the change, note how you tested it.
- CI must be green (the frontend build and Rust tests are required checks).
We squash-merge, so a clean PR title is the commit message. Conventional-commit
style is appreciated but not required (e.g. fix: reject absolute paths in resolve).
Releases (maintainers)
Section titled “Releases (maintainers)”Releases are cut by pushing a version tag. The
Release workflow builds macOS Apple Silicon, Windows x64, Linux x64, and Linux ARM64 installers. It attaches them to a draft for review. Publishing requires a second guarded workflow run for the same tag.
# Bump the version everywhere it's declared (package.json, Cargo.toml,# Cargo.lock, tauri.conf.json) in one shot, so the tag can't drift:./scripts/bump-version.sh 0.3.6
git commit -am "chore: release v0.2.0"git tag v0.2.0 && git push origin v0.2.0By contributing, you agree that your contributions are licensed under the project’s GNU Affero General Public License v3.0 or later.