for an overview, especially if you are familiar with C++.</p>
<!--- TODO: A section asking for people to report documentation bugs and
---- asking them to check if the problem exists in the prerelease docs.
---->
<h2id="setting-up-a-development-environment">Setting up a development environment<aclass="headerlink"href="#setting-up-a-development-environment"title="Permanent link">¶</a></h2>
<p>To develop <code>jj</code>, the mandatory steps are simply
to <ahref="https://www.rust-lang.org/tools/install">install Rust</a> (the default
installer options are fine), clone the repository, and use <code>cargo build</code>
, <code>cargo fmt</code>,
<code>cargo clippy --workspace --all-targets</code>, and
<code>cargo test --workspace</code>. If you are preparing a PR, there are some additional
<p>These are listed roughly in order of decreasing importance.</p>
<ol>
<li>
<p>Nearly any change to <code>jj</code>'s CLI will require writing or updating snapshot
tests that use the <ahref="https://insta.rs/"><code>insta</code></a> crate. To make this
convenient, install the <code>cargo-insta</code> binary.
Use <code>cargo insta test --workspace</code> to run tests,
and <code>cargo insta review --workspace</code> to update the snapshot tests.
The <code>--workspace</code> flag is needed to run the tests on all crates; by default,
only the crate in the current directory is tested.</p>
</li>
<li>
<p>GitHub CI checks require that the code is formatted with the <em>nightly</em>
version of <code>rustfmt</code>. To do this on your computer, install the nightly
toolchain and use <code>cargo +nightly fmt</code>.</p>
</li>
<li>
<p>Your code will be rejected if it cannot be compiled with the minimal
supported version of Rust ("MSRV"). Currently, <code>jj</code> follows a rather
casual MSRV policy: "The current <code>rustc</code> stable version, minus one."
As of this writing, that version is <strong>1.71.0</strong>.</p>
</li>
<li>
<p>Your code needs to pass <code>cargo clippy</code>. You can also
use <code>cargo +nightly clippy</code> if you wish to see more warnings.</p>
</li>
<li>
<p>You may also want to install and use <code>cargo-watch</code>. In this case, you should
exclude <code>.jj</code>. directory from the filesystem watcher, as it gets updated on
every <code>jj log</code>.</p>
</li>
<li>
<p>To run tests more quickly, use <code>cargo nextest run --workspace</code>. To
use <code>nextest</code> with <code>insta</code>,
use <code>cargo insta test --workspace --test-runner nextest</code>.</p>
</li>
</ol>
<h2id="previewing-the-html-documentation">Previewing the HTML documentation<aclass="headerlink"href="#previewing-the-html-documentation"title="Permanent link">¶</a></h2>
<p>The documentation for <code>jj</code> is automatically published to the website
<ahref="https://martinvonz.github.io/jj/">https://martinvonz.github.io/jj/</a>. At the moment, this is experimental,
but we hope to advertise this website to our users soon.</p>
<p>When editing documentation, we'd appreciate it if you checked that the
result will look as expected when published to the website.</p>
<h3id="setting-up-the-prerequisites">Setting up the prerequisites<aclass="headerlink"href="#setting-up-the-prerequisites"title="Permanent link">¶</a></h3>
<p>To build the website, you must have Python and <code>poetry</code> installed. If
your distribution packages <code>poetry</code>, something like <code>apt install
python3-poetry</code> is likely the best way to install it. Otherwise, you
can download Python from <ahref="https://python.org">https://python.org</a> or follow the <ahref="https://docs.python.org/3/using/index.html">Python
installation instructions</a>. Finally, follow the <ahref="https://python-poetry.org/docs/#installation">Poetry installation
instructions</a>.</p>
<p>Once you have <code>poetry</code> installed, you should ask it to install the rest
of the required tools into a virtual environment as follows:</p>
<h3id="building-the-html-docs-locally-with-live-reload">Building the HTML docs locally (with live reload)<aclass="headerlink"href="#building-the-html-docs-locally-with-live-reload"title="Permanent link">¶</a></h3>
<p>The HTML docs are built with <ahref="https://github.com/mkdocs/mkdocs">MkDocs</a>. After
following the above steps, you should be able to view the docs by running</p>
<divclass="highlight"><pre><span></span><code><spanclass="c1"># Note: this and all the commands below should be run from the root of</span>
<p>You should occasionally check the terminal from which you ran <code>mkdocs serve</code> for
any build errors or warnings. Warnings about <code>"GET /versions.json HTTP/1.1" code
404</code> are expected and harmless.</p>
<h3id="how-to-build-the-entire-website-not-usually-necessary">How to build the entire website (not usually necessary)<aclass="headerlink"href="#how-to-build-the-entire-website-not-usually-necessary"title="Permanent link">¶</a></h3>
<p>The full <code>jj</code> website includes the documentation for several <code>jj</code> versions
(<code>prerelease</code>, latest release, and the older releases). The top-level
URL <ahref="https://martinvonz.github.io/jj">https://martinvonz.github.io/jj</a> redirects to
<ahref="https://martinvonz.github.io/jj/latest">https://martinvonz.github.io/jj/latest</a>, which in turn redirects to
the docs for the last stable version.</p>
<p>The different versions of documentation are managed and deployed with
<ahref="https://github.com/jimporter/mike"><code>mike</code></a>, which can be run with
<code>poetry run -- mike</code>.</p>
<p>On a POSIX system or WSL, one way to build the entire website is as follows (on
Windows, you'll need to understand and adapt the shell script):</p>
<ol>
<li>
<p>Check out <code>jj</code> as a co-located <code>jj + git</code> repository (<code>jj clone --colocate</code>),
cloned from your fork of <code>jj</code> (e.g. <code>jjfan.github.com/jj</code>). You can also use a
pure Git repo if you prefer.</p>
</li>
<li>
<p>Make sure <code>jjfan.github.com/jj</code> includes the <code>gh-pages</code> branch of the jj repo
and run <code>git fetch origin gh-pages</code>.</p>
</li>
<li>
<p>Go to the GitHub repository settings, enable GitHub Pages, and configure them
to use the <code>gh-pages</code> branch (this is usually the default).</p>
</li>
<li>
<p>Run the same <code>sh</code> script that is used in GitHub CI (details below):</p>
<p>This should build the version of the docs from the current commit,
deploy it as a new commit to the <code>gh-pages</code> branch,
and push the <code>gh-pages</code> branch to the origin.</p>
</li>
<li>
<p>Now, you should be able to see the full website, including your latest changes
to the <code>prerelease</code> version, at <code>https://jjfan.github.io/jj/prerelease/</code>.</p>
</li>
<li>
<p>(Optional) The previous steps actually only rebuild
<code>https://jjfan.github.io/jj/prerelease/</code> and its alias
<code>https://jjfan.github.io/jj/main/</code>. If you'd like to test out version switching
back and forth, you can also rebuild the docs for the latest release as follows.</p>
<divclass="highlight"><pre><span></span><code>jj<spanclass="w"></span>new<spanclass="w"></span>v1.33.1<spanclass="w"></span><spanclass="c1"># Let's say `jj 1.33.1` is the currently the latest release</span>
<p>If you want to preserve some of the changes you made, you can do <code>jj branch
set my-changes -r gh-pages</code> BEFORE running the above commands.</p>
</li>
</ol>
<h4id="explanation-of-the-docs-build-deploy-script">Explanation of the <code>docs-build-deploy</code> script<aclass="headerlink"href="#explanation-of-the-docs-build-deploy-script"title="Permanent link">¶</a></h4>
<p>The script sets up the <code>site_url</code> mkdocs config to
<code>'https://jjfan.github.io/jj/'</code>. If this config does not match the URL
where you loaded the website, some minor website features (like the
version switching widget) will have reduced functionality.</p>
<p>Then, the script passes the rest of its arguments to <code>potery run -- mike
deploy</code>, which does the rest of the job. Run <code>poetry run -- mike help deploy</code> to
find out what the arguments do.</p>
<p>If you need to do something more complicated, you can use <code>poetry run -- mike
...</code> commands. You can also edit the <code>gh-pages</code> branch directly, but take care
to avoid files that will be overwritten by future invocations of <code>mike</code>. Then,
you can submit a PR based on the <code>gh-pages</code> branch of
<ahref="https://martinvonz.github.com/jj">https://martinvonz.github.com/jj</a> (instead of the usual <code>main</code> branch).</p>
<h2id="modifying-protobuffers-this-is-not-common">Modifying protobuffers (this is not common)<aclass="headerlink"href="#modifying-protobuffers-this-is-not-common"title="Permanent link">¶</a></h2>
<p>Occasionally, you may need to change the <code>.proto</code> files that define jj's data
storage format. In this case, you will need to add a few steps to the above
workflow.</p>
<ul>
<li>Install the <code>protoc</code> compiler. This usually means either <code>apt-get install
protobuf-compiler</code> or downloading <ahref="https://github.com/protocolbuffers/protobuf/releases">an official release</a>. The
<code>prost</code><ahref="https://docs.rs/prost-build/latest/prost_build/#sourcing-protoc">library docs</a> have additional advice.</li>
<li>Run <code>cargo run -p gen-protos</code> regularly (or after every edit to a <code>.proto</code>
file). This is the same as running <code>cargo run</code> from <code>lib/gen-protos</code>. The
<code>gen-protos</code> binary will use the <code>prost-build</code> library to compile the
<code>.proto</code> files into <code>.rs</code> files.</li>
<li>If you are adding a new <code>.proto</code> file, you will need to edit the list of
these files in <code>lib/gen-protos/src/main.rs</code>.</li>
</ul>
<p>The <code>.rs</code> files generated from <code>.proto</code> files are included in the repository,
and there is a GitHub CI check that will complain if they do not match.</p>
<scriptid="__config"type="application/json">{"base":".","features":[],"search":"assets/javascripts/workers/search.dfff1995.min.js","translations":{"clipboard.copied":"Copied to clipboard","clipboard.copy":"Copy to clipboard","search.result.more.one":"1 more on this page","search.result.more.other":"# more on this page","search.result.none":"No matching documents","search.result.one":"1 matching document","search.result.other":"# matching documents","search.result.placeholder":"Type to start searching","search.result.term.missing":"Missing","select.version":"Select version"},"version":{"provider":"mike"}}</script>